Using Vaadin 7 with Clojure

Feb 12, 2013   #java  #clojure  #vaadin 

There are some good examples on how to compose a web application with Clojure and Vaadin < 7. However, the web application bootstrapping process has changed for Vaadin 7. In this post I will show you how to create a Clojure/Vaadin 7 web application.

First we need a web.xml file in src/main/webapp/WEB-INF that defines the Vaadin servlet and parametrizes it with our main UI class.

Clojure Vaadin 7 Application Vaadin production mode productionMode false Clojure Vaadin 7 Application com.vaadin.server.VaadinServlet Vaadin UI UI cljvaadin7.MyApplicationUI Clojure Vaadin 7 Application /*

As there is no such thing as a class in Clojure, we will use its Java interoperability to create a Java class that serves as our Vaadin UI main class.

(ns cljvaadin7.MyApplicationUI (import [com.vaadin.ui VerticalLayout Label Button Button$ClickListener Notification]) (:gen-class :extends com.vaadin.ui.UI))

:gen-class will make the namespace available as a Java class.

We override the init method of com.vaadin.ui.UI. This is the entry point for our web application. init in com.vaadin.ui.UI has only one argument (request). However, our Clojure -init function has two arguments. The reason is that the function will receive “this” as the first argument. Now we can build our UI.

(defn- create-button [caption action] (doto (Button. caption) (add-action action))) (defn- create-main-layout [] (doto (VerticalLayout.) (.addComponent (Label. "Hello Clojure-Vaadin 7!")) (.addComponent (create-button "Push me!" show-click-message)))) (defn -init [main-ui request] (doto main-ui (.setContent (create-main-layout))))

In Java, button actions are triggered by registering a click handler for the button. We have to do this in Clojure as well but we will hide the actual ClickListener and use a more functional approach. We create a new function add-action that expects a button and an action as arguments. action can be any Clojure function we want to be executed when the button is clicked. The helper function create-button-click-listener wraps a Vaadin ClickListener around the action function.

(defn- show-click-message [] (Notification/show "Button clicked")) (defn- create-button-click-listener [action] (reify Button$ClickListener (buttonClick [_ evt] (action)))) (defn- add-action [button action] (.addListener button (create-button-click-listener action)))

The project file for building with Leiningen (and packaging with Maven) looks like this:

(defproject cljvaadin7 "0.1.0-SNAPSHOT" :description "Demonstrates how to integrate Clojure and Vaadin 7" :url "" :license {:name "Eclipse Public License" :url ""} :dependencies [[org.clojure/clojure "1.4.0"] [com.vaadin/vaadin-server "7.0.0"] [com.vaadin/vaadin-client-compiled "7.0.0"] [com.vaadin/vaadin-themes "7.0.0"] [javax.servlet/servlet-api "2.5"]] :aot [cljvaadin7.MyApplicationUI])

You can find the complete project on GitHub.