In my last post I discussed some of the attractive elements of the Clojure ecosystem. The primary Emberall app is still written in Rails and that’s still where most development happens, so I decided to take some time to enable the auto-refresh functionality built into Clojure’s Ring. Rails already gets us halfway there by automatically reloading updated files on the server, but by following these steps any open pages will also automatically refresh when code is updated in development.
Installing the Gems
Add the following two gems to your
Gemfile, then run
bundle binstub guard:
rack-livereload gem takes care of bundling livereload.js and injecting it into all HTML pages served in development. To configure it, add the following lines to your environment:
For the full list of configuration options see rack-livereload.
Restart Rails, and verify that
livereload.js is correctly included in your HTML pages. Note that at this point your page should be trying to open a websocket to port 35729 unsuccessfully; we’ll fix that in the next step.
Configure Guard to watch your
assets folder. I modified the default
guard-livereload template slightly to indicate that all of my SCSS files get included into
application.css, even in development. Other than that, this is the default Guard livereload configuration.
If you binstubbed Guard above you should now be able to run it simply with the
bin/guard command. If all goes well, as long as Guard is running making a change to a view or asset file will now automatically refresh the page with the new file!
- We use Vagrant virtual machines for development, and Guard doesn’t pick up on filesystem changes for shared folders or remote NFS mounts. I got around this by using Vagrant’s relatively new rsync folder-sharing strategy. This actually improves performance compared to NFS or a shared folder in Virtualbox, but does introduce a second or two of lag in synchronization.
- If you use HTTPS in development (for example, to check that HTTPS is forced for certain routes) LiveReload will fail in Chrome because it attempts to open an unencrypted
ws://websocket channel to the livereload server which is blocked for security reasons. From what I can tell guard-livereload doesn’t currently support TLS-secured websockets. If this is important to you, it should be possible to use stunnel as the websocket TLS termination and then pass the connection on to livereload.
Bonus – Livereload for Jekyll