Use Vaadin with eXo Platform and Build Stunning Web Applications
Overview
According to Simpalm, a web app development firm, “Vaadin is a powerful Java Framework for easily building high quality web-based applications with great looking user interfaces (UI). Vaadin supports two different programming models: server-side and client-side. The server-driven programming model is the more powerful one. It allows you to develop web applications in much the same way as you develop Java desktop applications using Java toolkits such as AWT and Swing.”
You can easily create your UIs on server-side: Vaadin will help you to control the rendering of Javascript and handling of AJAX communication between server and client side.
Vaadin supports deploying the application as a standard portlet (JSR-286). In this tutorial, you will see how to make a Vaadin portlet work on our eXo Platform.
Create Vaadin portlet
First of all, let’s create a standard portlet using Vaadin framework. Vaadin supports creation of a portlet project using Vaadin Plug-in for Eclipse. The plug-in provides a wizard to automatically generate the necessary descriptors for portlets such as portlet.xml. The following steps show how to create a simple QuickNote portlet that allows users to quickly add and edit notes online (you can take Firefox’s add-on QuickFox as an example).
Select Vaadin 7 Project wizard.
Name this project as QuickNote and use the latest version of configuration. For deployment configuration, remember to choose “Generic portlet (Portlet 2.0)”. And you might want to try the latest version of Vaadin for this portlet project. Please take note of this version info as we will use it later when deploying the portlet into our platform.
Enter the application name, the main UI class name and portlet title. The Theme name identifies the custom theme to be generated in the project.
As you can see in the project stub, there are several descriptors especially defined for Liferay portal (liferay-xxx.xml and liferay-plugin-package.properties). For eXo portal these files are useless so you can remove them all. The portlet.xml alone is enough. The internal Servlet class is also obsolete in this case because we are developing the portlet.
Annotation @Theme indicates the theme to be used for the dedicated UI class. Vaadin provides several built-in themes such as reindeer, runo, chameleon, etc. If you don’t want to spend time defining your own custom theme; using one of these built-in themes is good enough for your UI.
Change the code of NoteUI as below:
package com.example.quicknote; import java.io.File; import java.io.IOException; import com.google.gwt.thirdparty.guava.common.io.Files; import com.vaadin.annotations.Theme; import com.vaadin.data.Property.ValueChangeEvent; import com.vaadin.data.Property.ValueChangeListener; import com.vaadin.data.util.FilesystemContainer; import com.vaadin.data.util.TextFileProperty; import com.vaadin.server.VaadinRequest; import com.vaadin.ui.Alignment; import com.vaadin.ui.Button; import com.vaadin.ui.Button.ClickEvent; import com.vaadin.ui.Button.ClickListener; import com.vaadin.ui.HorizontalLayout; import com.vaadin.ui.RichTextArea; import com.vaadin.ui.Table; import com.vaadin.ui.Table.ColumnHeaderMode; import com.vaadin.ui.TextField; import com.vaadin.ui.UI; import com.vaadin.ui.VerticalLayout; import com.vaadin.ui.VerticalSplitPanel; import com.vaadin.ui.Window; @SuppressWarnings("serial") @Theme("runo") public class NoteUI extends UI { public static File NOTES_DIR = Files.createTempDir(); // To use a persistent directory in exo data dir, use this: // public static File NOTES_DIR = new File("data/quicknote"); FilesystemContainer notes = new FilesystemContainer(NOTES_DIR); Table noteList = new Table("Notes", notes); RichTextArea noteView = new RichTextArea(); Button add = new Button("+"); String filename; Window subWindow = new Window("Enter note name:"); TextField txtname = new TextField(); Button ok = new Button("OK"); Button cancel = new Button("Cancel"); @Override protected void init(VaadinRequest request) { VerticalSplitPanel split = new VerticalSplitPanel(noteList, noteView); split.setHeight("300px"); noteView.setSizeFull(); noteList.setSizeFull(); tableRefresh(notes); noteList.addValueChangeListener(new ValueChangeListener() { public void valueChange(ValueChangeEvent event) { noteView.setPropertyDataSource(new TextFileProperty( (File) event.getProperty().getValue())); } }); // Dialog box to enter note name VerticalLayout subVert = new VerticalLayout(); subVert.setMargin(true); subVert.setSpacing(true); subVert.addComponents(txtname, new HorizontalLayout(ok, cancel)); subWindow.setContent(subVert); // Center it in the browser window subWindow.setResizable(false); subWindow.center(); // Buttons click listener ok.addClickListener(new ClickListener() { public void buttonClick(ClickEvent event) { filename = txtname.getValue(); if (!filename.equals("")) { File newNode = new File(NOTES_DIR, filename); try { newNode.createNewFile(); } catch (IOException e) { e.printStackTrace(); } tableRefresh(notes); noteList.select(newNode); } subWindow.close(); } }); cancel.addClickListener(new ClickListener() { public void buttonClick(ClickEvent event) { subWindow.close(); } }); add.addClickListener(new ClickListener() { public void buttonClick(ClickEvent event) { addWindow(subWindow); } }); // set main layout VerticalLayout vert = new VerticalLayout(split, add); vert.setWidth("285px"); vert.setComponentAlignment(add, Alignment.MIDDLE_CENTER); setContent(vert); } private void tableRefresh(FilesystemContainer data) { noteList.setContainerDataSource(data); noteList.setSelectable(true); noteList.setImmediate(true); noteList.setColumnHeaderMode(ColumnHeaderMode.HIDDEN); noteList.setVisibleColumns(FilesystemContainer.PROPERTY_NAME); } }
If you wish to store notes in a persistent directory in exo data dir, please use this:
public static File NOTES_DIR = new File("data/quicknote");
instead of:
public static File NOTES_DIR = Files.createTempDir();
and make sure you have <Platform Home>/data/quicknote directory already created to store notes.
To get the portlet deployment binary file, just export it to .war file.
Integrate Vaadin portlet into eXo Platform
Now we are going to install Vaadin libs, themes and widgetsets into our Platform so that our portlet can run properly. Below are steps to install the Vaadin package into Platform:
1. Get the Vaadin installation package from the Vaadin download page. On the right side you should see all available released packages. Make sure you select the same version as the one you have chosen when creating your portlet and then download the All-in-One distribution zip file.
2. Extract the following Vaadin JARs from the installation package: vaadin-server.jar and vaadin-shared.jar, as well as the vaadin-shared-deps.jar and jsoup.jar dependencies from the lib folder.
3. Rename the JAR files as they were listed above, without the version number.
4. Put the libraries in <Platform Home>/webapps/WEB-INF/lib/.
5. Extract the VAADIN folders from vaadin-server.jar, vaadin-themes.jar, and vaadin-client-compiled.jar and copy their contents to <Platform Home>/webapps/html/VAADIN.
$ cd <Platform Home>/webapps/html
$ unzip <path-to>/vaadin-server-<Vaadin version>.jar ‘VAADIN/*’
$ unzip <path-to>/vaadin-themes-<Vaadin version>.jar ‘VAADIN/*’
$ unzip <path-to>/vaadin-client-compiled-<Vaadin version>.jar ‘VAADIN/*’.
If a custom theme or widgetset will be used by more than one portlet, it must be copied into this VAADIN folder.
To deploy this portlet to eXo Platform, just simply copy the exported .war file into <Platform Home>/webapps. You should find the QuickNote portlet available in the Application Registry after deploying (If it is not there yet, just click Import Applications).
Open Page Editor of the page where you would like to add this portlet, then drag and drop the portlet in the right place.
Now it’s time to show up QuickNote portlet on eXo Platform.
Going further
This is just a Vaadin portlet setup tutorial and the objective is to show how Vaadin UI components are working on eXo Platform. For more advanced portlets you might want to integrate your portlet with the low level service layer of eXo or have a database connection. They are all possible. The next tutorial will show you how Vaadin portlets can interact with eXo APIs and services.
Resource
Project source code on Github
Join the discussion on the eXo Community to learn more about this integration.