Skip to content

Instantly share code, notes, and snippets.

@jtlocsei
Last active July 31, 2019 19:08
Show Gist options
  • Save jtlocsei/64956ba9e38d6643bafd818bb9829d67 to your computer and use it in GitHub Desktop.
Save jtlocsei/64956ba9e38d6643bafd818bb9829d67 to your computer and use it in GitHub Desktop.
Edit and run code on remote server as if it's local with Clojure

Mirror + Clojure remote REPL

Motivation & summary

In a nutshell

Use mirror + clojure remote repl to edit and run clojure files on a server as if they're local.

What does it add beyond clojure remote REPL alone?

Any files you create in your local project are synced to the server and vice-versa. If your program creates or reads files on the filesystem then this syncing makes it much easier to see what's going on.

Why not just develop on your local machine?

Developing on the server lets you test your code on the same environment it will be deployed in, including specific JVM version, machine CPU and RAM limitations, presence of specific binaries and non-java packages and resources (e.g. ImageMagick, fonts).

Why not use a docker container on your local machine?

Docker's great too. But for large images I don't want a lot of them taking up disk space on my local machine. Also sometimes it's quicker and easier to launch a new VM (e.g. on DigitalOcean or MirHosting than it is to make a new docker image on my machine.

What OS does it work with?

This works with MacOS or Linux on local machine, and Linux on the server.

Method

Syncing folders

  1. Install Mirror on both your local machine and the server. It enables real-time two-way sync between a folder on your local machine and a folder on the server.
  2. SSH into the server, with port forwarding of port 49172 (default port for mirror), e.g ssh -L 49172:localhost:49172 name@server.com
  3. On the server, run mirror server
  4. On the local machine, run mirror client -h localhost -l "/blah/local-folder" -r "/blah/remote-folder/". For example, if local-folder is a lein project and remote-folder is empty, then the lein project will get copied to the folder. Any further changes on either side will be synced in real-time.

Connecting to remote REPL

  1. On the server, in the directory of the project, run lein repl :start :port 7002 (or choose whatever port you want).
  2. On your local machine, run ssh -L 7002:localhost:7002 name@server.com
  3. Add remote repl in Cursive
    1. Open lein project in Cursive
    2. Click on the REPL dropdown near the top-right of the window
    3. Click Add/Edit configurations
    4. Click +
    5. Choose Clojure REPL / Remote, with host 127.0.0.1 and port 7002
  4. Try running a command in the repl like (spit "/blah/remote-folder/hello.txt" "hello world"). The file hello.txt will be created on the server, and then immediately synced to the local-folder.
  5. If you add dependencies to your project.clj, you'll need to restart the repl on the server (i.e. re-do step 1). The good thing is you won't need to copy your code across to the server because it will already be there thanks to mirror syncing the folders.
@johanatan
Copy link

Emacs’ TRAMP is another way to accomplish this.

@ahmed1hsn
Copy link

Mutagen is also an elegant tool for real-time two-way file sync:
https://github.com/mutagen-io/mutagen/blob/master/README.md

It have great documentation:
https://mutagen.io/documentation/introduction/

@jtlocsei
Copy link
Author

Emacs’ TRAMP is another way to accomplish this.

@johanatan that's neat, I didn't know about TRAMP (I'm not an emacs user).

@jtlocsei
Copy link
Author

@ahmed1hsn thanks for recommending Mutagen, I'll check it out. It looks like it might be more straightforward to use than Mirror because it doesn't require anything to be installed on the remote.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment