Delivering responsive web design in IBM Notes applications

Posted by:


Responsive web design (RWD) has been the talk of town the last years. In 2012 it was listed as #2 in ‘Top Web Design Trends’ by .net magazine and Mashable called 2013 the ‘Year of Responsive Web Design’. Many other sources have recommended responsive design as a cost-effective alternative to mobile applications.


While I assume that a large portion of the internet (and in some cases intranet) sites are nowadays optimized for the device that accesses them, but what about your company’s (internal) business applications? 

Business value

IT departments need to prioritize their activities and internal applications are most often accessed by a smaller audience than external applications. Historically the internal app was accessed with a desktop computer. With the trend of smartphones and tablets taking over the workspace this may no longer be the case in your company? 

With a VPN connection users want to continue to execute their work on this new breed of devices, instead starting up a desktop computer for a single task. Here is where the business value of RWD comes in.

Continue to work on same device = More productive employees = Saving time and perhaps even hardware

Mobile first

A trend is to apply the progressive application strategy of ‘Mobile first’. Instead of designing a complex application for desktop computers first and thereafter gracefully degrade it for mobile devices, the user interface is initially designed for mobile devices and enhanced for desktops with more processing power.


Many RWD frameworks embrace this ‘Mobile first’ concept nowadays.

Options in Notes

So what are your options in delivering RWD in your beloved Notes applications? Depending on your roadmap for the platform and personal preferences you have the following options.

  1. Build the application with XPages technologies.
  2. Build the application with common web technologies.

The XPages way

An approach for your Notes platform that is highly promoted by IBM is to deliver web interfaces for Notes applications with XPages. Not only bring you in Rapid Application Development (RAD) principles in your project also the range of capabilities is much more diverse.

Another benefit is that you can stay on the core technologies: JSF, JavaScript and Java. This you can combine with common web technologies like AJAX, HTML5, CSS and REST services. For the RWD you can use your favorite framework such as Bootstrap or Foundation.

Bootstrap framework


Bootstrap is a popular framework for developing responsive, mobile first projects on the web. It makes front-end web development faster and easier. Bootstrap is based upon HTML, CSS and JavaScript, technologies already well-known in Notes web apps.


You have several options how you distribute the Bootstrap framework to your audience:

  1. Install the files on your Domino server.
  2. Embed the files in a Notes application.
  3. Install an additional XSP library on your Domino server.
  4. Install the latest extension library on your Domino server.

In case you do not utilize the OSGi runtime on your Domino server you can either install the files on centrally on the Domino server or embed the files in each Notes application. The installation on the Domino server makes the distribution of updates easier but the administrator is responsible for the distribution across servers. Embedding the files in a Notes application is less efficient (e.g. caching) but makes distribution of updates a task for the developer.

Probably the best approach would be to utilize the OSGi runtime on your Domino server and distribute the files as a library via an Update site Notes application across your servers. This makes the task even simple and small for an administrator.

If you choose to do so you have the option to either install bootstrap4xpages library as a separate library or you can install the latest extension library (from 10 november 2014). The latter give you several benefits:

  • Custom renderer for the Application Layout control, which makes it easy to define the layout structure of your application.



    • This renderer gives the control a Bootstrap look & feel, as well making the control responsive.
  • A newer version of jQuery.
  • Latest Bootstrap themes (3.2.0 normal or flat).
  • Additional configuration options in the Application Layout control wizard for the Bootstrap navigation components.

Separate Mobile devices UI alternative

The extension library (a library with additional XPages controls and functions) provides also so-called ‘Mobile controls’ which allow you to deliver a separate interface for mobile devices for your Notes apps. Via a wizard you can build a ‘single page application’ in a matter of minutes with full CRUD (create, read, update and delete) operations and infinite scrolling through document lists (aka views).

This approach does not deliver RWD but a separate user interface for mobile devices. At least it gives you the option to deliver a UI adapted for mobile devices in a very short time with little investment.

You can choose to make the UI of the app look like a native app for iPhone or Android. Alternatively you can choose to make the UI look in line with other IBM products (iNotes, Connections). A video that demonstrates the controls briefly you can find here:

The WEB way

In case you do not walk the XPages path but instead you prefer the approach to deliver the application with more common web technologies like HTML, CSS, AJAX and REST services you can still install the files of your responsive web design framework of choice on the Domino server or embed them in a Notes application.

From there you can start to (re)write your ‘traditional’ Domino application as a Web project. In the latter case you use Notes only as a container for your data documents and design elements and use forms and views only as data schemes.

This approach dodges the RAD capabilities in Notes and will demand more development time. But you can apply this approach also to other platforms that you may have. You can later even debate why the data should be stored in Notes and not in a document-oriented database alternative? The layered security and replication capabilities are often good arguments. 

Implementing RWD via the Extension Library option

In the following scenario we will describe the implementation of RWD with the Extension Library more in details.

  • Database enablement.
  • Application Layout.

Database enablement

Assuming you have installed the extensions for the Domino server and Domino Designer (DDE) client according the instructions in the readme.pdf file you can now enable a Notes application.

XSP properties

The XSP properties file allows you to configure parameters for the XPages framework. Open the file in DDE.


In the General tab you have now two more themes to select:

  • Bootstrap 3.2.0
  • Bootstrap 3.2.0 flat

The ‘flat’ theme delivers:

  • The resources and styling that comes with Bootstrap v3.2.0.
  • jQuery v2.1.1 resources.
  • Cleanup of specific XPages controls when using Bootstrap.
  • Glyphicon halflings.
  • dbootstrap resources, which provide Bootstrap styling for Dojo controls.

The ‘ordinary’ theme provides all of the same resources as the flat theme, and includes 3D effects to buttons and some other additional styling.

Select one of the two themes:


Application layout

The RWD plugin adds a new renderer for the Application Layout control which you normally use to structure the layout of your application. This renderer gives your application layout the Bootstrap look and feel, as well as responsive behavior. When the application is rendered on a smaller screen, such as on a mobile device, it will automatically re-organize the application contents for an optimal user experience.

The control also has new configuration options. Add the Application control on a custom control and open the All Properties tab. In the basics section you can choose now the xe:bootstrapResponsiveConfiguration option:


Note: in case you have already a configured Application Layout control you can change the configuration option directly in the Source panel to keep the rest of your configuration (e.g. xe:applicationConfiguration -> xe:bootstrapResponsiveConfiguration).

This configuration options give you several more properties:

  • collapseLeftColumn
  • collapseLeftMenuLabel
  • collapaseLeftTarget
  • fixedNavbar
  • invertedNavbar
  • pageWidth

With the first 3 properties you define how the left column should behave on smaller devices (collapsed for smaller devices, display text when collapsed, item the left menu should be attached to).

You can determine the behavior of the navbar (inverted, fixed (top or bottom)) and the width of the page e.g. fluid = use Bootstrap 'fluid' container (almost full width).


When you initially drag on the Application Layout control on the custom control a two-step wizard is presented. In the first step you select one of available configurations. You can filter on responsive and non-responsive.


In the second you set the properties for the chosen configuration. In case you choose the Responsive Bootstrap option you will see the following screen:


Under configuration you can set the properties for the layout including the 6 additional properties mentioned earlier. Set also the other properties like you would normally do.

Voila! Your application is now ready for development.

Hiding elements for specific devices

The plugin provides only the resources and structure for responsive web design. In case you want to optimize the layout for devices by explicitly show or hide them you can use CSS classes.

Bootstrap provides some handful helper classes, for faster mobile-friendly development. These can be used for showing and hiding content by device via media query combined with large, small, and medium devices.




Extra small (less than 768px) visible


Small (up to 768 px) visible


Medium (768 px to 991 px) visible


Larger (992 px and above) visible


Extra small (less than 768px) hidden


Small (up to 768 px) hidden


Medium (768 px to 991 px) hidden


Larger (992 px and above) hidden

Note that the elements that you hide are still being loaded, but simply not being displayed.

Data View control

Probably a typical use case is the display of table columns or lists. On a desktop you may want to show more columns than on a smaller devices.

Typical you use the Data View control from the extension library to display lists of documents. The information you want to display as a link is defined in the summaryColumn property.


Additional columns that are displayed on the right of the summaryColumn will be displayed via the extraColumns property. Each additional column is defined in a viewExtraColumn item which contains properties for styleClass and headerStyleClass. For example you could set these as followed:


<xe:viewExtraColumn columnName="Date" columnTitle="Date" style="width: 100px"  styleClass=" hidden-xs hidden-sm " headerStyleClass=" hidden-xs hidden-sm"></xe:viewExtraColumn>


This will show the extra column only for medium and larger devices since they will be hidden for (extra) small devices.


Wrap up

Delivering responsive web design on your Notes applications has never been as easy as it is nowadays with the RWD plugin in the extension library. It also respects the rapid application (web) development mantra of XPages.

In case you do decide to follow this path remember you need to check what information you want to show or hide for specific devices.

So what is keeping you from getting a bigger bang for the buck by delivering optimized user experiences for mobile, tablet and desktops for your Notes applications?



Developing social applications with the Social Business Toolkit SDK

Posted by:


The Social Business Toolkit SDK (SBT SDK) is a set of libraries and code samples that you use for connecting to the IBM Social Platform. As a developer you can choose which web development skills fits you best: Java, (client side) JavaScript or XPages. Your social platform may reside in the cloud or on premise.

In this post I will give you guidelines and practical examples to get you started. I choose XPages as development environment.


In the document terms are thoroughly used:




Social Business Toolkit


Software Development Kit


Domino Designer on Eclipse


XPages is a rapid web and mobile application development technology


Open Source Community for (IBM) Collaboration Solutions


Open standard for authorization

Managed Bean

Java Beans representing system objects and resources


Encapsulates the access to a service provider, like Connections or Sametime

Installation of the SDK


Before you can start with development in Domino Designer on Eclipse you need to install the SBT SDK. It can be downloaded from the following address: files you need to work with the SBT SDK and Domino are located in folder ‘redist\domino’ in the downloaded ZIP file.

Extension Library

Another condition to be able to run the Social SDK within your XPages you need to have installed the Extension Library, available on OpenNTF: You need to have the library installed on both Domino server and DDE.

Installation for Domino Server

You can find a set of instructions how to install the SBT SDK on an IBM Domino server on the address: I recommend the installation via an Eclipse Update site. As a result your Update site should display the following plugins:


Installation for DDE

The Domino Designer deployment of the IBM Social SDK can use the same imported update site from the Update Site NSF. On Domino Designer verify that the checkbox for "Enable Eclipse plugin install" is checked in the Domino Designer preferences. You can find a set of instructions how to install the SBT SDK on DDE on the same address:

Setting up a Notes application

Create a new Notes application from scratch. I called mine ‘bornsocial.nsf’. Open the Xsp Properties file in DDE. Include the following libraries:




The Social Business Toolkit leverages a credential store for single sign on. For OAuth for example the user tokens are stored in this repository so that users don’t have to authenticate and grant access to services like IBM Connections for every session. The OAuth application tokens are also stored in this repository so that all tokens can be managed in one central place. You can read more on the credential store here: And it is also explained in the following video:

In basic: the implementation of the credential store is performed by the use of a managed bean. The usage of this credential store is then defined in an endpoint. An endpoint encapsulates the access to a service provider, like Connections or SameTime.

In the Package Explorer open the faces-config.xml file:


Add the following lines:

<!– Token Store memory implementation –>

<!– Password Store memory implementation –>


In the first example(s) we are only going to demonstrate to connect to IBM Connections. Add the following lines:


For value of managed property ‘url’ you must enter the address of your connections installation or in case you are using IBM Greenhouse for demonstration purposes you can choose '’.

Login page

A custom login page will presented when a user initially tries to connect to IBM Connections:


The elements for the login page are in the XPagesSBT.nsf application which comes with the SBT SDK. The nsf is located in folder redist\domino. The login page consists of the following design elements:






Custom Control


Custom Control

You can simply copy the design elements from the sample application in your application and modify them e.g. for branding.

Connecting to Connections

Your application is now ready to connect to Connections. Where you place the code to connect to Connections is up to you. A recommended approach could be to establish connections via Managed Beans.A managed bean is nothing more fancy than a registered a JAVA object.

Managed Bean

In our first example we are going to read the content under My Files in Connections. These are the files that you have uploaded and shared.

  1. Create a new Java design element (Java Class).
  2. Enter the following code:

package com.quintessens.bornsocial.sbt;

public class ServiceBean implements Serializable{
private static final long serialVersionUID = 1L; 

    public FileList getMyFiles() {   
                FileService service = new FileService();   
                try {      
                    return service.getMyFiles();   
                } catch (FileServiceException e){
                return null;

Code explanation

The function getMyFiles gets handle to the FileService object. Then the getMyFiles function is called to get all the files (both private and shared) the user has uploaded in Connections. Then a FileList object is returned to the caller. 

The FileList object can then be used in a suitable XPage control e.g. the DataTable or the DataView control. 


In order to access the Managed Bean you have to register it. This is done in the faces-config.xml file. Open the file and add the following lines:


You will access the bean via its name ServiceBean.


Finally we have come to a point where we can display the files that the managed bean returns from IBM Connections. I have choosen the XPages environment to do so.

Custom Controls

A best practice in XPages development is to divide functionality in individual blocks known as Custom Controls. This make it easier to re-use the functionality across your application.

Custom Control for a ‘My Files’ overview

  • Create a new Custom Control design element.
  • Add the following code to the control:

<xe:widgetContainer id="widgetContainer1" itleBarText="#{javascript:return compositeData.widgetTitle;}">
        <xe:dataView id="dataView1" var="file" rows="5" columnTitles="true" styleClass="filesDataView">
                <xe:viewExtraColumn columnTitle="Filetype"></xe:viewExtraColumn>
                <xe:viewExtraColumn columnTitle="Created"></xe:viewExtraColumn>
                <xe:viewExtraColumn columnTitle="Size"></xe:viewExtraColumn>

                <xe:viewSummaryColumn columnTitle="Filename"></xe:viewSummaryColumn>
                <xp:panel xp:key="noRows" id="topicsPanel2">
                    <xp:div styleClass="lotusWidgetBody">
                                <![CDATA[#{javascript:return (viewScope.myFilesAvailable ? “No files found.” : “My Files unavailable.”);}]]>
                <xp:panel id="summaryPanel" xp:key="summary" style="width:50%;white-space:nowrap;">
                    <h4><xp:link styleClass="dataViewLink" escape="true" id="link7" target="_blank" text="#{javascript:return file.getTitle();}">
    <xp:this.value><![CDATA[#{javascript:return file.getContentUrl();}]]></xp:this.value>
                <xp:panel id="typePanel" xp:key="extra0" style="width: 20%;white-space:nowrap;">
                            <![CDATA[#{javascript:return file.getType();}]]>
                <xp:panel id="sizePanel" xp:key="extra2" style="width: 15%;white-space:nowrap;">
                            <![CDATA[#{javascript:var size = file.getSize();
var kilobyte = 1024;
var megabyte = kilobyte *1024;
if(size < kilobyte) {
    return (size + " B");
}else if(size < megabyte) {
    return (Math.round(size/kilobyte) + " KB");
}else {
    return (Math.round(size/megabyte) + " MB");
                <xp:panel id="panel1" xp:key="extra1" style="width: 15%;white-space:nowrap;">
                    <xp:text escape="true" id="computedField3" value="#{javascript:file.getCreated()}"></xp:text>

As a result the files in IBM Connections for the authenticated user will be listed e.g.: 


Code explanation

The DataView control is using the getMyFiles function from Managed Bean ServiceBean for data binding:



<xe:dataView id="dataView1" var="file" rows="5" columnTitles="true" styleClass="filesDataView">            

It iterates through the returned FileList object and for each column values from each entry in the ‘file’ collection the value is computed e.g.:

<xp:panel id="summaryPanel" xp:key="summary" style="width:50%;white-space:nowrap;">
                    <h4><xp:link styleClass="dataViewLink" escape="true" id="link7" target="_blank" text="#{javascript:return file.getTitle();}">
                        <xp:this.value><![CDATA[#{javascript:return file.getContentUrl();}]]></xp:this.value>

API Explorer

Use the SBT API Explorer which method each object provides:




As you have seen getting started with the Social Business Toolkit is not that difficult for XPages developers. As alternative you could also choose JavaScript or JAVA if those skills fit you better. The SDK will help you understanding Connections piece by piece from a developer perspective.

In the example information is read from Connections but you can also post data. The SDK allows you to create great 'social enabled' applications. This can be applications that solely work with Connections or integrate with other platforms e.g. IBM Notes. 

I hope to write more on the Social Business Toolkit in another post. Thank you for reading.

Patrick Kwinten







Phonegap / Cordova 3.6.3 & CDVPlugin class CDVNotification (pluginName: Notification) does not exist

Posted by:

Eager to get your hands on the new and shiny huh?

Well, if you're using the plugin: org.apache.cordova.dialogs and upgraded your project to Phonegap / Cordova 3.6.3 you're in for a world of hurt.

This plugin is what provides native notifications like alert, confirm, prompt and beep. This will, after upgrading, cease to work and you should get a confusing error message in XCode like below:

(The text from row 3 and below will vary, depending on your implementation of the plugin)

2014-09-23 08:27:40.512 Rooms[7288:414440] CDVPlugin class CDVNotification (pluginName: Notification) does not exist.
2014-09-23 08:27:40.512 Rooms[7288:414440] ERROR: Plugin 'Notification' not found, or is not a CDVPlugin. Check your plugin mapping in config.xml.
2014-09-23 08:27:40.512 Rooms[7288:414440] -[CDVCommandQueue executePending] [Line 158] FAILED pluginJSON = [
    "You have to perform the setup, before you can use the application.",
    "Perform Setup",
    "Don't worry, it's easy"

This is how to solve it:

You need to add the plugin, manually, to the build phase of the project and you need to add a framework. Sounds complicated? It really isn't. Just have a look at the image below, follow the steps and…. BOOM! You're of to stardom once again!



JSR286 portlet unit testing with Jetty, Pluto and JWebUnit

Posted by:


Unit testing using JUnit has been around for quite some time, and even though I have used in early JUnit versions, it got really going when I also started to use maven. It was quite easy to create unit tests for any of my classes. Since I worked a lot with portlets I wanted to do expand my unit tests to include portlets.


The JSR286 portlet standard has been around for a while and it surprised me that I couldn't find any unit tests for JSR286 portlets, only JSR168 portlets. The most helpful blog I found was this one Testing Portlets with Jetty, Pluto and JWebUnit but again it applies to JSR168 portlets. Starting from there I tried to do the same thing with JSR286 portlets, but the pluto version used wasn't designed to work with JSR286 portlet. However, it gave me a starting point to recreate the setup for JSR286 portlet unit testing.



I will be using only a minimalistic portlet to demonstrate the setup. My starting point is a minimalistic portlet set up with maven. I demonstrated how to set that up in my last blog entry. From there I enhanced it a bit to allow for more testing. Here is the portlet class, the portlet.xml and the jsp I am using.

package com.mycompany.myportlet;


import javax.portlet.GenericPortlet;
import javax.portlet.PortletException;
import javax.portlet.PortletRequestDispatcher;
import javax.portlet.RenderRequest;
import javax.portlet.RenderResponse;

public class MyPortlet extends GenericPortlet {

	public void doView(RenderRequest request, RenderResponse response)
			throws PortletException, IOException {
		PortletRequestDispatcher rd = getPortletContext().getRequestDispatcher(
		rd.include(request, response);

<?xml version="1.0" encoding="UTF-8"?>
<portlet-app xmlns="" version="2.0" xmlns:xsi="" xsi:schemaLocation="" id="MyPortlet">
		<display-name xml:lang="en">MyPortlet</display-name>

<%@page session="false" contentType="text/html" pageEncoding="ISO-8859-1" %>
<%@ taglib uri="" prefix="portlet"%>                

<div id="HelloWorldDiv">
Hello World!

Maven dependencies

Next I set up the maven configuration. For this example I am using a simple pom.

<project xmlns="" xmlns:xsi="" xsi:schemaLocation="">
	<name>My Portlet</name>
	<description>A basic portlet mavenized</description>

I will describe what all of this does starting at the top. It starts with the basic maven configuration for the project. Moving on to the build section. There are some issues with loading classpaths and if I don't tell the surefire plugin to not use the system classloader, jetty will not be able to find the JSTL tag library and thus the entire test will fail.

 In the dependencies section I will start with the standard portlet api. This is required to compile the portlet class. Next is the jetty-maven-plugin. This is the lightweight web container used as a web server if you will when we are running the tests. This is then used together with the maven-jetty-pluto-embedded plugin. Pluto provides the portlet engine for the portlet  and maven-jetty-pluto-embedded provides the possibility to use pluto together with jetty. Starting with version 2.0 of this plugin the JSR286 portlet specification was supported. Next is jwebunit-htmlunit-plugin. This is what I use for the actual tests in my test class. The exclusion in the dependency is for us to be using my own custom logging configuration and so is slf4j-log4j12. Also note that all of these dependencies (except for the portlet api) are using the test scope. This is because I will only require these during the test phase.

Also as a sidenote. Some of these implementations have newer versions available in particular the jetty-maven-plugin, but since one of the critical components is maven-jetty-pluto-embedded, the version I use here is the latest compatible version I have found I can use.

The test class

Now off to the test class. Basically I do this in three steps. Setting up the server, running my tests and shutting down the server.

package mytest;

import static net.sourceforge.jwebunit.junit.JWebUnit.assertElementPresent;
import static net.sourceforge.jwebunit.junit.JWebUnit.assertTextPresent;
import static net.sourceforge.jwebunit.junit.JWebUnit.beginAt;
import static net.sourceforge.jwebunit.junit.JWebUnit.getTestContext;

import org.apache.pluto.container.driver.PortletServlet;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.mortbay.jetty.Server;
import org.mortbay.jetty.servlet.ServletHolder;
import org.mortbay.jetty.webapp.WebAppContext;

public class MyPortletTest {
	private Server server;
	private static final int SERVER_PORT = 8080;

	public void setUp() throws Exception {
		System.setProperty("org.apache.pluto.embedded.portletIds", "MyPortlet");
		server = new Server(SERVER_PORT);
		WebAppContext webapp = new WebAppContext("src/main/webapp", "/test");
		ServletHolder portletServlet = new ServletHolder(new PortletServlet());
		portletServlet.setInitParameter("portlet-name", "MyPortlet");
		webapp.addServlet(portletServlet, "/PlutoInvoker/MyPortlet");
		getTestContext().setBaseUrl("http://localhost:" + SERVER_PORT + "/test");

	public void tearDown() throws Exception {

	public void testDoView() {
		assertTextPresent("Hello World!");

The startup of the server can be done also through configuration, but I extended my work starting from the blog where I found the JSR168 examples so I will continue the same way. In the setUp() method I do all of the server configuration and startup work. The exact name of the method id not important, but it must use the @Before annotation. The first line defines the portlets I use in my tests, the exact name is not important but it must match the portlet name in the portlet.xml. There can be multiple portlets as long as they are on a comma-separated list. The server is created with only a port where the server is started. The port can pretty much be any port as long as it is not already in use.


Next the web application context is set up. Here I define a servlet url mapping and add pluto descriptors and classes in order to get a proper portlet engine. The web application context is added to the server and the server is started. Finally the base url to use for all tests is defined.


The tearDown method is run after all the tests have completed (using the @After annotation). All this method does is to stop the server.


Finally I have the test method. This is just a simple demonstration to get started. What you want to do with your tests is up to you. Any test method can contain a number of different tests and there can be multiple tests in a test class. Here I start navigating to the pluto portals front page, making sure a certain text and div is present.


Reduce logging

If you run the test with only the above setup, you will find there is some extensive logging done. This is because the logging is set to debug level. I find this a bit too talky myself. In order to fix this, first we must exclude the default logging from JWebUnit. Jetty uses slf4j and all I did from there was to add the log4j impementation of slf4j using this configuration.

log4j.rootLogger=WARN, stdout
log4j.appender.stdout.layout.ConversionPattern=[%p] %c{1}:%L - %m%n

This configuration will set the logging to warn level. This will reduce the logging drastically but the cause will still be logged if an error fails. You may need to adjust the log level for further debugging if a test fails, but I found this to be a nice setting. I have also added a configuration which will output maven-like logging.



Make your portlet development use maven in no-time

Posted by:


I started using maven some time back and I have found many advantages. One in particular was the ease to run unit tests. This made me want to be able to unit test portlets. The portlets I create nowadays are all based on the JSR286 standard. I did not find any examples of that, but with some help from what I found I was able to do unit testing. First things first though. Before we can use unit testing for portlets, we need to have a portlet where we also use maven. This blog entry will show you have you as simple as possible get your portlet sources mavenized. 

I will not cover the topic of why you should use portlets or maven. There are so many good resources out there already and a simple search should be easy enough to find them.


Basic portlet

First of all I have a really minimalistic portlet. There is only what I need to have inb order for the portlet to work. The point was to give a basic example of what you need to do to start using maven to build your portlet. In this I had the portlet class, a jsp file, the portlet.xml, the web.xml and some resource bundle property files.



In order to use maven you need to have some software installed. You need to have a jdk (I used the latest available from Oracle) and maven. Make sure you have your maven binaries set in your path and your JAVA_HOME environment variable set to the directory where you installed the JDK. Note! It must be the jdk, a jre will not be sufficient in the long run.

If you just want to use the central maven repository and have direct access to Internet you don't need to do any other configuration, but if your network setup is different you may need to look at additional steps to configure maven, such as using a proxy with maven.


Moving files

Maven use a standard layout for its directories. You are in no way obliged to follow this standard and I am not going to even get into a discussion about what is best, I will simply leave that up to you. In this example though, I am using the standard directory layout as it makes the maven configuration easier. 

A portlet is packed in a web application archive, a war file. While maven has no direct portlet packaging available, it is not really required either as we use the war packaging, which effectively does the job. With this in mind there in particular three directories which we will use from the maven standard.


At this step you should move all of your portlet files into these three directories.

src/main/java should contain all your java sources. It is the root directory of your java sources so if you have your classes in packages, that structure must still be intact. The compiled classes will end up in your WEB-INF/classes directory. src/main/resources contains non-java files which should end up together with your compiled classes. In this case the portlet ResourceBundle property files will be here. Again, if you are using a package structure for your resources, that structure must be intact. The resources files will be copied as is (depending on your maven configuration) to your WEB-INF/classes directory. Finally the src/main/webapp directory contains all the files which should end up in the root directory of your web application. This includes any jsps you may have as well as your META-INF and WEB-INF directories (and all the files there in such as WEB-INF/portlet.xml and WEB-INF/web.xml). 

After all of this is completed I ended up with the following file structure:


Maven configuration

The heart of maven configuration is the pom. It is in xml format and its name is pom.xml. This file was created in the root directory. First there was the basic stuff. I won't go into details of any of this. Some of it is fairly self explanatory, but for the rest I suggest you look at the pom reference.

<project xmlns="" xmlns:xsi="" xsi:schemaLocation="">
    <name>My Portlet</name>
    <description>A basic portlet mavenized</description>
    <!-- The dependencies will be added here.-->

Finally the portlet apis need to be added in order for the portlet class to be compiled. For this we add a dependency. A dependency is really what the name implies. In order to compile and build our portlet we have a dependency on another library (apart from standard java) in this case the portlet api. For this portlet to work only the portlet api is needed, but there may be many dependencies. Note the scope in this dependency. With the scope of provided we are telling maven that this dependency will be provided later on, we only need to use it now at compile time. This is true because the portlet libraries are provided by the portlet container when we run the portlet. The libraries should not be included in our war file.



Now we are done and we are ready to build. The command to build, package and verify as much as possible without adding our built war to the local or remote repository is mvn verify. If all has been done right you should get a BUILD SUCCESSFUL message in the end.





5 minutes of effort = 1600% increase in performance

Posted by:

So, the other day I was humming along for one of our larger clients – putting the finishing touches on one of their applications. The app in question handles matching of vacancies against applications. The administrator needs to quickly have the ability to browse what vacancies have what status. 

One vacancy can have one of three different statuses:

  1. View – Show the selected application for this vacancy.
  2. List – Lists all matching applications for this particular vacancy.
  3. Missing – No current applications exists that match the criteria for this vacancy.

Don't worry too much about the business logic, I only provide a quick background to give you some idea of what I was trying to achieve.


Oh, I nearly forgot! Of course this is an IBM Domino solution as we are a "True Blue" IBM Premium Business partner. Unfortunately this client was stuck with a fairly old IBM Domino server: 8.5.2, so I wasn't too keen on using an XPages solution. Why? Because in my humble opinion XPages just hadn't matured enough yet. (Missing HTML5 features, no SSJS debugger, old DOJO release, loooong "first hit" boot times and so on – Yes, all of this can be mended, worked around, patched etc. But sometimes you can just say enough is enough and go with old school Domino development.)

Anywho, my first inclination was to create a WebQuerySave agent that did the matching ServerSide before presenting the result to the user, a very common approach. But the performance was really bad – The WQS agent took around 4000ms although the workload was light and number of documents fairly low (in the hundreds anyway). The page itself took around a second to load with an empty cache, so we we're looking at a total page load time here in the neighborhood of five seconds – not acceptable.

So I used an approach that's known as perceived performance. Let's take a clock as example – If you use a clock that doesn't show seconds, time seems to move slower. If there's a lot of stuff going on, the general experience is that things are happening quicker. So I extracted my LotusScript code and placed it in an agent that get's called thru AJAX. This way the page loads quickly, the user can start to interact with it immediately and the state of each vacancy trickles in as the server sees fit.

Below is a screenshot of the application, waiting for the AJAX request to comeback with the data. (The only vacancies that know its state are the ones that are booked, they're marked with "Visa" in the column to the right, the rest are pending).


Finally, here we have the first icarnation of the code:

Nothing too odd about the above, I would even dare to say a fairly common approach. I do what I can to speed up the process by using NotesViewEntryCollections and the ColumnValue-property. Using one view as the source, that has a column that combines the particular criteria for that vacancy. The key can look something like this:

2015-05-27DSurgeon (Date + Slot + Role)

We use this key to find any matching requests, if none is found it's added to the string that's returned to the AJAX request. We only need the ones that doesn't have a match (Missing) as the first state (View) is stored with the vacancy and the second state (List) are all that are not missing. Ideally "Missing" should always be very few documents so the data transfer over the wire should also be low, increasing performance further.


So, everything was "hunky-dory" then. The application loaded quickly and felt responsive to the user, but… The bad performance of the LotusScript code was nawing at me… 

After a murky night of coding I came up with the following:

Option Public
Option Declare
Sub Initialize
	Dim s As New NotesSession 
	Dim db As NotesDatabase 
	Dim vRequest As NotesView
	Dim vMatchVacancy As NotesView
	Dim veRequest As NotesViewEntry 
	Dim veMatchVacancy As NotesViewEntry 
	Dim rowIds As String
	Dim key As String
	Dim i As Integer
	Dim count As Long
	Dim hasEmptySlots As Boolean
	Dim navMatch As NotesViewNavigator 
	Dim navRequest As NotesViewNavigator 
	Dim ve As NotesViewEntry
	On Error GoTo handler
	Set db = s.Currentdatabase

	Set vMatchVacancy = db.getView("vMatchVacancy")
	Set vRequest = db.getView("vRequest-list-match")
	Call vRequest.refresh()
	Call vMatchVacancy.refresh()
	Set navMatch = vMatchVacancy.createViewNav()
	Set navRequest = vRequest.createViewNav()
	count = vMatchVacancy.Allentries.Count
	i = 0
	' do not do AutoUpdates
	vMatchVacancy.AutoUpdate = False
	vRequest.AutoUpdate = False
	' enable cache for max buffering
	navMatch.BufferMaxEntries = 100
	' if we are not interested in the number of children, we can go a little faster
	navMatch.EntryOptions = Vn_entryopt_nocountdata

	Set veMatchVacancy = navMatch.GetFirst
	Print "content-type: text;charset=utf-8;"
	While ( i <  count )  
		hasEmptySlots = False
		key = veMatchVacancy.Columnvalues(0)
		Set veRequest = vRequest.Getentrybykey(key, True)
		If(veRequest Is Nothing) Then
			Print  rowIds & veMatchVacancy.Columnvalues(1) & ","
		End if
		Set veMatchVacancy=navMatch.getNext(veMatchVacancy)
		i = i + 1

	Exit Sub 
	MsgBox db.filepath & "agentMatchVacancys - " & Error & Chr(13) + "Module: " & CStr( GetThreadInfo(1) ) & ", Line: " & CStr( Erl ) 
	Print Error & Chr(13) + "Module: " & CStr( GetThreadInfo(1) ) & ", Line: " & CStr( Erl ) 
	Resume exitSub 
End Sub

The big difference here is the use of the NotesViewNavigator. When using the NotesViewNavigator object you have the opportunity to use it's cache – "BufferMaxEntries". I set it to 100 in my case as the view will show no more then 100 rows at a time. I also set the EntryOptions to "VN_ENTRYOPT_NOCOUNTDATA" as I have no parent/child relationship in the view.

All in all the the running time of the agent went from 4000ms to 25ms! Pretty darn impressive if anyone were to ask me!


This technique is nothing new, but the performance gains are so huge I thought it's well wort repeating.

I was heavily influenced by this article: "Fast Retrieval of View Data Using the ViewNavigator Cache – V8.52" and I highly recommend you check that out for more details.



After re-running the performance tests in my local test environment I've "only" managed a 200% increase in performance. Beware, YMMV….


XPages – How to get a proper JavaScript debugger in XPiNC!

Posted by:

The low down: Download FireFox 5 + FireBug 1.8.4 and BAM! Instant CSJS debugger!

Yup! It’s basically that simple (for once). Read on for the gory details…

In one of my client projects I had the opportunity to work with XPages in the Notes Client, or XPiNC for short. Being a developer with almost 20 years experience I take “limited pleasure” in developing for the Notes client. My opinion is that you’re too restricted in what you can achieve front-end and graphical layout is unmistakably Notes – in a bad way. IBM Notes has it’s benefits – like you only have to worry about the shortcomings of one client, where as web clients have a legion of different vendors and versions. Sometimes even the same vendor is incompatible with it’s own versions! Yes – I’m looking at you Internet Explorer! But still, the benefits of web based development outweighs the negatives, at least for me.

But, hey! We have a new kid in town: XPages! Who’s supposed to run in the Notes client, more or less without modification…

“Wow! What a totally amazing, excellent discovery!”-Wayne Campbell


Excellent! Or – It could have been

XPiNC uses a browser to render your XPage inside the Notes client. We have been able to do parts of this for years, by utilising an embedded browser control in the Notes client:

Domino Designer – Form – Create / Object / Control – “Microsoft Web Browser”

You can see in action here, from an application I did a while back. We’re jumping straight into the action at 3:04 showcasing the embedded  “Microsoft Web Browser”-control in an ordinary Notes form, no XPages as far as the eye can see!

video demo of the "Microsoft Web Browser"-control in action

Video demo of how an embedded web browser control can interact with a Notes client, without using XPages

Yes – Yes! I Know! It doesn’t have the full potential of XPiNC, like offline support, field level encryption and so on. But still, it usually impresses the “general population”. You might notice that the performance of the web part of the GUI isn’t stellar? It’s because the client used IE7 which is “less then great” (to put it kindly) at performance in general and JavaScript in particular.


Speaking of old browsers

Anywho! Where was I…? Yes! This could be really great news – the ability to run XPages in the Notes client. But it has some shortcomings. The browser we’re stuck with is something called a “XULRunner”, more about that in a bit. The version of your embedded browser differs depending on the version of IBM Notes in use. In my case: IBM Notes 8.5.3FP1 UP1 translates to R5.0 of XULRunner. One way to check what version your particular installation is using is to run a JavaScript snippet: window.navigator.appVersion on an XPage in your environment. Now, there’s a gazillion different ways to achieve this. Well, maybe not a gazillion exactly – but there abouts. I will demonstrate a particularly cumbersome way, just because I can! (And you will see some added benefits to your development environment in the process).


Getting FireBug Lite

When I first started dealing with XPiNC I found that you can set some params in the file to enable some version of FireBug Lite:

That’s one way of doing it. But you’re stuck with a really old (and ugly!) version (surprise! NOT!) A much better way is to inject the FireBug addOn thru an Eclipse plugin. This way, no other developers will be bugged (pun intended) by the debugger and you can always enjoy the latest version of FireBug, regardless of what IBM seems fit.

So, without further ado, I present the excellent work by Mr Karsten Lehman: XPiNC app development tool


XPiNC front-end performance

Once that is over and done with, you can run my earlier JS snippet:  window.navigator.appVersion – In my case that would return “5.0 (Windows; sv)”.

– Ok, great! We now know that you’re running R5.0 of something called a “XULRunner”. That’s neat and all! But why should I care?

Well, because XULRunner 5.0 is in all useful purposes equivalent to FireFox 5.0!

– Wohoo! Sweet! But.. But? Isn’t that like reallllly old?

Yes, yes it is. It was released back in the day: 21 of June 2011. 14 releases, or almost two years ago (That’s like 20 “web years”). The latest version, at the time of this writing, is R19.0!

(Earlier version of IBM Notes uses the XULRunner equivalent of Firefox 3.6.x)

HTML5 support

Below is a comparison between the HTML5 capabilities between the different versions of Firefox currently used in IBM Notes vs the latest release of Firefox available:

Comparing HTML5 capabilities Firefox browser versions

[Click the image for the full comparison.]Comparing the HTML5 capabilities of the different versions of Firefox

As you can see the capabilities aren’t great, but whether it’s a real problem is entirely up to the application being developed. Put simply, if you’re not taking advantage of the capabilities in HTML5 (you should!) then this won’t be a problem.

To get some ideas, regarding the benefits of using HTML5, I recommend the site HTML5Rocks.

CSS3 support

But the limitations doesn’t end there I’m afraid. I’ve included a comparison for CSS3 support below. Showing R3.6, R5.0 and R19 in that order. (Click the image for the full comparison! But be warned, it’s BIG!)

Comparing CSS3 support across Firefox versions

This is not an exhaustive comparison, but should give a good indication.

If you click the image, you will be painfully aware of small nuances that will plague your road to the pixel perfect heavens of stardom!

JavaScript performance

If that wasn’t bad enough, the JavaScript performance is about 200% faster in Firefox 19 compared to Firefox 5. (Haven’t been able to test Firefox 3.6, but do expect it to be quite a bit slower.)

Running the browsers thru the ECMAScript testing page (click here to test it yourself) will make you even more depressed. Firefox 3.6 fails in 4247 tests, Firefox 5.0 fails 282 and Firefox 19 in 170. Granted that Firefox 5 scores pretty good, but for instance it doesn’t support the very common DOM operation parentElement. Makes you wonder what else it has in store for you programming endeavours doesn’t it?

Basically, what all this boils down to, is that to keep your XPages compatible with XPiNC you have to limit your webpages to the old standard that particular version of Firefox supports (dragging newer browsers down), or support two different versions of your XPages. Not a very appealing proposition either way.

I expected IBM Domino 9 to update the XULRunner, but no luck there. At least the public Beta 1 is still running R5.0 of XULRunner. I’m not expecting this to change for the released version, which is too bad.

Still some good news

If you’re a “Copy / Paste”-developer – who sticks with the default widgets provided with XPages,  then the above probably won’t cause you much headache and I’m afraid you’ve read most of this in vain. Because XPages in combination with Dojo will make most of the differences go away and the ones that are left might be tolerable to you.

But if you like to not only push the envelope, but to kick the crap out of it! Then the above will be the cause of some major grief and sleepless nights.

Hopefully you can limit some of the pain, revelling in the fact that you can do your front-end debugging using all the glory of FireFox 5 instead of mocking about with the embedded XULRunner client in the Notes client. This includes installing a big fat and juicy version of FireBug 1.8.4 in FireFox 5, no more debuggers on a diet for you!

You can download FireFox 5 here and FireBug 1.8.4 here.

Yet to come

I plan a follow up post where I share my experience developing for XPiNC, like potential pitfalls and how to circumvent those.

Keep watching this space!

In the meanwhile you can follow me @JBoive &| Google+

Page 1 of 2 12