The prerequisite for receiving indications is at least one existing subscription on a CIMOM. It is out of the scope of this document to explain the creation of subscriptions. Please see the corresponding DMTF standards.
The delivery of indications reverses the roles of client and server. The CIMOM acts as HTTP client, the SBLIM CIM Client for Java as an HTTP server. The indication delivery is asynchronous and completely independent from an open client-to-CIMOM connection.
The following code snippet illustrates how to set up a simple indication listener.
/** * Starts a indication listener that dumps every received indication to System.out * @param port The TCP port to listen on * @param ssl Set true if you want to listen on a secure (SSL) socket * @return The indication listener instance. Call removeLister() to stop the listener. */ private WBEMListener startIndicationListener(int pPort, boolean pSsl) throws IOException { try { WBEMListener listener = WBEMListenerFactory.getListener(WBEMClientConstants.PROTOCOL_CIMXML); listener.addListener(new IndicationListener() { public void indicationOccured(String pIndicationURL, CIMInstance pIndication) { System.out.println("Indication received on: " + pIndicationURL + ":"); System.out.println(pIndication.toString()); } }, pPort, pSsl ? "https" : "http"); return listener; } catch (IOException e) { System.err.println("Failed to bind socket to port "+pPort); throw e; } }
This sample will listen for indications on the given socket. Every indication received
is dispatched to the single registered CIMListener
that prints the event
details to stdout
. In a real world application you would replace the
System.out.println()
with your indication processing code.
In order to stop listening and free the socket just call removeListener(int pPort)
.
The WBEMListener
is a singleton that keeps a map of socket listeners keyed by port. On
multi-homed systems it is possible to bind the listener to a given IP only. The WBEMListenerSBLIM
class offers an additional signature of addListener()
that allows you to pass individual configuration
properties.
When you start an indication listener you start a little HTTP server. This server has to fulfill the usual duties: wait for incoming connections, handle them (also concurrently), parse the request, send a response, create a CIM indication and forward it to the corresponding indication listener from your application.
These duties are handled by four layers, each of which runs in one or more separate threads (compare with picture).
When you subscribe on multiple CIMOMs you have to be able to distinguish which CIMOM is the origin of a particular indication. This is not as easy as it seems since an indication doesn't have sender information. Therefore the common way is to make the destination unique in the subscription. This can be done by either using an individual port per subscription or by using an individual local path per subscription. The first option creates more overhead in the client since we have to start a separate HTTP server for each port. Therefore we recommend using the second option.
We have five configuration options that allow you to fine tune the indication listener. All of them are coupled together and a wrong setting might harm your ability to receive indications.
HTTP timeout | minimum pool size | maximum pool size | backlog | idle timeout | remarks |
---|---|---|---|---|---|
10s | 2 | 8 | 2 | 30s | Default setting. Will keep number of handlers low & stable. Aggressive HTTP timeout and two handlers always open will keep vulnerability low. |
60s | 0 | 8 | 0 | 10s | More dynamic handler allocation. Will destroy all handlers fast when idling and create them without delay on traffic. Allows higher HTTP timeout. |
60s | 0 | 8 | 0 | 120s | Similar to default but keeps handler count stable by long idle timeout instead of backlog. Makes it less vulnerable against blocking, but keeps handler open long after traffic peeks. Needs on average more handlers than default. |
10s | 0 | 2 | 0 | 10s | Resource saving: maximum of two handlers, aggressive HTTP timeout, short idle timeout. Will keep number of handlers low but is heavily creating & destroying its handlers. |
Reliable indication support, as defined by DMTF Indications Profile [DSP1054], is included in the SBLIM CIM Client for Java beginning with version 2.1.9. The gist of reliable indication support is for indications to be delivered to the listener in the order intended by the CIMOM, NOT the order which they arrive at the Client. In other words, if the CIMOM sends indications [#4,#5,#6] but network issues cause them to arrive at the Client as [#5,#6,#4], the Client will deliver them to the listener as [#4,#5,#6].
When reliable indication support is enabled (the default is disabled), the Client is responsible for determining when to dispatch reliable indications, which includes queuing unexpected indications in either a hash table or linked list, caching all indications for the duration of their sequence identifier lifetime, and logging missing, duplicate and out-of-order indications.
A reliable indication must contain both the SequenceContext and SequenceNumber properties, the latter of which is used to deliver indications to the listener in order of increasing value. The sequence identifier lifetime is defined as:
DeliveryRetryAttempts * DeliveryRetryInterval * 10
There are four configuration options that allow you to control reliable indication handling:
The following code snippet illustrates how to set up a simple indication listener with reliable indication support enabled.
/** * Starts a indication listener that dumps every received indication to System.out * @param port The TCP port to listen on * @param ssl Set true if you want to listen on a secure (SSL) socket * @return The indication listener instance. Call removeLister() to stop the listener. */ private WBEMListener startIndicationListener(int pPort, boolean pSsl) throws IOException { try { WBEMListener listener = WBEMListenerFactory.getListener(WBEMClientConstants.PROTOCOL_CIMXML); // Cast WBEMListener to WBEMListenerSBLIM to get access to the addListener() method that // accepts properties - this method is not part of the JSR48 standard, but is a SBLIM addition WBEMListenerSBLIM SBLIMlistener = (WBEMListenerSBLIM) listener; // Enable reliable indications using 2 retries at intervals of 30 seconds Properties props = new Properties(); props.setProperty("sblim.wbem.listenerEnableReliableIndications", "true"); props.setProperty("sblim.wbem.listenerDeliveryRetryAttempts", "2"); props.setProperty("sblim.wbem.listenerDeliveryRetryInterval", "30"); SBLIMlistener.addListener(new IndicationListener() { public void indicationOccured(String pIndicationURL, CIMInstance pIndication) { System.out.println("Indication received on: " + pIndicationURL + ":"); System.out.println(pIndication.toString()); } }, pPort, pSsl ? "https" : "http", null, props); return listener; } catch (IOException e) { System.err.println("Failed to bind socket to port "+pPort); throw e; } }
The properties can also be set in the properties file itself, in which case the code would be identical to the first snippet above. However, that would enable reliable indication support and set the attempts/interval for all listeners whereas this code snippet enables support and sets the attempts/interval for this particular listener only.
NOTE:If reliable indication support is enabled but the CIMOM does not send reliable indications (required properties missing), the indications are passed directly to the listener.