Your custom remote development environment: run VS Code on server and access it anywhere

Cover image

Introduction #

Visual Studio Code is one of the most used code editors out there, with lots of extensions, integrations, and other functionalities that makes dev's life easier.

It's built with Electron and it is primary language it's Typescript, which means that it's almost like a web-app in your computer. This facts gives us the possibility to modify this app and run it on a server.

This is what code-server project is doing. They have developed an open source (MIT) project that allows users to run VSCode on a remote server, accessible through the browser.

What are the PRO's?

How do I start? #

It is very simple to get started, all you need is the following:

First step #

Create your Vultr instance (personally I recommend Ubuntu LTS), with 4GB RAM and 2 CPU, more depending on team size and number of repositories/languages enabled. You can also use an existing Vultr instance of yours.

Optional: Update your instance: #

Before proceeding with the installation, update your instance. You can do it by simply running the following command (which updates software lists and downloads latests updates):

sudo apt update && sudo apt upgrade -y

Download code-server #

Wait until the instance is created, and then open a terminal on your computer and SSH into your instance.

Example:
ssh [email protected]

Once in visit the releases page of the project in Github and copy the link to the download for the latest version available (Linux).

In the terminal use wget to download the release into your instance:

wget https://github.com/cdr/code-server/releases/download/1.1119-vsc1.33.1/code-server1.1119-vsc1.33.1-linux-x64.tar.gz

Now let's extract the files from the .tar.gz downloaded file:

tar xvf code-server1.1119-vsc1.33.1-linux-x64.tar.gz

Once done, a new folder is created with the main binary of the project.

Start your code-server #

cd into the created folder ("code-server1.1119-vsc1.33.1-linux-x64") and run the following commands:

chmod +x code-server
sudo ./code-server -p 8080 

The first command gives execution permissions for the binary, and the second starts the main server in the port 8080 (you can choose whatever port you want). Also this last command provides the main password to access your IDE, so copy it and secure it.

The last command will run "forever" until force closed, so maybe it's useful to you to start it in background (with & or nohup), in order to not block your terminal:

sudo ./code-server -p 8080 &

Browse to your server #

It is almost done! We have code-server running in the port 8080. Now open your browser, type your instance IP:8080 and access to it.

Important note: code-server uses a self-signed SSL certificate that may prompt your browser to ask you some additional questions before you proceed. For example, Chrome will alert you that your connection is not private. Then to proceed to the IDE, click "Advanced" and then click "proceed anyway".

Once in, you will be prompted to insert the password to enter the IDE. Type it and you are done! Now you have a fully featured VSCode running in your instance and accesible from anywhere!


Customize it #

Now you have the server launched with a self signed certificate and an autogenerated password, that will also not autostart on reboots...

But code-server has options to change that and made your server hosted IDE more stable and customized. You can run ./code-server --help in order to view all usage possibilities:

USAGE
$ server [WORKDIR]

ARGUMENTS
WORKDIR  [default: /root/code-server-1.1119-vsc1.33.1-linux-x64] Specify working dir

OPTIONS
-d, --data-dir=data-dir
-h, --host=host          [default: 0.0.0.0]
-o, --open               Open in browser on startup
-p, --port=port          [default: 8443] Port to bind on
-v, --version            show CLI version
--allow-http
--cert=cert
--cert-key=cert-key
--help                   show CLI help
--no-auth
--password=password

Data directory #

You can use the -d (or --data-dir) option to specify the root folder that VS Code will start in.
Example (excluding the parentheses):

./code-server --data-dir=(path/to/directory)

Host #

You can use the -h (or --host) option to specify the address you want to use (by default code-server will use 0.0.0.0 as its address).

Example:

./code-server -h 127.0.0.1

Cert and Cert Key #

In order to encrypt the traffic between the browser and server use ./code-server --cert= followed by the path to your .cer file. You can also use certificate keys with ./code-server --cert-key followed by the path to your .key file.

Example:

./code-server --cert /etc/letsencrypt/live/example.com/fullchain.cer --cert-key /etc/letsencrypt/live/example.com/fullchain.key

Here you can use your own generated certificate and key, or use services like LetsEncrypt, using the Certbot cli to generate certificates. You can find more information in this article.

Extra: How to generate your own self-signed certificate: #

It is recommended to use Self-signed TLS/SSL certificates for personal use of code-server or within an organization.

You can specify any location that you want to save the certificate and key. In this example, we will navigate to the root directory, create a folder called certs and cd into it:

mkdir ~/certs && cd ~/certs

You will need a TLS certificate and key. If you don't already have a TLS certificate and key, you can generate them with the command below. They will be placed in ~/certs:

openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout ~/certs/MyKey.key -out ~/certs/MyCertificate.crt

Running that command, you will be prompted to add some identifying information about your organization. Fill all the information until the command finishes.

Important note: If you already have a TLS certificate and key, you can simply reference them in the --cert and --cert-key flags when launching code-server

Now you can add the flags --cert and --cert-key with the generated certs and keys to the command to run your code-server:

./code-server --cert=~/certs/MyCertificate.crt --cert-key=~/certs/MyKey.key

**Note that you will know your connection is secure if the lines WARN No certificate specified. This could be insecure. WARN Documentation on securing your setup: https://coder.com/docs no longer appear.

Setup a domain #

You will also be interested in setting a custom domain for your instance and in order to issue the certificates. This could be easily achieved using tools to Setup Dynamic DNS and your custom domain (or free subdomains). For more info about this check this article.

Nginx as Reverse Proxy #

You can use Nginx for reverse proxy passing the option --allow-http option to the code-server command.

You can also use Certbot as explained above to get SSL certificates for free.

Here is a simple example of virtual host that works with code-server:

server {
    listen 80;
    listen [::]:80;
    server_name code.example.com code.example.org;
    location / {
        proxy_pass http://localhost:8443/;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection upgrade;
    }
}

More detailed instructions on how to configure Nginx as reverse proxy can be found in this article (example for Ghost app).

Autostart code-server on startup #

You can configure a simple service to execute the code-server (with your own options) in startup and make it more stable development environment.

Just follow this simple steps:

Move the binary to /usr/local/bin: #

sudo mv (path/to/downloaded/code-server) /usr/local/bin/code-server

Add a script to the runlevel defaults: #
sudo touch /etc/init.d/codeserver
sudo chmod 755 /etc/init.d/codeserver
sudo update-rc.d codeserver defaults
Completing the script (assumming code-server is in /usr/local/bin/code-server): #
####################################################### 
#! /bin/sh 
# . /etc/rc.d/init.d/functions  # uncomment/modify for your killproc 
case "$1" in 
start) 
echo "Starting code-server." 
/usr/local/bin/code-server 
;; 
stop) 
echo -n "Shutting down code-server." 
killproc -TERM /usr/local/bin/code-server 
;; 
*) 
echo "Usage: $0 {start|stop}" 
exit 1 
esac 
exit 0 
####################################################### 

Now, on restart, code-server will be running.

Securing your instance with ufw and fail2ban #

Security and privacy matters. You will be working with code and sure you don't want it to be exposed or deleted.

Then you can install two simple programs (one firewall and one simple "auto-ban") in order to harden your server.

For ufw simply install it with sudo apt install ufw and add rules to allow incoming traffic to the code-server port:

sudo ufw allow 8080
sudo ufw allow 20
sudo ufw enable

This will enable the firewall at startup, start it, allow traffic from 8080 and 20 ports (to ssh your instance) and block other ports. You can find more information in this article.

For fail2ban you only have to follow this doc.

Now your instance is secure enough to keep working.

How to upgrade code-server #

To upgrade code-server, keep an eye on new updates of code-server and just download the latest release from the releases page on Github. Extract the contents of the release, and move it to /usr/local/bin/code-server (replacing the existing binary).

Important note: ensure nobody is working and code-server is stopped before upgrading code-server.


Working with Docker #

You can also use code-server with Docker.
If you want to know how to install and run Docker in your instance check out this article.

Example one liner with Docker (caution: no auth!):

docker run -t -p 127.0.0.1:8443:8443 -v "${PWD}:/root/project" codercom/code-server code-server --allow-http --no-auth

Dockerfile can be found in Github.

Check out the image in Docker Hub.


Congratulations! That is all to get it running and having your own stable, secured and fully featured dev environment in the cloud.

If you have any doubt, you need support of found a bug, you can join their discord server.

🙏🙏🙏

Since you've made it this far, sharing this article on your favorite social media network would be highly appreciated 😀! For feedback, please ping me on Twitter.

Published