Getting started with ClojureScript and Noir #1

12 Feb 2012

Being a backend developer by trade, the prospect of working in a frontend environment has always been a daunting and confusing experience, especially if you’re not too well versed in Javascript. While it may not be the best language in the world, it’s most certainly the language that the browser developers have chosen as the standard for client side processing.

Luckily some clever folk out there have recognised the fact that Javascript can be a foundation for other languages to compile down to, whether it be CoffeeScript, Google Web Toolkit or the language I’m interested in ClojureScript, there are plenty of options out there.

The problem is, getting started in ClojureScript is pretty difficult, which is understandable considering how alpha the compiler is, but I think I’m finally getting somewhere by utilising the libraries written by Chris Granger. While I understand that excellent projects like ClojureScript One are certainly a boost to the community, creating your own project from scratch still is quite hard.

I figured my findings might also be useful to those starting out too


You’ll need the following Leingingen plugins installed

lein plugin install lein-noir 1.2.1

Then set up your new project

lein noir new testproject
cd testproject

This will generate a skeleton noir project with the relevent items in their rightful places. If you are not familiar with noir, please read this excellent tutorial on the library which is more than adequate for getting up to scratch.

Incorporating ClojureScript into your Noir project

Firstly you will need to modify your project.clj to set up your project and the environment that ClojureScript will work within

(defproject testproject "0.1.0-SNAPSHOT"
		:description "FIXME: write this!"
		:dependencies [[org.clojure/clojure "1.3.0"]
					   [noir "1.2.1"]]
		:dev-dependencies [[lein-cljsbuild "0.0.13"]] ; cljsbuild plugin
		 :source-path "src-cljs"
		  :output-to "resources/public/js/cljs.js"
		  :optimizations :simple
		  :pretty-print true
		:main testproject.server)

Then run

lein deps

This will install all the dependencies we will be using, including the cljsbuild plugin that will compile your ClojureScript code down to Javascript (into the file resources/public/js/cljs.js defined in your project.clj above)

Then we need to setup an area of our codebase to store our ClojureScript code, as defined in our project.clj above

mkdir -p src-cljs/testproject

Finally, open a new terminal and navigate to your project directory, then run the cljsbuild plugin

cd testproject
lein cljsbuild auto

This will compile your ClojureScript code as you work.

Modifying your project

To get the browser to load your compiled ClojureScript you will need to include the generated JS file compiled by cljsbuild - the location of which is defined in your project.clj file.

Noir gives you a ‘common’ view located under src/testproject/views/common.clj as default that can be used to wrap other views accordingly. I recommend adding your JS definition here, as per below

(ns testproject.views.common
  (:use [noir.core :only [defpartial]]
	[ :only [include-css include-js html5]]))
  (defpartial layout [& content]
		[:title "testproject"]
		  (include-css "/css/reset.css")]
			  (include-js "/js/cljs.js")))

Open another terminal and run your server by running lein run, which can be viewed at http://localhost:8080

Writing your ClojureScript code

Create the file src-cljs/testproject/test.cljs and insert the following code

(ns testproject.test)
(js/alert "Hello world!") 

Now load the page http://localhost:8080/welcome, you should see an alert box! If so congratulations, you’re now all ClojureScripted up

Big deal, I could have done all that with one <script> tag!

Yep, but now you can write your client side code in Clojure! Unification of the client-side and server-side under one language (somehwat…)

In the next blog post I will build on the foundation described in this blogpost to produce a very simple ClojureScript/Clojure application.

Update - 14/02/2012: The source code for the instructions above can be found in this repository

Please contact me if you find any issues with this post.