From 43a2355b95ee89d8866d8532ffbc650c911b8a39 Mon Sep 17 00:00:00 2001
From: Mark Craig <mark.craig@forgerock.com>
Date: Wed, 12 Aug 2015 12:06:11 +0000
Subject: [PATCH] CR-7880 OPENDJ-1608 Provide asynchronous examples
---
docs/src/main/docbkx/dev-guide/chap-using-the-sdk.xml | 217 ++++++++++++++++++++++++++++++++++++++---------------
1 files changed, 155 insertions(+), 62 deletions(-)
diff --git a/docs/src/main/docbkx/dev-guide/chap-using-the-sdk.xml b/docs/src/main/docbkx/dev-guide/chap-using-the-sdk.xml
index c2192b3..f6c7918 100644
--- a/docs/src/main/docbkx/dev-guide/chap-using-the-sdk.xml
+++ b/docs/src/main/docbkx/dev-guide/chap-using-the-sdk.xml
@@ -30,80 +30,173 @@
xmlns:xlink='http://www.w3.org/1999/xlink'>
<title>Using the LDAP SDK</title>
- <para>As LDAP relies on a connection from the client to the directory server,
- the starting point for working with the LDAP SDK is a new
- <literal>LDAPConnectionFactory</literal>, from which you then get either
- a synchronous connection, or pass in a handler to an asynchronous
- connection. You then use the connection to make requests and get responses
- from the directory server.</para>
+ <para>
+ As LDAP relies on a connection
+ from the client application to the directory server,
+ the starting point for working with the LDAP SDK is
+ a new <literal>LDAPConnectionFactory</literal>.
+ The connection factory allows an application to get a connection
+ either synchronously or asynchronously.
+ The application then uses the connection
+ to make requests and to get responses from the directory server.
+ </para>
<section xml:id="sync-vs-async">
- <title>Synchronous & Asynchronous Operations</title>
- <indexterm>
- <primary>Connections</primary>
- <secondary>Asynchronous</secondary>
- </indexterm>
- <indexterm>
- <primary>Connections</primary>
- <secondary>Synchronous</secondary>
- </indexterm>
+ <title>Synchronous vs. Asynchronous APIs</title>
- <para>For synchronous operations your application gets a connection from
- the <literal>LDAPConnectionFactory</literal> and requests operations on
- the connection. When finished, your application closes the connection.</para>
+ <para>
+ The LDAP SDK offers synchronous and asynchronous APIs.
+ The difference is that synchronous APIs
+ wait for each task to complete before starting the next task,
+ whereas asynchronous APIs
+ allow another task to start before the current one finishes.
+ </para>
- <programlisting language="java">
+ <section xml:id="sync-apis">
+ <title>Synchronous APIs</title>
+
+ <indexterm>
+ <primary>Connections</primary>
+ <secondary>Synchronous</secondary>
+ </indexterm>
+
+ <para>
+ For synchronous operations the application gets a connection
+ from a connection factory,
+ and then requests operations on the connection in sequence.
+ When finished, the application closes the connection
+ as shown in the following example:
+ </para>
+
+ <programlisting language="java">
[jcp:org.forgerock.opendj.examples.Search:--- JCite ---]
- </programlisting>
+ </programlisting>
- <para>
- For a complete example in context, see
- <link
- xlink:href="../resources/org/forgerock/opendj/examples/Search.java"
- xlink:show="new"
- >Search.java</link>.
- </para>
+ <para>
+ For the complete example in context, see
+ <link
+ xlink:href="../resources/org/forgerock/opendj/examples/Search.java"
+ xlink:show="new"
+ >Search.java</link>.
+ </para>
+ </section>
- <para>
- For asynchronous operations,
- your application obtains a connection with
- <literal>LDAPConnectionFactory.getConnectionAsync()</literal>,
- and then uses promises to handle the bind, the subsequent operations,
- the results, and any errors in asynchronous fashion.
- </para>
+ <section xml:id="async-apis">
+ <title>Asynchronous APIs</title>
- <programlisting language="java">
+ <indexterm>
+ <primary>Connections</primary>
+ <secondary>Asynchronous</secondary>
+ </indexterm>
+
+ <para>
+ Asynchronous code can be tricky to read and to write.
+ To make coding easier,
+ the asynchronous APIs use <firstterm>promises</firstterm>.
+ Promises might be familiar to JavaScript developers.
+ A promise is the result of a task that might or might not be complete.
+ Fluent code style, which strings together chains of methods,
+ works well with promises.
+ </para>
+
+ <para>
+ The following code outline chains asynchronous calls together:
+ </para>
+
+ <programlisting language="java"><![CDATA[
+class AsyncApp {
+ private Connection connection;
+
+ public void myMethod(String host, int port) {
+ // Get a connection to the directory asynchronously,
+ // returning a promise (with the connection if all goes well).
+ new LDAPConnectionFactory(host, port)
+ .getConnectionAsync()
+
+ // Bind asynchronously, returning a promise with the bind result.
+ // Notice the connection is consumed, the bind result produced.
+ .thenAsync(new AsyncFunction<Connection, BindResult, LdapException>() {
+ @Override
+ public Promise<BindResult, LdapException> apply(Connection connection)
+ throws LdapException {
+ SearchAsync.connection = connection;
+ return AsyncApp.bindAsync(
+ Requests.newSimpleBindRequest(bindDn, password));
+ }
+ })
+
+ // When the bind completes, perform an LDAP operation,
+ // returning a promise with the result of the operation.
+ // Here the bind result is consumed, and the next result produced.
+ .thenAsync(new AsyncFunction<BindResult, Result, LdapException>() {
+ @Override
+ public Promise<Result, LdapException> apply(BindResult bindResult)
+ throws LdapException {
+ // Return a promise from an asynchronous method.
+ // return connection.***Async(...);
+ }
+ })
+ // An application might chain several more calls together.
+ // .thenAsync(new AsyncFunction<Result, Result, LdapException>() {...
+ // .thenAsync(new AsyncFunction<Result, Result, LdapException>() {...
+ // ...
+
+ // Handle the result, if any.
+ .thenOnResult(new ResultHandler<Result>() {
+ @Override
+ public void handleResult(Result result) {
+ // Handle the result.
+ }
+ })
+
+ // Handle any exceptions that arise.
+ .thenOnException(new ExceptionHandler<LdapException>() {
+ @Override
+ public void handleException(LdapException e) {
+ // Handle exceptions.
+ }
+ });
+
+ closeSilently(connection);
+ return;
+ }
+}
+ ]]></programlisting>
+
+ <para>
+ The following example demonstrates a search using the asynchronous APIs:
+ </para>
+
+ <programlisting language="java">
[jcp:org.forgerock.opendj.examples.SearchAsync:--- Using Promises ---]
- </programlisting>
+ </programlisting>
- <para>
- When the factory gets a connection,
- your application passes an <literal>AsyncFunction</literal>
- to apply to the connection to handle the bind
- by using the <literal>thenAsync()</literal> method in the fluent style.
- Your application uses <literal>thenAsync()</literal> again
- to pass another <literal>AsyncFunction</literal> to perform the operation.
- In the sample shown here, the second call to <literal>thenAsync()</literal>
- passes a function that performs a search, passing in a handler
- to deal with the search results returned by the directory server.
- The call to <literal>onSuccess()</literal> handles the final result,
- with the call to <literal>onFailure()</literal> dealing with exceptions.
- </para>
+ <para>
+ When the factory gets a connection,
+ the application passes an <literal>AsyncFunction</literal>
+ to apply to the connection to handle the bind
+ by using the <literal>thenAsync()</literal> method in the fluent style.
+ The application uses <literal>thenAsync()</literal> again
+ to pass another <literal>AsyncFunction</literal> to perform the operation.
+ In the sample shown here, the second call to <literal>thenAsync()</literal>
+ passes a function that performs a search,
+ using a handler to deal with the search results returned by the server.
+ The call to <literal>thenOnResult()</literal> handles the final result,
+ with the call to <literal>thenOnException()</literal> dealing with exceptions.
+ </para>
- <para>
- Asynchronous methods are non-blocking, returning a <literal>Promise</literal>,
- so that you can chain methods in the fluent style.
- Your application must coordinate concurrency
- when you use asynchronous operations.
- </para>
+ <para>
+ The application must coordinate concurrency when using asynchronous APIs.
+ </para>
- <para>
- For a complete example in context, see
- <link
- xlink:href="../resources/org/forgerock/opendj/examples/SearchAsync.java"
- xlink:show="new"
- >SearchAsync.java</link>.
- </para>
+ <para>
+ For the complete example in context, see
+ <link
+ xlink:href="../resources/org/forgerock/opendj/examples/SearchAsync.java"
+ xlink:show="new"
+ >SearchAsync.java</link>.
+ </para>
+ </section>
</section>
<section xml:id="error-handling">
--
Gitblit v1.10.0