Skip to main content

skip to main content

developerWorks  >  Lotus  >

Open Standards, Open Source, and Domino 6: Accessing the Domino Directory through Python and Java

developerWorks
Document options

Document options requiring JavaScript are not displayed


Rate this page

Help us improve this content


Level: Intermediate

Raj Balasubramanian, Consulting IT Architect, IBM

20 Sep 2004

We conclude our article series on open standards and Open Source in Lotus Domino 6 by explaining how you can build two different applications for accessing a Domino Directory. The first is a Python application created with the GIMP Toolkit (GTK), and the second is a Java application created using the Standard Widget Toolkit (SWT).

In part 1 of this three-part article series on open standards and Open Source in Lotus Domino 6, we discussed the open standards implemented in Lotus Domino. In part 2, we examined how you can leverage some of Domino's Open Source projects. In this last article in the series, we continue this theme by looking at how to use GIMP Toolkit/Python and Standard Widget Toolkit/Java to access Domino applications on a Linux server. We include sample code that you can download from the Sandbox.

This article assumes that you're an experienced Notes application developer. We suggest you read the previous two articles in this series if you haven't already.

Accessing a Domino directory through GTK and Python

The GIMP Toolkit (GTK) is a multi-platform toolkit for creating graphical user interfaces. It provides a comprehensive set of widgets and supports Unicode and bidirectional text. GTK is free software and part of the GNU Project. GTK supports several languages, including C++, Perl, and Python. A valuable tool for using GTK in Python programs is PyGTK, which provides a wrapper for the GTK library for use in Python programs, handling details such as managing memory.

In this section, we explain how you can use Domino's native GTK on a Linux desktop to connect to a Domino application. Our sample application is built using Python and PyGTK to access a modified Domino Directory hosted on a Domino 6.5 server. You can download the complete code for this application from the Sandbox.

The sample GTK/Python application

Our sample GTK/Python application opens the Domino Directory and retrieves information from individual Person documents. Here is a screen of how the application looks on a Linux laptop:


Figure 1. Sample GTK/Python application
Sample GTK/Python application

Clicking a name displays information about that entry:


Figure 2. GTK/Python application person information
GTK/Python application person information

The following diagram illustrates how the components of the GTK application work together to open the Domino Directory and to obtain person information from it:


Figure 3. GTK application components
GTK application components

The key concepts that make the GTK/Python application possible are:

  • XML data can be obtained directly from a Domino view.
  • We can generate XML from a Notes document via LotusScript (using DXL).
  • GTK Python bindings allow us to easily script a GUI program.

Before you deploy the application, you must make two modifications to the Domino Directory itself. First, change the ACL to allow Anonymous reader access. You must also create an agent called dxldoc to deliver XML to a given UNID. (We describe the code for this agent later in this article.)

Here is a high-level sequence diagram of how the application functions:


Figure 4. GTK application sequence diagram
GTK application sequence diagram

Briefly, the sequence of events shown in Figure 4 are as follows:

  1. The user launches the application.
  2. The application opens the Domino Directory (in this case named testnab.nsf) and retrieves data from the People view.
  3. The application parses the information and displays it to the user (Figure 1).
  4. The user clicks a listed name to display information about that particular user.
  5. The application retrieves the person information (in DXL format) from the dxldoc agent running in the Domino Directory.
  6. The application parses the information and displays it to the user (Figure 2).

Deploying and running the application

To run this sample application on a Linux server, you must do the following:

  1. Install Python 2.2 or later. Then ensure it is executable from a shell prompt (if not, add Python to your PATH statement).
  2. Download and install PyGTK 2.2. Run the PyGTK demos as part of the PyGTK installation package to verify that the installation was successful.
  3. Install PyXML. PyXML is a collection of libraries to process XML with Python.
  4. Edit our sample application source code to reflect your server name/IP address and the name of the database (testnab.nsf). Ensure that the ACL is set to Anonymous reader access.
  5. Deploy the test database on a Domino server and sign the dxldoc agent with the proper authority.
  6. Run the application using the command # python gtk-ReadNAB.py.

Before you do this, read the following sections to understand how the agent and Python code work.

GTK/Python application code

This section reviews the code necessary for the GTK/Python application. This consists of the dxldoc agent that runs on the Domino Directory and the Python code for the application itself.

dxldoc agent
The dxldoc agent generates the DXL form of documents stored in the Domino Directory. This allows the Python program to read the documents and to retrieve information from them. To use the dxldoc agent, copy it from the Sandbox and paste it into the custom Domino Directory using Domino Designer.

The first part of the agent declares all the required Notes objects:

Sub Initialize
	'declare notes objects
	Dim s As New notessession
	Dim db As notesdatabase
	Dim doc As notesdocument
	Dim doc1 As notesdocument
	Set doc1 = s.DocumentContext

Next, the agent sets the content type to XML format to be output to the requesting application:

	Print "Content-type: text/xml" 
	On Error Goto err1
	
	Set db = s.currentdatabase
	
	Print ""

These lines parse the URL of the document to obtain its UNID:

	Dim stg As String
	stg = doc1.Query_String(0)
	If Len(stg) < 5 Then
		Goto err1
	End If
	If Instr(stg,"unid=") < 1 Then
		Goto err1
	Else
		stg =  Right(stg,Len(stg)-Instr(stg,"="))
		'Print stg
	End If

	Set doc = db.GetDocumentByUnID(stg)

And these lines declare DXL-specific data:

	Dim exporter As NotesDXLExporter
	Dim stream As notesstream
	Set exporter = s.CreateDXLExporter
	Set stream = s.CreateStream
	Call exporter.SetInput(doc)

Now the agent processes the Person document as DXL:

	Call exporter.SetOutput(stream)
	Call exporter.Process	

Finally the agent outputs the DXL XML text to the requestingr application (or prints an error message if unsuccessful for any reason):

	Print stream.ReadText()
	End
err1:
	Print "You reached in error"
End Sub

Python code
Now let's briefly examine the logic and organization behind the source code for the main Python program (which you can download from the Sandbox). Python's ease of scripting and syntax coupled with the GTK libraries (and the ability to wire widgets and events) gives you the power to quickly develop GUI applications on Linux (as well as Windows).

The core application is organized into two classes (ReadNAB and displayForm) contained within the single Python program. Each of these classes have defs (functions/methods) defined to perform a unit of work. The reason for splitting them into classes is to logically lay out the first GUI window that displays the view entries and the second window that displays details on a selected user entry. Both classes perform very similar operations: Use XML libraries to connect to a Domino server using a URL and process data to be stored in a temporary data structure (a/b/d/pp) in addition to handling the windows, buttons, layouts, menus, and display. The core widget used to display the view data is a TreeView widget, which is embedded in a window object. The display of the Person document data is done using labels on a window. Experienced coders can investigate other widgets and objects to better display and handle the data. (For example, you can add additional fields and better organization to the layout.)

User actions (button click, double click of text entry, and so on) are wired back to specific functions that are defined in the class. For example, clicking the OK button in the Person data window hides the display window, while leaving the main window on:

def button_press(self, widget, data=None):
	self.window.hide()
........
self.button.connect("clicked", self.button_press,"done")

Similarly, choosing File - Close in the main window (view entries) closes the application:

def menuitem_response(self, widget, data):
		gtk.main_quit()
		return gtk.FALSE
......
self.menu_items.connect("activate", self.menuitem_response, "Close")

We then use the native image display facilities in GTK to display a company logo showing your company name. (The logo images reside in the same directory as the Python source you are running.)

For processing the XML, the program keys off of the columnnumber attribute, and uses the view entries and item name in the Person document to get the core data to display within the windows. Refer to the book Python and XML for a good introduction to Python XML processing.

The Python code starts processing the XML by importing all the packages it will be using in the application: PyGTK, GTK for building the GUI, and Sax2 for XML parsing. We then declare the displayForm class and define various functions to perform the following:

  • Cleanup
    Clears the temporary data structure that stores the Person document fields (DN, lastname, mail, and company name).
  • button_press
    Handles the event when the OK button is clicked.
  • Displayf
    Builds the windows and paints the screen with data and graphics.
  • parseDoc
    Gets XML and parses it based on rules (which field to get for display and so on).

Following this are the declaration for the ReadNAB class and definitions for various functions:

  • findText
    Parses XML based on rules (which column to display).
  • delete_event
    Handles the event when a window is closed.
  • menuitem_response
    Handles the event when a menu item is clicked.
  • getUnid
    Given a key, returns the document UNID.
  • selection_changed
    Handles the event when a particular entry is checked.
  • Init
    Handles the launch point of the class that handles window/display and connects to Domino to get XML.



Back to top


Accessing a Domino Directory through SWT and Java

The Standard Widget Toolkit (SWT) is a set of tools that deliver native widget functionality for the Eclipse platform. SWT is the core of the Eclipse Rich Client Platform (RCP).

In this section, we discuss how to leverage the power of SWT to write a custom Java client on Linux. We used SWT to write a simple interface to the Domino Directory using IIOP as the transport. This provides a fast and easy way to build GUI applications on both Windows and Linux (as well as Mac OSX). Our sample application is built using Java and SWT to access the standard Domino Directory hosted on a Domino 6.5 server. There is no special code written on the Domino end to create the application.

The sample SWT application works similarly to the GTK/Python application discussed earlier in this article. It accesses a Domino Directory and retrieves user information from it. For example, Figure 5 shows the main application window, which lists Person documents found in the Domino Directory:


Figure 5. Standard Widget Toolkit (SWT) application
Standard Widget Toolkit (SWT) application

Clicking a listed name displays the Person document information for that user, for example:


Figure 6. SWT application person information
SWT application person information

As you can see, the applications (the one written in Java and the one written in Python) look similar in their windowing displays. The reason for this is that we used SWT (instead of AWT/SWING) in our Java application. This provides an abstraction layer over the existing operating system-specific windowing system (GTK in case of Linux). If you run the application on Windows, the look and feel would be similar to that of a Windows application.

To gain an understanding of the application flow, here is an activity diagram:


Figure 7. SWT application activity diagram
SWT application activity diagram

The sequence of events for the SWT application is similar to (but a little simpler than) the sequence for the GTK application:

  1. The user launches the application.
  2. The application opens the Domino Directory and retrieves data from the People view.
  3. The application displays the view information to the user (Figure 5).
  4. The user clicks a listed name to display information about that particular user.
  5. The application retrieves the person information from the Person document in the Domino Directory.
  6. The application displays the person information to the user (Figure 6).

Figure 8 shows how the main components of the SWT application fit together:


Figure 8. SWT application components
SWT application components

SWT application code

Now let's look at some of the key pieces of Java source code for the SWT application. Notice that the overall application is somewhat simpler than the GTK application in that it doesn't require a special agent to be added to the Domino Directory. (You can download the complete code for the SWT application from the Sandbox.)

To start, SWT uses shell and display to initialize and draw the windows:

Display disp = new Display();
shell = new Shell(disp);
shell.setText("NAB Viewer by SWT");

After you have the display and shell initialized, you can add any number of existing objects such as menu bars, tables, buttons, grids, and so on. In this case, the program adds one table with five columns and two buttons.

Initializations of the Domino-related session, database, and view objects happen prior to populating the table with data read from the Domino Directory. In the sample application, we used ViewEntryCollection to loop through and populate the table columns based on the document fields (for instance, firstname and shortname):

vec = v.getAllEntries();
	for (int i=1; i<=vec.getCount();i++){
		TableItem item = new TableItem(table,SWT.NULL);
		doc = vec.getNthEntry(i).getDocument();
		item.setText(0,doc.getItemValueString("firstname"));
		item.setText(1,doc.getItemValueString("lastname"));
		item.setText(2,doc.getItemValueString("jobtitle"));
		item.setText(3,doc.getItemValueString("department"));
		item.setText(4,doc.getItemValueString("shortname"));
	}

After the user selects an entry in the table and clicks the More Info button, the program uses the DispDialog form class to draw the document view of the selected entry. We enabled the button to respond to clicks by adding a listener:

	b2.addSelectionListener(new SelectionAdapter(){
	public void widgetSelected(SelectionEvent e) {
		...some action here...
	}
});

Here is how the window to display the Person document information is initialized, using the selected document passed as the key (using the setKey method):

Document doc1 = drawMain.this.vec.getNthEntry(selectn+1).getDocument();
DispDialog form = new DispDialog(drawMain.this.shell);
form.setKey(doc1);
form.show();

The DispDialog form then initializes the display with grid layouts:

GridLayout layout = new GridLayout();
layout.numColumns=2;
group.setLayout(layout);

...and adds labels and associated fields from the document:

new Label(group, SWT.SHADOW_OUT).setText("Notes DN");
firstName = new Text(group, SWT.COLOR_DARK_BLUE);
firstName.setText(doc1.getItemValueString("fullname"));

The preceding label snippet is repeated for all the fields to display.

The other addition to this form is a button to illustrate the Message Box feature:

MessageBox mb = new MessageBox(shell,SWT.OK|SWT.CANCEL|SWT.ICON_QUESTION);
mb.setText("Question---");
mb.setMessage("Do you really want to close?");
int reply = mb.open();
if (reply == SWT.OK){
	shell.dispose();	
}	

After clicking the Done button, the user is prompted with a dialog box asking whether or not to proceed.

This application is a simple illustration of the power of SWT and the associated widgets. You can use this core technology along with JFace to build an Eclipse plug-in and host it within the new Eclipse Rich Client Platform (RCP). This allows you to create a true client for the Domino server on Linux, Windows, or Mac OS.



Back to top


More to come!

With the introduction of IBM Lotus Workplace, it is evident that the message from IBM is full reliance on open standards and Open Source technologies. For example, release 2.0 of Lotus Workplace incorporates the following open standards:

  • HTTP
  • IIOP
  • POP3
  • SMTP
  • LDAP
  • IMAP
  • SIP
  • BEEP
  • SyncML
  • SOAP
  • WSDL
  • X.509
  • S/MIME

And here are some of the key Open Source projects available in Lotus Workplace:

  • Eclipse/SWT/JFace
  • Apache AXIS
  • Log4J
  • Tapestry
  • Sync4J

The preceding lists clearly demonstrate IBM's strong and ongoing commitment to better interoperability and scalability through open standards and Open Source projects.

In this article series, we introduced you to the Open Source projects and open standards that pertain to Domino 6. We then discussed how to leverage some of these Open Source projects and open standards to solve practical problems in your Domino environment. Our overall goal has been to show how you can expand your Domino 6 environment to work with other applications, using Open Source code and open standards as the "bridge."

We hope you found this article series helpful. Please let us know what you think, and feel free to suggest related topics you'd like to see us cover in the future.



Resources



About the author

Raj Balasubramanian is a Consulting IT Architect for IBM Software Services for Lotus (ISSL). He works on customer engagements delivering application and infrastructure related projects. His interests range from anything technical to history and physics. During his copious spare time, he enjoys talking about robots with his sons.




Rate this page


Please take a moment to complete this form to help us better serve you.



 


 


Not
useful
Extremely
useful
 


Share this....

digg Digg this story del.icio.us del.icio.us Slashdot Slashdot it!



Back to top