Working with JSON in your XPages application (2) – getEntryByKey

Introduction

In the previous post we started with the first steps to modernize our xpages application by defining our Notes view data in JSON format, create objects from them in Java with help from  com.ibm.commons.util.io.json and return them to the xpage (repeat control).

In our example we used the AllEntries method which is well known across the languages Domino supports (LotusScript/JavaScript/Java).

getEntryByKey

As Domino also supports other methods to work with Notes view data we have to extend our Java class with them. Next in line lies the getEntryByKey method.

Changes in setup

Removed Content Delivery Network

In the previous post we used CDN for loading Bootstrap. Since we work with XPages and the latest and greatest Extension Library at our service we simple apply the Bootstrap theme for our application.

New Notes view

In our *NonSQL* database we will add a new view with the first column categorized. I have chosen the following document properties:

varUNID:=@Text(@DocumentUniqueID);
varAuthor:=Au_Author;
varCategory:= Photo_Category;
varCreated:=@Text(@Date(@Created));
@Return(Photo_Title:varUNID:varAuthor:varCategory:varCreated)

I also extended the second column compared with the first view. The column formula is as followed:

REM {This column builds a JSON string};

varUNID := @Text(@DocumentUniqueID);
varCategory:= Photo_Category;
varTitle := Photo_Title;
varAuthor:=Au_Author;
varDesc:=PhotoDescription;
varCreated:=@Created;
varThumb:=Photo_ThumbFilename;
varSmall:=Photo_SmallFilename;

jsonOpener := “{“;
jsonClosure := “}”;
jsonSeparator := “\”,”;
jsonLastItem := “\””;

@Return(
jsonOpener +
“\”docUNID\”: \”” + varUNID + jsonSeparator +
“\”author\”: \”” + @Name([CN]; varAuthor) + jsonSeparator +
“\”category\”: \”” + varCategory + jsonSeparator +
“\”subject\”: \”” + varTitle + jsonSeparator +
“\”descr\”: \”” + varDesc + jsonSeparator +
“\”created\”: \”” + @Text(@Date(varCreated)) + jsonSeparator +
“\”imgthumb\”: \”” + varThumb + jsonSeparator +
“\”imgsmall\”: \”” + varSmall + jsonLastItem +
jsonClosure
)

Notice I added an additional key:pair for a smaller (preview) image. I also find the @Return function a good best practice to explicit indicate something is being returned.

With this new view available we will update our Java class.

Java class additions

Our Java class will have two new functions:

  • loadPicture(Key)
  • loadJSONObject

The first indicates we will send along a unique identifier and the second indicates we will return a single JSON object.

public JsonJavaObject loadPicture(String Key) throws NotesException {
JsonJavaObject json = null;

NotesContext nct = NotesContext.getCurrent();
Session session = nct.getCurrentSession();

String ServerName = “dev1”;
String DatabaseName = session.getCurrentDatabase().getFilePath();
String ViewName = “$v-pixJSONCategories”;

try {
json = loadJSONObject(ServerName, DatabaseName, ViewName, Key, 1);
} catch (NotesException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return json;
}

and

private JsonJavaObject loadJSONObject(String ServerName, String DatabaseName, String ViewName, String Key, Integer ColIdx) throws NotesException {

JsonJavaObject json = null;

NotesContext nct = NotesContext.getCurrent();
Session session = nct.getCurrentSession();
Database DB = session.getDatabase(ServerName, DatabaseName);

if (!(DB==null)) {

if (!(DB.isOpen())) {
DB.open();
}

View luView = DB.getView(ViewName);
if (!(luView == null)) {

ViewEntry entry = luView.getEntryByKey(Key);
if (!(entry == null)) {

Vector<?> columnValues = entry.getColumnValues();
String colJson = String.valueOf(columnValues.get(ColIdx));

try {
JsonJavaFactory factory = JsonJavaFactory.instanceEx;
json = (JsonJavaObject) JsonParser.fromJson(factory, colJson);
} catch (JsonException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

entry.recycle();
}
luView.recycle();
}
DB.recycle();
}
return json;
}

Probably during development (and acceptance) you would like include a logging mechanism. I have left the System.out.println statements out of the examples…

A new XPage

Since we will call the loadPicture method with a key we need to provide a mechanism to capture this key. In our first example we capture the key from the unid parameter that we attach to the URL e.g. page2.xsp?unid=1234. Notice that the unid has to respond to a category value set in the category column in the Notes view. So my proposal is to use categories that are sufficient distinguished from each other.

In my xpage I drag in a panel and define a dataContext for it:

<xp:this.dataContexts>
<xp:dataContext var=”data”>
<xp:this.value><![CDATA[#{javascript:var paramUNID = paramValues.get(“unid”);
strUNID = paramUNID.toString();
PictureProvider.loadPicture(strUNID);}]]></xp:this.value>
</xp:dataContext>
</xp:this.dataContexts>

Notice I am using the paramValues global object available in XPages to capture the key. With this key I call the loadPicture method.

Within the panel I define a Bootstrap form:

https://www.dropbox.com/s/gxfofuu6ujec2qt/bootstrap%20form.txt?dl=0

(for some reasons WordPress want to transform my text into HTML)

Data is the variable I have defined for the dataContext. Hereby I can easily access the JSON object properties and collect a value by accessing a key e.g. data.docUNID.

With these new additions our result looks and followed:

isn't she lovely?

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s