Using NoSQLPublisherConfig

Use oracle.kv.pubsub.NoSQLPublisherConfig to specify connection and authentication information to the store. You can also use this class to configure performance parameters.

Configuring a Connection to the Store

When you construct a NoSQLPublisherConfig object, you provide it with an oracle.kv.KVStoreConfig object. This object is used to provide store connection information:

  • The name of the store that your publisher is monitoring

  • A list of one or more helper host port pairs. These helper hosts are Storage Nodes in the store. They must be resolvable using either DNS or the local /etc/hosts file.

For example:

package pubsub;

import oracle.kv.KVStore;
import oracle.kv.KVStoreConfig;
import oracle.kv.KVStoreFactory;

...

String[] hhosts = {"n1.example.org:5088", "n2.example.org:4129"};
KVStoreConfig kconfig = new KVStoreConfig("exampleStore", hhosts); 

This simple example is sufficient to connect to a store that is not configured for authentication. For information about connecting to a secure store, see Authenticating to a Secure Store.

Creating a Basic NoSQLPublisherConfig Object

You use NoSQLPublisherConfig.Builder to construct a NoSQLPublisherConfig object. The constructor for this class requires you to provide a KVStoreConfig object, as well as a path to the publisher's root directory (this directory is used to contain files necessary for the publisher's proper operation).

...

// Create a minimal KVStoreConfig
String[] hhosts = {"n1.example.org:5088", "n2.example.org:4129"};
KVStoreConfig kconfig = new KVStoreConfig("exampleStore", hhosts);

final NoSQLPublisherConfig publisherConfig =
    new NoSQLPublisherConfig.Builder(kconfig, "/export/publisher")
    .build(); 

Once you have created the NoSQLPublisherConfig object, you can use it in a call to the NoSQLPublisher.get() method to obtain a NoSQLPublisher instance and connect to the store. See, Authenticating to a Secure Store for an example of this.

Tuning Your Publisher

When you construct a NoSQLPublisherConfig object, you can specify several tuning controls:

  • Maximum concurrent subscriptions

    Specifies the maximum number of subscribers that this publisher can run. This must be set to at least 1.

    Use NoSQLPublisherConfig.setMaxConcurrentSubs() to configure this value. Default is 32.

  • A shard timeout value. If the publisher does not hear from a source shard in the amount of time specified here, the publisher will throw ShardTimeoutException via a call to NoSQLSubscriber.onWarn. If a ShardTimeoutException is thrown, the stream and the connection to the shard still remain alive, just that there is no operation received from that shard within the timeout period.

    Use NoSQLPublisher.setShardTimeoutMs() to configure this value. This method takes a long that represents the timeout value in milliseconds. Default is 600000 ms (10 minutes).

For example:

...

// Create a minimal KVStoreConfig
String[] hhosts = {"n1.example.org:5088", "n2.example.org:4129"};
KVStoreConfig kconfig = new KVStoreConfig("exampleStore", hhosts);

final NoSQLPublisherConfig publisherConfig =
    new NoSQLPublisherConfig.Builder(kconfig, "/export/publisher")
    .setMaxConcurrentSubs(2)
    .setShardTimeoutMs(10000)
    .build(); 

Authenticating to a Secure Store

To authenticate to a secure store, you must provide login credentials. The simplest way to connect your stream processing application to secure store is by specifying a value for the oracle.kv.security system property, which incudes the pathname of a file containing the security property settings generated while setting up a user login for a secure store. For more information about setting up a secure store to generate the security property file, see Performing a Secure Oracle NoSQL Database Installation in the Security Guide.

Note that if you choose to follow the method above, you do not need to modify your application code. To run the example to connect to secure store, use the command below:

java -Doracle.kv.security=mylogin 
-cp $KVHOME/lib/kvstore.jar:. pubsub.NoSQLStreamExample

Reauthentication

Once the publisher has created an initial authenticated connection to the store, the authentication credentials are lost; they are not kept in memory or in any way cached.

After the initial connection, every subscription also has to be authenticated. This authentication process ensures that the subscriber has the appropriate read access to the table(s) for which a subscription is being obtained. If the user is attempting to subscribe to a single table or a small set of tables, she needs READ_TABLE access for each table. If the user wants to subscribe to any table in the store, then for convenience that user account can be configured with READ_ANY_TABLE access.

To allow subscriptions to authenticate, you implement a ReauthenticationHandler class and then provide it to your NoSQLPublisherConfig object using the NoSQLPublisherConfig.setReauthHandler() method.

The following example extends the authentication example shown in the previous section to add a reauthentication handler.

First, you must implement ReauthenticationHandler. The following is an example of a very simple implementation:

package pubsub;

import oracle.kv.ReauthenticationHandler;
import oracle.kv.PasswordCredentials;

public class MyReauthHandler implements ReauthenticationHandler {
    public void reauthenticate(KVStore reauthStore) {

    // The code you use to obtain the username and password strings
    // should be consistent with the code you use to perform
    // simple authentication for your publisher. Here we do
    // the simplest -- and least secure -- thing possible.

    // This is really not what you should do for production 
    // code.

    final String username = "beth";
    final String password = "my_clever_password00A";

    PasswordCredentials cred = new PasswordCredentials(username,
    password.toCharArray());

    reauthStore.login(cred); 

We then extend the previous authentication example to use our implemented ReauthenticationHandler. We do this with a single line of code, which is in bold in the example.

package pubsub;

...

// Create a KVStoreConfig object that is configured
// for a secure store.
String[] hhosts = {"n1.example.org:5088", "n2.example.org:4129"};
KVStoreConfig kconfig = new KVStoreConfig("exampleStore", hhosts);

// Need to set some required security properties.
Properties secProps = new Properties();
secProps.setProperty(KVSecurityConstants.TRANSPORT_PROPERTY,
                     KVSecurityConstants.SSL_TRANSPORT_NAME);

// The client.trust file is created when you install your 
// store. It must be moved locally to every machine where
// client code will run.
secProps.setProperty
	(KVSecurityConstants.SSL_TRUSTSTORE_FILE_PROPERTY,
	"/home/kv/client.trust");
kconfig.setSecurityProperties(secProps);

// Create a PasswordCredentials instance. We hard-code
// the credentials here, but in a production environment
// this information should be provided in a significantly
// more secure way.

// username and password must have been configured for the store
// by its administrator.

final String username = "beth";
final String password = "my_clever_password00A";

PasswordCredentials pc = 
    new PasswordCredentials(username,
                            password.toCharArray());

// Create the publisher's configuration object.
// Keeping it simple.
final NoSQLPublisherConfig publisherConfig =
    new NoSQLPublisherConfig.Builder(kconfig, "/export/publisher")
 .setReauthHandler(new MyReauthHandler())
    .build(); 

// Now connect to the store
try {
    NoSQLPublisher publisher =
        NoSQLPublisher.get(publisherConfig, pc);
} catch (PublisherFailureException pfe) {
        System.out.println("Connection or authentication failed.");
        System.out.println(pfe.toString());
}