Using the WebSphere MQ messaging provider in WebSphere Application Server V7, Part 2: Using channel exits

A channel exit is user code that is run at defined points in the life cycle of an IBM® WebSphere® MQ channel. There are many potential uses for channel exits, including auditing, security, compression, conversion, among others. Prior to WebSphere Application Server V7, channel exits were not fully supported, but now channel exits can be configured on both connection factories and activation specifications. This article describes the types of channel exits, their usage restrictions, and how they can be enabled in application server and application client environments. This content is part of the IBM WebSphere Developer Technical Journal.

Matthew Leming (lemingma@uk.ibm.com), WebSphere Messaging Development, IBM

Matthew Leming joined IBM in 2002. He has worked on various areas of WebSphere Application Server beginning with Version 5, including the transactions component and the default messaging provider. More recently he was responsible for co-developing the WebSphere MQ messaging provider with Adrian Preston.



Graham Hopkins (GHOPKIN@uk.ibm.com), Lead Tester, IBM

Graham Hopkins joined IBM in 2000. He has worked with WebSphere MQ and the default messaging provider within WebSphere application Server and is currently the lead tester for interaction between WebSphere Application Server and WebSphere MQ.



24 June 2009

Also available in Chinese Japanese

Introduction

The IBM WebSphere MQ messaging provider in IBM WebSphere Application Server V7 provides full support for Java™-based channel exits. A channel exit is user code that is run at defined points in the life cycle of a WebSphere MQ channel. There are many potential uses for channel exits, including auditing, security, compression, conversion, and more.

In prior versions of WebSphere Application Server, channel exits were not fully supported and had to be configured by custom properties. In WebSphere Application Server V7, channel exits can be configured on both connection factories and activation specifications using either the administrative console, administrative commands, or by specifying them in a client channel definition table (CCDT) entry.


Types of channel exit

The WebSphere MQ messaging provider supports three different types of channel exits: security, send, and receive exits. Each exit type is invoked at different points in the lifecycle of a client connection channel, as described in Table 1.

Table 1. Channel exit invocation times
Exit typeWhen constructor is called
Security exit
  • At channel initialization time.
  • If a security flow is received from a security exit installed on the server connection channel.
Send exit
  • At channel initialization time.
  • Prior to any data being sent to the queue manager.
Receive exit
  • At channel initialization time.
  • After data has been received from the queue manager, and prior to that data being passed to the application.

Send and receive exits support chaining; that is, more than one send or receive exit can be specified on a WebSphere MQ messaging provider resource. If chaining is used, the first exit in the chain is called and the data it returns is passed on to the next exit in the chain. This continues until all the exits have been invoked and the data is then sent to the queue manager or client, as appropriate.

As mentioned above, security exits installed on a WebSphere MQ messaging provider resource are only invoked if a security exit on the appropriate server connection channel sends a security flow. As security exits are only invoked at channel startup time, security exits are ideal for performing functions that only need to be done once. As the name suggests, this typically means performing authentication. Figure 1 shows a security exit being invoked at channel start up.

Figure 1. Security exit invocation
Figure 1. Security exit invocation

Sender and receiver channel exits are invoked prior to data being sent to, or received from a queue manager, respectively. Typical uses of these exit types might include performing accounting of the amount of data sent or received, or some form of data transformation, such as compression. If necessary, complementary send and receive exits can be installed at either end of the channel. For example, if exits were used to perform compression, a send exit would be needed at both ends of the channel to perform data compression, and receive exits would be needed at both ends to perform decompression. An example of this is shown in Figure 2.

Figure 2. Complementary send and receive exits
Figure 2. Complementary send and receive exits

See Resources for more information about when and where channel exits are invoked.


Channel exit usage restrictions

There are some restrictions with using channel exits with the WebSphere MQ messaging provider that you should be aware of:

  • In order to make use of a channel exit, a WebSphere MQ messaging provider connection factory or activation specification must have a transport type of either client or bindings-then-client. This is because channel exit programmes can only be used when connecting to a WebSphere MQ queue manager or queue sharing group that uses a client-connection channel based connection. If the bindings-then-client transport mode is chosen, channel exits will only be driven if the bindings mode connection fails.
  • WebSphere MQ supports channel exits written in a variety of different programming languages in addition to Java, including C and C++. However, the WebSphere MQ messaging provider only supports Java-based channel exits, and so C and C++ channel exits cannot be used.
  • WebSphere MQ messaging provider resources that make use of channel exits load the channel exit classes based on the class path of the application that first uses the resource. Be sure to follow the WebSphere MQ documentation about specifying from where to load channel exit resources unless otherwise recommended by IBM. Class loading consideration for channel exits with the WebSphere MQ messaging provider is covered in a later section in this article.

Writing a simple channel exit

Creating a channel exit for use with the WebSphere MQ messaging provider requires implementing one or more of the Java channel exit interfaces. There are two sets of interfaces: one was introduced for WebSphere MQ V7 to provide enhanced performance and functionality, and the other has been available since WebSphere MQ V5. Either set can be used with the WebSphere MQ messaging provider, but the examples used in this article will use the new interfaces exclusively.

Regardless of which set of interfaces are used, they all follow the same pattern. One interface is provided for each type of channel exit, and each interface provides a single method to be implemented. The interface and method signatures are shown in Table 2.

Table 2. Channel exit interface definitions
Interface typeInterface nameInterface method
New Send exitcom.ibm.mq.exits.WMQSendExitpublic ByteBuffer channelSendExit(MQCXP channelExitParms, MQCD channelDefinition, ByteBuffer agentBuffer)
New Receive exitcom.ibm.mq.exits.WMQReceiveExitpublic ByteBuffer channelSendExit(MQCXP channelExitParms, MQCD channelDefinition, ByteBuffer agentBuffer)
New Security exitcom.ibm.mq.exits.WMQSecurityExitpublic ByteBuffer channelReceiveExit( MQCXP channelExitParms, MQCD channelDefinition, ByteBuffer agentB
Old Send exitcom.ibm.mq.MQSendExitpublic byte[] sendExit(MQChannelExit channelExitParms, MQChannelDefinition channelDefinition, byte[] agentBuffer)
Old Receive exitcom.ibm.mq.MQReceiveExitpublic byte[] receiveExit(MQChannelExit channelExitParms, MQChannelDefinition channelDefinition, byte[] agentBuffer)
Old Security exitcom.ibm.mq.MQSecurityExitpublic byte[] securityExit(MQChannelExit channelExitParms, MQChannelDefinition channelDefinition, byte[] agentBuffer)

If you are using the new style exits, a copy of com.ibm.mq.jmqi.jar will be needed when writing and compiling channel exits, If you are using the older style exits, then you will need a copy of com.ibm.mq.jar. These jars can be obtained from either the <WAS_INSTALL_ROOT>/lib/WMQ/ra/ directory, or from a WebSphere MQ installation.

The simplest form of each exit uses the exit interface method to return the agentBuffer parameter that is passed in. The class shown in Listing 1 provides the most basic implementation of all three exit types. This is the example that shall be referred to for the remainder of this article.

Listing 1
package com.ibm.ce;

<IMPORTS REMOVED>

/**
 * A simple channel exit that provides an implementation of a send,
 * receive and security exit.
 */
public class LoggingChannelExit implements WMQSendExit, WMQReceiveExit, WMQSecurityExit
{
     /**
      * Send exit implementation.
      */
     public ByteBuffer channelSendExit(MQCXP channelExitParms, 
						MQCD channelDefinition,   
						ByteBuffer agentBuffer) 
     {
         System.out.println("Send Exit Invoked");
         return agentBuffer;
      }

      /**
       * Receive exit implementation.
       */
      public ByteBuffer channelReceiveExit(MQCXP channelExitParms, 
						MQCD channelDefinition, 
						ByteBuffer agentBuffer) 
      {
          System.out.println("Receive Exit Invoked");
          return agentBuffer;
      }

      /**
       * Security exit implementation.
       */
      public ByteBuffer channelSecurityExit(MQCXP channelExitParms, 
						MQCD channelDefinition, 
						ByteBuffer agentBuffer) 
      {
          System.out.println("Security Exit Invoked");
          return agentBuffer;
      }
}

When creating and installing channel exits, each defined exit can pass in up to 32 characters of data that can be used for configuration purposes. In the new style interfaces, this data can be accessed by the MQCXP.getUserData() method, which returns a string. The next section shows how this exit data can be set.


Configuring channel exits on WebSphere messaging provider resources

The steps used to specify which channel exits run on a particular WebSphere MQ messaging provider resource depend on whether or not that resource is based off the information in a CCDT. If the resource is based off a CCDT, channel exit information is specified at CCDT creation time. Figure 3 shows how to use the WebSphere MQ Explorer tool to add the simple channel exit programme defined above to a client connection channel definition. (Some user data has been specified here, but in this example the channel exit implementation won’t make use of it.)

Figure 3. Configuring a channel exit on a CCDT
Figure 3. Configuring a channel exit on a CCDT

If you are adding a channel exit to a non-CCDT-defined WebSphere MQ messaging provider resource, then you can use either the administrative console or the wsadmin command line tool.

If you use the administrative console:

  1. Log into the administrative console and navigate to the relevant non-CCDT based WebSphere MQ messaging provider activation specification or connection factory.
  2. As indicated in Figure 4, click on the Client transport properties link on the right side of the panel under Additional properties.
    Figure 4. Client transport properties
    Figure 4. Client transport properties
  3. In the relevant channel exit field, enter the full name of the channel exit class, including its package. In this example, enter com.ibm.ce.LoggingChannelExit. If more that one send or receive exits are required, then enter their names separated by a comma.
  4. Enter any user data in the relevant user data field. If multiple channel exits are defined, you can define multiple sets of user data, separated by a comma. If you define more channel exits than user data, the user data for the remaining channel exits will be a blank string. Similarly, if a double comma is entered as user data, then the channel exit at that position in the list will get user data consisting of a blank String.
  5. Click OK and save the changes.

Using channel exit enabled resources in the application server environment

When writing enterprise applications that use WebSphere MQ messaging provider resources that are configured to use channel exits, you must take care to ensure that the channel exit implementations can be loaded by the messaging provider. This section explains how to achieve this in the application server environment, and the next section explains how to make channel exit implementation classes available in the application client environment.

If an instance of a WebSphere MQ messaging provider activation specification or connection factory has been configured with a channel exit, the messaging provider will attempt to load the channel exit implementation class using reflection when the activation specification or connection factory is created. In order for this to work, the channel exit implementation class must be available to the class loaders used by the WebSphere MQ messaging provider runtime. There are three ways you can accomplish this:

  • The simplest approach is to make the channel exit classes available for loading by the entire application server runtime, which is possible by adding the classes to the application server class path. However, this approach is not recommended because it can cause confusion about where the actual classes are being loaded from, especially if multiple versions of the same class are being used inside a single application server.
  • Alternatively, each application can be deployed with a copy of the channel exit classes bundled inside it, either in the form of a JAR file, or as one or more class files. This approach is reasonable if only one application will ever use a WebSphere MQ messaging provider connection factory or activation specification that has been configured with a channel exit. However, in most cases -- and particularly if channel exits are widely used -- this approach is undesirable because it increases the size of the application and makes channel exit implementation upgrades time consuming and error prone.
  • The third and preferable approach is to provide channel exit implementations as shared libraries and make them accessible to the applications that need them. This approach means that application developers don’t need to be aware of channel exit use, plus it prevents class path bloat and provides a simple upgrade strategy if the channel exit implementation changes. There are a few ways to use shared libraries in WebSphere Application Server: you can use shared library references, or you can use the new asset support introduced in WebSphere Application Server V7.

When an enterprise application uses a WebSphere MQ messaging provider resource that has been configured to use channel exits, but the channel exit implementation is not available on the application class path, an MQException with an error code of 2406 will result. Listing 2 shows an example of this condition occurring. In the listing, an application attempts to make use of a WebSphere MQ messaging provider connection factory that has been configured to use the LoggingChannelExit class as a send exit. When running in an application server environment, these exceptions will typically be contained in one or more First Failure Data Capture (FFDC) records.

Listing 2
com.ibm.mq.MQException: JMSCMQ0001: WebSphere MQ call failed with compcode '2' 
	('MQCC_FAILED') reason '2406' ('MQRC_CLIENT_EXIT_LOAD_ERROR').
	at com.ibm.msg.client.wmq.common.internal.Reason.createException(Reason.java:206)
	... 30 more
Caused by: com.ibm.mq.jmqi.JmqiException: CC=2;RC=2406;AMQ9535: User exit not valid. 
	[1=com.ibm.ce.LoggingChannelExit]
	at com.ibm.mq.jmqi.remote.internal.RemoteExitChain.loadJavaExitByName
(RemoteExitChain.java:1858)
	at com.ibm.mq.jmqi.remote.internal.RemoteExitChain.loadByName
(RemoteExitChain.java:1816)
	at com.ibm.mq.jmqi.remote.internal.RemoteExitChain.parseSendReceiveExitsChain
(RemoteExitChain.java:1655)
	at com.ibm.mq.jmqi.remote.internal.RemoteExitChain.loadExits
(RemoteExitChain.java:824)
	at com.ibm.mq.jmqi.remote.internal.RemoteHconn.initSendReceiveExits
(RemoteHconn.java:683)
	at com.ibm.mq.jmqi.remote.internal.system.RemoteConnectionPool.getConnection
(RemoteConnectionPool.java:295)
	at com.ibm.mq.jmqi.remote.internal.RemoteFAP.jmqiConnect(RemoteFAP.java:1371)
	at com.ibm.msg.client.wmq.internal.WMQConnection.<init>(WMQConnection.java:331)
				... 29 more
Caused by: java.lang.ClassNotFoundException: com.ibm.ce.LoggingChannelExit
	at java.net.URLClassLoader.findClass(URLClassLoader.java:419)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:643)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:609)
	at com.ibm.mq.jmqi.remote.internal.RemoteExitChain.loadJavaExitByName
(RemoteExitChain.java:1855)
				... 36 more

The steps below show how to make use of shared libraries so that an enterprise application can use a WebSphere MQ messaging provider connection factory or activation specification that has been configured with channel exits.

  1. From the WebSphere Application Server admin console, navigate to Applications => Application Types => WebSphere enterprise applications, and then click on the application that will be making use of channel exit enabled WebSphere MQ messaging provider resources.
  2. As shown in Figure 5, click on the Shared library references link in the References section. Select the application module that will be making use of the WebSphere MQ messaging provider resource, and click on the Reference shared libraries button.
    Figure 5. Custom properties
    Figure 5. Custom properties
  3. If the relevant shared library isn’t already defined, click on the New button (circled in Figure 5). This displays a panel for entering class path information that can be used to locate the exit library. Enter the information and press OK.
  4. Select the library from the Available list, and use the arrow buttons to move it to the Selected list (Figure 6). Click OK, then OK again.
    Figure 6. Shared library mapping
    Figure 6. Shared library mapping
  5. Finally, save the changes and restart the application server.

When the enterprise application is next run, it should be able to use the channel exit enabled WebSphere MQ messaging provider resources. For example, take the case of a simple application that uses a WebSphere MQ messaging provider connection factory configured to use the LoggingChannelExit class as a send exit. This results in the application server log output shown in Listing 3.

Listing 3. Output from LoggingChannelExit
[05/10/08 16:06:02:736 BST] 00000010 SystemOut     O Send Exit Invoked
[05/10/08 16:06:02:861 BST] 00000010 SystemOut     O Send Exit Invoked
[05/10/08 16:06:02:877 BST] 00000010 SystemOut     O Send Exit Invoked
[05/10/08 16:06:02:877 BST] 00000010 SystemOut     O Send Exit Invoked
[05/10/08 16:06:02:877 BST] 00000010 SystemOut     O Send Exit Invoked
[05/10/08 16:06:02:877 BST] 00000010 SystemOut     O Send Exit Invoked
[05/10/08 16:06:02:877 BST] 00000010 SystemOut     O Send Exit Invoked
[05/10/08 16:06:02:986 BST] 00000010 SystemOut     O Send Exit Invoked

Using channel exit enabled resources in the application client environment

The class loading considerations when using WebSphere MQ messaging provider connection factories are simpler in the client environment than they are in the server environment. The channel exit classes or JARs are either part of the client application, or the client application class path is adjusted so that it includes a reference to the external channel exit classes or JARs. The best approach in this case is to reference an external JAR or set of classes using the -CCclasspath attribute of the launchClient command, shown in Listing 4.

Listing 4. Specifying classpath information with launchClient
C:\was7gm\profiles\AppSrv01\bin>launchClient.bat client.ear -CCclasspath=c:\exits\
 2809 m1
IBM WebSphere Application Server, Release 7.0
Java EE Application Client Tool
Copyright IBM Corp., 1997-2008
WSCL0012I: Processing command line arguments.
WSCL0013I: Initializing the Java EE Application Client Environment.
[05/10/08 16:18:00:002 BST] 00000000  W UOW=null source=com.ibm.ws.ssl.config.SSLConfig
 org=IBM prod=WebSphere component=Application Server thread=[P=879377:O=0:CT]
          CWPKI0041W: One or more key stores are using the default password.
WSCL0035I: Initialization of the Java EE Application Client Environment has completed.
WSCL0014I: Invoking the Application Client class Main
Send Exit Invoked
Send Exit Invoked
Send Exit Invoked

Conclusion

The IBM WebSphere MQ messaging provider support in WebSphere Application Server V7.0 makes it possible to deploy Java EE applications that directly leverage the enterprise messaging capabilities of WebSphere MQ. This article provided an overview of channel exits, and described their benefits, usage restrictions, and examples of how you can now enable them in application server and application client environments.

Resources

Comments

developerWorks: Sign in

Required fields are indicated with an asterisk (*).


Need an IBM ID?
Forgot your IBM ID?


Forgot your password?
Change your password

By clicking Submit, you agree to the developerWorks terms of use.

 


The first time you sign into developerWorks, a profile is created for you. Information in your profile (your name, country/region, and company name) is displayed to the public and will accompany any content you post, unless you opt to hide your company name. You may update your IBM account at any time.

All information submitted is secure.

Choose your display name



The first time you sign in to developerWorks, a profile is created for you, so you need to choose a display name. Your display name accompanies the content you post on developerWorks.

Please choose a display name between 3-31 characters. Your display name must be unique in the developerWorks community and should not be your email address for privacy reasons.

Required fields are indicated with an asterisk (*).

(Must be between 3 – 31 characters.)

By clicking Submit, you agree to the developerWorks terms of use.

 


All information submitted is secure.

Dig deeper into WebSphere on developerWorks


static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=1
Zone=WebSphere
ArticleID=398843
ArticleTitle=Using the WebSphere MQ messaging provider in WebSphere Application Server V7, Part 2: Using channel exits
publish-date=06242009