Clojure Toolchain Reloaded

Clojure keeps growning up, and my 2.5-years old guide for setting up Clojure environment on Mac OS X had been out-of-date for quite a while. The toolchains based on Leiningen 2 and nREPL rise from underground, become really powerful and easy (even joyful for most of us) to use, and de facto standard. Nearly all main stream developing environments provide solutions for serious Clojure developers: Eclipse + Counter Clockwise, IntelliJ IDEA + La Clojure, Sublime Text 2 + SublimeREPL, Vim with fireplace.vim, etc.1, and the favorite I finally found several months ago, Emacs Live.

Emacs Live is brought to us by Sam Aaron, a major developer of Overtone, the Clojure-based open source live-programmable music exploration & collaboration toolkit2. From Emacs Live documentation:

Emacs Live is a carefully curated Emacs config which transforms vanilla Emacs from simply an incredible editor into an intense experience. The key is in the curation. Unlike other exemplary Emacs config tools such as the Starter Kit and Prelude which are very modular, Emacs Live embodies a holistic approach creating an all-round package. We build on the shoulders of giants and incorporate many independent projects, ensuring that they all work together seamlessly.

Emacs Live A curated Emacs experience

Emacs Live emphasizes the curation of the whole bundle, providing great experiences for out-of-box usage. Some of the best features it packs include:

  • Solid configuration for fundamental Emacs usage, especially Paredit3
  • Well picked and configured Clojure toolkit:
    • With Leiningen as the only dependency, without cluttered configuration files which normal IDEs usually introduce
    • Built-in nREPL.el for communicating with nREPL servers
    • Clojure Mode with fancy (λ a) and ƒ(+ % 5) prettifications
    • Auto completion support for both Clojure and nREPL buffer with inline documentation display (see it in action below)
    • Fancy highlighting of sexps on eval; rainbow parens and delimiters
  • Amazing powerful features like: undo-tree, Textmate-like snippets, quick jump and Ace Jump mode

My custom Emacs Live in working

Emacs Live also provides modular customization mechanism called packs. As you can see in the above screenshot, I don’t like the font and color theme bundled with Emacs Live so I use my favorite Pragmata Pro coding font and Solarized color theme. For people who like a really powerful yet beautiful and elegant developing environment for Clojure, I’ll describe below how I set up all on Mac OS X in half an hour, step by step.

Pre-requisites

OS: Mac OS X 10.6 or above
Java VM: Java SDK 6 or later

% uname -a
Darwin matrix.local 12.3.0 Darwin Kernel Version 12.3.0: Sun Jan 6 22:37:10 PST 2013; root:xnu-2050.22.13~1/RELEASE_X86_64 x86_64
% java -version
java version "1.6.0_43"
Java(TM) SE Runtime Environment (build 1.6.0_43-b01-447-11M4203)
Java HotSpot(TM) 64-Bit Server VM (build 20.14-b01-447, mixed mode)

Emacs

Emacs Live needs vanilla Emacs 24 or above. Which you can get in one of these methods:

  • Download pre-built universal binary from emacsformacosx.com, mount the image and copy Emacs.app to /Applications.
  • Use Homebrew, the best package manager for OS X. It’s as simple as brew install emacs --cocoa.
  • Download source from GNU Emacs site and build it:
bzr branch http://bzr.savannah.gnu.org/r/emacs/trunk
cd trunk
./autogen.sh
./configure --with-ns
make bootstrap && make install
mv nextstep/Emacs.app /Applications

Leiningen

Leiningen is for automating Clojure projects without setting your hair on fire.

Emacs Live depends on Leiningen 2. The best way to get Leiningen on board is, again, to use Homebrew brew install leiningen.

Of course the official method should work fine too:

  1. Download the script.
  2. Place it on your $PATH e.g. ~/bin or /usr/local/bin
  3. Set it to be executable e.g. chmod 755 ~/bin/lein or chmod 755 /usr/local/bin/lein

Either way you can verify it by issuing4:

% lein -v
Leiningen 2.1.2 on Java 1.6.0_43 Java HotSpot(TM) 64-Bit Server VM

Cleanup

If you are already Emacs user, which means that most likely you already have an .emacs config file and lots of stuff in .emacs.d folder under your home ~/. In this case before going any further you have to backup all of them for later use.

mkdir -p ~/Desktop/Emacs.backup
mv ~/.emacs ~/.emacs.d ~/Desktop/Emacs.backup

Emacs Live

There are several methods to install Emacs Live. But here is my favorite:

cd ~/
git clone git://github.com/overtone/emacs-live.git ~/.emacs.d

That’s it. Now you can try it by simply launching Emacs.app from your /Applications folder. You’d better not touch the ~/.emacs.d folder from now on, so you can update Emacs Live anytime you want by issuing git pull in this folder.

All following steps are for more customization, and optional.

Emacs Live Customization

Create Custom User Pack

mkdir ~/.live-packs
cp -R ~/.emacs.d/packs/template/user-template-pack ~/.live-packs/yourname-pack

The folder name yourname-pack can be anything you’d like. Mine is neo-pack and you can have it as reference on GitHub.

User Pack Structure

  • config: Folder for Emacs config files. Typically a bindings.el for keybindings (which is already there), and a yourname-conf.el for your custom setting (which is not exist by default). I created a config/neo-conf.el and imported most of my settings from the old ~/.emacs file, which you can find here.
  • lib: Folder for Emacs mods. Put stuffs from old .emacs.d folder into it and load them like this (in init.el or any scripts under config folder):
(live-add-pack-lib "some-great-mod") ; some-great-mod is sub-folder under lib folder
(require 'great-mod-init) ; great-mod-init.el is script under sub-folder some-great-mod
(great-mod) ; great-mod is some function in great-mod-init.el
  • init.el: Entry script of the pack. Mostly something like:
init.el
;; Load bindings config
(live-load-config-file "bindings.el")
;; Custom settings
(live-load-config-file "yourname-conf.el")
  • info.el: Meta data of the user pack.
  • README.md: Helpful info for user pack customization.

Import 3rd Party Pack

The built-in cyberpunk color theme bundled with Emacs Live is amazing, but I love the epic Solarized color theme all the time. Fortunately an Emacs Live user has made a reusable pack for it5. Simply import it from GitHub:

cd ~/.live-packs
git clone git://github.com/siancu/solarized-pack.git
cd solarized-pack
git submodule init
git submodule update

Tell Emacs to Load User Packs

Emacs Live uses ~/.emacs-live.el to load user packs. So we need to create a ~/.emacs-live.el file and put these lines in it:

.emacs-live.el
(live-use-packs '(live/foundation-pack ; Use live-use-packs to control which built-in packs should be loaded
; live/colour-pack ; This built-in pack MUST be disabled if you want to use 3rd party color theme pack
live/clojure-pack
live/lang-pack
live/power-pack))
(live-add-packs '(~/.live-packs/neo-pack ; Use live-add-packs to load custom packs
~/.live-packs/solarized-pack))

Final Tweaks

Emacs Launching Time

Emacs Live is extremely powerful and thus cause rather long Emacs starting time as trade-off. Fortunately Emacs has standard solution for this problem: the Emacs daemon and emacsclient. Just add these aliases in your shell startup script (e.g. my ~/.zshrc):

alias es='/Applications/Emacs.app/Contents/MacOS/Emacs --daemon'
alias emacs='/Applications/Emacs.app/Contents/MacOS/bin/emacsclient -c -n'

Then you can firstly launch the Emacs server daemon by issuing es in shell (only once), after which you can instantly open Emacs editor by emacs <filename>.

Connecting to nREPL

Emacs Live provides nREPL integration through nrepl.el. To use that you can choose one of two ways.

Jacking In

The simplest way to get Emacs Live connected with a Clojure process is to use M-x nrepl-jack-in command. This allows you to connect to a specific Leiningen project which therefore ensures that all the project dependencies defined in the project’s project.clj are available on the JVM classpath.

In order to communicate with the correct project, you should summon M-x nrepl-jack-in whilst the active buffer displaying file which is part of the Leiningen project you wish to connect to. This will then spawn lein repl :headless as an external shell process and automatically connect to it.

Manually Connection

Another option for connecting to an nREPL process is to manually start a Leiningen REPL by cding to the project folder and issuing the command lein repl. This will start a REPL on the terminal, but also tell you which port nREPL is listening on i.e.:

nREPL server started on port 62132

Then use M-x nrepl command in Emacs and feed it with 127.0.0.1 (default) host and right port, which should have been printed in the shell output of lein repl command. In the case shown above the right port is 62132. Soon you will get annoyed by looking for this random port number and paste it to Emacs M-x nrepl prompt. Fortunately we can ask the nREPL server to listen to the default 4555 port by adding a custom lein command in ~/.lein/profiles.clj:

profiles.clj
{:live-repl {:repl-options {:port 4555}}
:user {:aliases {"live" ["with-profile" "default,live-repl" "repl"]}
:dependencies [...]}
}

Now you can issue lein live command under the project folder, which will start a normal nREPL session, but this time it will always be listening on port 4555. Connecting from Emacs is now just a matter of M-x nrepl RET RET.

FAQ

Emacs Live is being very actively developed and with relatively little documentation. Here are some tricks I used in my pack, which may be updated from time to time.

Q: Why is my custom color theme overrided by Emacs Live built-in theme?
A: You have to disable the built-in live/colour-pack to use custom color theme, as shown in the Tell Emacs to Load User Packs section above.

Q: How to use my favorite font instead of the default one?
A: Modify default-frame-alist in conf/yourname-conf.el under your user pack (~/.live-packs/yourname-pack):

(add-to-list 'default-frame-alist '(font . "PragmataPro 14"))

Q: How to customize my cursor color?
A: Modify default-frame-alist in conf/yourname-conf.el under your user pack:

(add-to-list 'default-frame-alist '(cursor-color . "palegoldenrod"))

Q: I want the highlight current line feature back!
A: After disabling the built-in live/colour-pack (see the first question above) you will lose the highlight current line feature as a side effect (since it’s defined in that pack). But it’s very easy to add it back, by adding the following line to conf/yourname-conf.el under your user pack:

(global-hl-line-mode 1)

  1. See the Getting Started guide in the official dev wiki for more. But note that many info in it are deprecated (e.g. Netbeans and Enclojure, Swank Clojure for Emacs, VimClojure, etc.).

  2. Overtone is extremely amazing and I highly suggest to have a try. Or you can see the video (Emacs Live in action!) to get some idea.

  3. IMHO, Paredit is one of the key reasons which makes Emacs the best editor for all LISP dialects. See this perfect guide if not familiar with paredit.el.

  4. If choosing the official method while running lein -v the first time it will download all dependencies for Leiningen, and then print out the version info.

  5. Studying this simple user pack example can make building your own pack, especially color-theme pack as easily as Copy and Paste.

Neo Lee's Picture

About Neo Lee

An Internet architect, product designer, entrepreneur, lifetime game and music lover.

Shanghai, China http://soulhacker.me