Use @Transform to build JSON and consume the output in an XAgent

Put this piece of code into a view column; in _exclude list all items from the document, that should not be included in the output
All items in the document that are not excluded are used to build a JSON String 

=========================== @Formula START =========================================

_exclude:="$FILE":"$Fonts":"Form":"$UpdatedBy":"$Revisions":"ID":"ModifiedBy":"AddressInvoiceAppartment";
_fld:=@Trim(@ReplaceSubstring(@DocFields;_exclude;@Nothing));

"{\"@unid\":\""
+@Text(@DocumentUniqueID)+"\","
+ @Implode (
@Transform (
_fld; "_fn" ; "\"" + _fn + "\":\"" + @Text ( @GetField ( _fn) ) + "\"" ) ; "," ) +
"},"

=========================== @Formula  END=========================================

To retrieve the JSON string, create a new XAgent

=========================== XAgent START=========================================

<?xml version="1.0" encoding="UTF-8"?>
<xp:view xmlns:xp="http://www.ibm.com/xsp/core" rendered="false">
	<xp:this.afterRenderResponse><![CDATA[#{javascript:try{
	var externalContext = facesContext.getExternalContext();
	var writer = facesContext.getResponseWriter();
	var response = externalContext.getResponse();
	  
	// Set content type	
	response.setContentType("application/json");	 
	response.setHeader("Cache-Control", "no-cache");
	var json:java.lang.StringBuilder = new java.lang.StringBuilder();
	var v:NotesView = database.getView("($jsonContact)");
	//do not do AutoUpdates
	v.AutoUpdate = false;
	var nav:NotesViewNavigator = v.createViewNav();
	nav.setEntryOptions(
	NotesViewNavigator.VN_ENTRYOPT_NOCOUNTDATA);
	//enable cache for max buffering
	nav.BufferMaxEntries = 400
	var entry:NotesViewEntry = nav.getFirst();

	while (entry != null) {
		json.append( entry.getColumnValues().elementAt(0).toString());
		var tmpentry:NotesViewEntry = nav.getNext(entry);
		entry.recycle();
		entry = tmpentry;
	}

	writer.write('[' + @Left(json.toString(), @Length(json.toString()) - 1) + ']');	 
	writer.endDocument();
} catch(e){
	_dump(e);	
}}]]>
	</xp:this.afterRenderResponse>
</xp:view>

=========================== XAgent END =========================================

The XAgent uses a ViewNavigator for fast retrieval of the column entries. The real magic is the use of java.lang.StringBuilder() to concat the view entries. A stringBuilder is the fastest way to concat a large number of strings. It is faster than just to use string1 + string2 

UPDATE:

Here is an enhancement, if you want to fetch the column values with Java

public class ViewColumn {
	private static final String MSG_STRING_ERROR = "ERROR: ";
	private static final String MSG_STRING_NOT_FOUND = " not found";

	public ViewColumn() {
	}
	
	public String getViewColumnValueJSON(String viewname, int pos) {
		ViewNavigator nav = null;
		StringBuilder json = new StringBuilder();
		json.append('[');
		String strValue = "";
		try {
			View view = getCurrentDatabase().getView(viewname);
			if (null != view) {
				view.setAutoUpdate(false);
				nav = view.createViewNav();
				nav.setEntryOptions(ViewNavigator.VN_ENTRYOPT_NOCOUNTDATA);
				nav.setBufferMaxEntries(400);
				ViewEntry entry = nav.getFirst();

				while (entry != null) {
					json.append( entry.getColumnValues().elementAt(pos).toString());
					ViewEntry tmpentry= nav.getNext(entry);
					entry.recycle();
					entry = tmpentry;
				}		
				strValue = json.toString();
				strValue = strValue.substring(0, strValue.lastIndexOf(",")) + "]";
				view.setAutoUpdate(true);
			} else {
				System.out.println(MSG_STRING_ERROR + viewname + MSG_STRING_NOT_FOUND);
			}
		} catch (NotesException e) {
			System.out.println(MSG_STRING_ERROR);
			strValue = "[{}]";
		}
		
		return strValue;

	}
}








An FAST and easy way to build a complex JSON String / (Almost) No need to calculate at runtime.
Can be used i.e. in the xGrid project http://www.openntf.org/Internal/home.nsf/project.xsp?databaseName=CN=NotesOSS2/O=NotesOSS!!Projects\pmt.nsf&documentId=8147C9C5EC59C08E86257A0C006FD1F8&action=openDocument

JavaScript (Server)
Ulrich Krause
June 1, 2012 4:21 AM
Rating
430

All code submitted to OpenNTF XSnippets, whether submitted as a "Snippet" or in the body of a Comment, is provided under the Apache License Version 2.0. See Terms of Use for full details.



No comments yetLogin first to comment...