[ Implementation | Development | Conclusion ]
The Client API
This section shows how you can access Nabu from your application. To make use of Nabu in your application, you need a Jabber client library to connect to Nabu, and an RDF parser to parse replies.
For Java, the Nabu project has a simple API you can use to listen to chat events for user observation and to communicate with the Nabu server via requests. The API encapsulates both the connection handling and the encoding/parsing of request and responses. The API does not include an RDF parser to avoid dependencies to a specific RDF implementation. To parse the RDF , you can use the Jena framework (it will be used in the examples below).
Installation
To use the client API in your Java application, download nabu-clientAPI-0.1.zip, unpack it and add the contained JAR files (nabu-client.jar, nabu-remote.jar, smack.jar, smackx.jar) to your classpath.
If you build from source, go to the nabuclient/ directory and run
ant nabuclient_jar
After build, you can find the JAR files in nabuclient/target/lib. Add them to your classpath.
Connect to the server
The following code snippet shows how to connect to the server:
import de.dfki.km.xmpp.nabu.observer.Client; import de.dfki.km.xmpp.nabu.observer.impl.ClientImpl; // [...] String USER = "alice"; // the user name (node part of the Jabber ID) String RESOURCE = "nabu"; // the resource to be used, can be any // resource that is not in use e.g. by // your graphical client String PASS = "topsecret"; // the jabber password of alice String HOST = "foo.jabber.org"; // the server, int PORT = 5222; // the port, usually 5222 for unsecured //connections and 5223 for SSL String BOT = "nabubot@nabu.foo.jabber.org"; // the JID of the nabu bot, // as listed in the contact list Client client = new ClientImpl(); // for a SSL connection, use // "new ClientSSLImpl()" (note that the port // will change too, e.g. to 5223) try { client.login(USER, RESOURCE, PASS, HOST, PORT); } catch (Exception e) {} client.setBot(BOT); // here you can send requests, start observation etc. (see below) // [...]
User Observation
To use user observation, implement the Listener interface:
import de.dfki.km.xmpp.nabu.observer.Listener; public class MyListener implements Listener { public void receiveObservationNotification(String uri, String cbd) { System.out.println("Received message with URI " + uri); System.out.println("Description in RDF:"); System.out.println(cbd); // Act on notification } public void receiveResponse(Response response) { System.out.println("A new response arrived! Response code: " + response.getCode()); } }
Create an listener instance and register it at the client and start the observation:
client.setBot(BOT); client.addListener(new MyListener()); // adds the listener client.startObservation(); // starts the observation
Now observation is activated and every received notification is passed to !MyListener::receiveObservationNotification().
To stop the observation, call client.stopObservation();
Sending Requests
The client API also offers a convenient way to send request to Nabu and to receive responses without building request strings and parsing responses. To send a request, simply create a request object and pass it to the client. Let's send the annotation example from the handbook via the API.
CREATESTATEMENT RESOURCE http://foo/Messages/someMessage http://purl.org/dc/terms/subject http://foo/Categories/Projects/Nabu
becomes:
int type = CreateStatementRequest.ObjectType.Resource; String subject = "http://foo/Messages/someMessage"; String predicate = "http://purl.org/dc/terms/subject"; String object = "http://foo/Categories/Projects/Nabu"; CreateStatementRequest req = new CreateStatementRequest(null, type, subject, predicate, object); client.sendRequest(req);
To handle responses, reimplement receiveResponse() from the Listener interface. To handle the different sub classes, you might also implement the ResponseVisitor interface:
public class MyListener implements Listener, ResponseVisitor { public void receiveResponse(Response response) { visit(response); } public void visitMessageLoggingStatusResponse(MessageLoggingStatusResponse response) { System.out.println("message logging is " + (response.getStatus() ? " enabled " : "disabled") ); } public void visitQueryResultResponse(QueryResultResponse response); { Model m = ModelMaker.createDefaultModel(); // create a Jena Model of // the RDF m.read(new StringReader(response.getResult(), null); // do something with the model } // ... }
By implementing the visitX class for every response type X, you can handle all the response types you are interested in. For instance, the visitQueryResultResponse() implementation in the example uses Jena to parse the RDF sent in the response.
[ Implementation | Development | Conclusion ]