4.1 Steps to develop JSM broadly speaking, a JMS application is a few JMS clients exchanging messages, and developing a JMS client application consists of the following steps:
Using Jndi to get ConnectionFactory object;
Create connection objects with ConnectionFactory;
Create one or more JMS sessions with the connection object;
Using Jndi to get target queue or Subject object, namely destination object;
Create MessageProducer and Messageconsumer with session and destination;
Notifies connection to start sending messages.
4.2 Programming Template 4.2.1 connectionfactory to initialize JMS, you need to use a connection factory. The client creates a connection to the ACTVEMQ by creating the ConnectionFactory, and a connection factory encapsulates a set of connection configuration parameters that are defined when the ACTIVEMQ is configured, such as Brokerurl parameters, This parameter is passed to the ACTIVEMQ service address and port, the default connection for the Openwire protocol is tcp://localhost:61616, and the default connection to the STOMP protocol is tcp://localhost:61613.
Note: Because the C + + client only supports the STOMP protocol for the time being, you need to use tcp://localhost:61613.
ConnectionFactory supports concurrency.
Java Client:
Activemqconnectionfactory Construction Method:
Activemqconnectionfactory ();
Activemqconnectionfactory (String brokerurl);
Activemqconnectionfactory (string userName, string password, string brokerurl);
Activemqconnectionfactory (string userName, string password, URI brokerurl);
Activemqconnectionfactory (URI brokerurl);
Where Brokerurl is the ACTIVEMQ service address and port.
For example:
Activemqconnectionfactory connectionfactory = new Activemqconnectionfactory ("tcp://192.168.0.135:61616");
Or
Activemqconnectionfactory connectionfactory = new Activemqconnectionfactory ();
ConnectionFactory. Setbrokerurl ("tcp://192.168.0.135:61616");
4.2.2 Connection After the successful creation of the correct connectionfactory, the next step is to create a connection that is a JMS-defined interface. ConnectionFactory is responsible for returning connection implementations that can communicate with the underlying messaging system. Typically, clients use only a single connection. According to the JMS documentation, the purpose of connection is to "encapsulate open connections with JMS providers" and to represent "open TCP/IP sockets between client and provider service routines." The document also states that connection should be the place where client authentication is performed, and that, among other things, the client can specify a unique identifier.
When a connection is created, its transmission is turned off by default and must be opened using the Start method.
A connection can establish one or more sessions.
When a program completes, the previously created connection must be closed, otherwise ACTIVEMQ cannot release the resource, and closing a connection also closes the Session,messageproducer and Messageconsumer.
Connection supports concurrency.
4.2.2.1 Create Connection
Java Client:
Activemqconnectionfactory Method:
Connection createconnection ();
Connection createconnection (String userName, string password);
For example:
Connection Connection = Connectionfactory.createconnection ();
4.2.2.2 Open Connection
Java Client:
Activemqconnection Method:
void Start ();
For example:
Connection.start ();
4.2.2.3 off Connection
Java Client:
Activemqconnection Method:
void Close ();
For example:
Connection.close ();
4.2.3 Session Once you get a connection from ConnectionFactory, you must create one or more sessions from the connection. A session is a thread that sends or receives messages, which you can use to create a messageproducer,messageconsumer and a message.
Sessions can be transacted or not transacted, usually by passing a Boolean parameter to the appropriate creation method on the connection.
Java Client:
Activemqconnection Method:
Session CreateSession (Boolean transacted, int acknowledgemode);
Which transacted for the use of transaction identification, Acknowledgemode for the signing mode.
For example:
Session session = Connection.createsession (false, Session.auto_acknowledge);
4.2.4 Destination Destination is an object that a client uses to specify the production message target and the consumer message source.
In PTP mode, the destination is called a queue, and in pub/sub mode, destination is called the topic, the subject. You can use multiple queue and topic in your program.
Java Client:
Activemqsession Method:
Queue createqueue (String queuename);
Temporaryqueue Createtemporaryqueue ();
Topic createtopic (String topicname);
Temporarytopic Createtemporarytopic ();
For example:
Destination Destination = Session.createqueue ("TEST. FOO ");
Or
Destination Destination = Session.createtopic ("TEST. FOO ");
4.2.5 MessageProducer MessageProducer is an object created by the session that is used to send messages to destination.
4.2.5.1 Create MessageProducer
Java Client:
Activemqsession Method:
MessageProducer createproducer (destination destination);
For example:
MessageProducer producer = Session.createproducer (destination);
4.2.5.2 Send Message
Java Client:
Activemqmessageproducer Method:
void send (destination destination, message message);
void send (destination destination, message message, int deliverymode, int priority,
Long TimeToLive);
void send (Message message);
void send (Message message, int deliverymode, int priority, long timetolive);
Where DeliveryMode is the transfer mode, priority is the message priority, TimeToLive is the message expiration time.
For example:
Producer.send (message);
4.2.6 Messageconsumer Messageconsumer is an object created by the session to receive messages from destination.
4.2.6.1 Create Messageconsumer
Java Client:
Activemqsession Method:
Messageconsumer Createconsumer (destination destination);
Messageconsumer Createconsumer (destination destination, String messageselector);
Messageconsumer Createconsumer (destination destination, String Messageselector, Boolean nolocal);
TopicSubscriber Createdurablesubscriber (Topic Topic, String name);
TopicSubscriber Createdurablesubscriber (Topic Topic, string name, String Messageselector, Boolean nolocal);
Where Messageselector is the message selector, the NOLOCAL flag defaults to False, and when set to true, the consumer can only receive messages that are published by the same connection (Connection), which applies only to topics, not to queues ; name identifies the subscription name that corresponds to the subscription topic, which you set when you persist the subscription.
For example:
Messageconsumer consumer = session.createconsumer (destination);
Synchronous and asynchronous reception of 4.2.6.2 messages
The synchronous reception of a message means that the client takes the initiative to receive the message, and the client can receive the next message using the Messageconsumer receive method.
Asynchronous reception of a message means that the ACTIVEMQ actively notifies the client when the message arrives. Clients can register to Messageconsumer by registering an object that implements the MessageListener interface. MessageListener only one method that must be implemented is--onmessage, which receives only one parameter, the message. This method is invoked when the OnMessage is implemented for each message sent to destination.
Java Client:
Activemqmessageconsumer Method:
Message receive ()
Message receive (Long timeout)
Message receivenowait ()
Where timeout is the wait time, in milliseconds.
Or
Implements the MessageListener interface, and whenever the message arrives, ACTIVEMQ invokes the OnMessage function in MessageListener.
For example:
Message message = Consumer.receive ();
4.2.6.3 message Selector
JMS provides a mechanism by which the messaging service can perform message filtering based on the criteria in the message selector. Producers can put application-specific properties in messages, and consumers can use selection criteria based on these attributes to indicate whether they are interested in the message. This simplifies the client's work and avoids the overhead of sending messages to consumers who do not need those messages. However, it also adds some extra overhead to the messaging service that handles selection criteria.
A message selector is a filter for messageconsumer that can be used to filter the properties and header portions of an incoming message (but not the message body) and determine whether the message will actually be consumed. According to the JMS documentation, the message selector is a string of strings that are based on a syntax that is a subset of SQL-92. You can use the message selector as part of the Messageconsumer creation.
Java Client:
For example:
Public final String SELECTOR = "Jmstype = ' topic_publisher '";
The selector examines the Jmstype property of the incoming message and determines whether the value of this property is equal to Topic_publisher. If equal, the message is consumed, and if not equal, the message is ignored.
4.2.7 Message The ultimate goal of a JMS program is to produce and consume messages that can be used by other programs, and the JMS message is a simple and flexible basic format that allows you to create messages that are not in the JMS format on different platforms. The message consists of the following parts: header, attribute, and message body.
Java Client:
Activemqsession Method:
Blobmessage createblobmessage (file file)
Blobmessage Createblobmessage (InputStream in)
blobmessage createblobmessage (URL url)
blobmessage createblobmessage (URL url, boolean deletedbybroker)
Bytesmessage Createbytesmessage ()
Mapmessage Createmapmessage ()
Message CreateMessage ()
ObjectMessage Createobjectmessage ()
ObjectMessage createobjectmessage (Serializable object)
TextMessage Createtextmessage ()
TextMessage createtextmessage (String text)
For example:
The following example demonstrates creating and sending a textmessage to a queue:
TextMessage message = Queuesession.createtextmessage ();
Message.settext (Msg_text); Msg_text is a String
Queuesender.send (message);
The following example shows the receipt of a message and converts it to the appropriate message type:
Message M = queuereceiver.receive ();
if (M instanceof textmessage) {
TextMessage message = (textmessage) m;
SYSTEM.OUT.PRINTLN ("Reading message:" + message.gettext ());
} else {
Handle Error
}
4.3 reliability mechanism The most reliable way to send a message is to send a persistent message in a transaction, ACTIVEMQ to send a persistent message by default. There are two ways to end a transaction: Commit or rollback. When a transaction commits, the message is processed. If there is a step in the transaction that fails, the transaction rolls back, and the action already executed in the transaction is revoked.
The most reliable way to receive a message is to receive information in a transaction, whether it is receiving messages from a non-temporary queue in PTP mode or a persistent subscription from Pub/sub mode.
For other programs, low reliability can reduce overhead and improve performance, such as when sending messages, you can change the priority of a message, or specify the expiration time for a message.
The higher the reliability of message delivery, the more overhead and bandwidth you will need. The tradeoff between performance and reliability is one aspect of design that needs to be considered. You can choose to generate and use non-persistent messages for optimal performance. On the other hand, you can get the best reliability by generating and using persistent messages and using transaction sessions. There are many choices between these two extremes, depending on the requirements of the application.
4.3.1 basic reliability mechanism 4.3.1.1 Control message signing (acknowledgment)
The sign that the client successfully receives a message is that the message was signed. A successful reception of a message typically consists of the following three phases:
1. The client receives the message;
2. Client processing messages;
3. The news was signed. The sign can be initiated by ACTIVEMQ or by the client, depending on the setting of the session signature mode.
In a session with a transaction, the signature occurs automatically when the transaction is committed. If a transaction is rolled back, all messages that have been received will be sent again.
In a session without a transaction, when and how a message is signed depends on the setting of the session.
1. Session.auto_acknowledge
When the client successfully returns from receive or OnMessage, the session automatically sign the receipt for this message from the client. In the Auto_acknowledge session, synchronous receive receives is an exception to the above three stages, in which case receipts and signing are followed immediately after the message is processed.
2. Session.client_acknowledge
The client sign the message by invoking the acknowledge method of the message. In this case, the sign takes place at the session level: signing up for a message that has already been consumed will automatically sign a receipt for all the messages that have been consumed.
3. Session.dups_ok_acknowledge
This option indicates that the session does not have to ensure that the delivery message is signed. It may cause a duplication of messages, but reduces the cost of the session, so only the client can tolerate duplicate messages to use (if ACTIVEMQ sends the same message again, the jmsredelivered in the header will be set to true).
Java Client:
Signature mode is:
1. Session.auto_acknowledge
2. Session.client_acknowledge
3. Session.dups_ok_acknowledge
Activemqconnection Method:
Session CreateSession (Boolean transacted, int acknowledgemode);
For example:
Session session = Connection.createsession (false, Session.auto_acknowledge);
For queues, if it receives a message but does not sign it when a session terminates, ACTIVEMQ retains the message and sends it back to the next consumer entering the queue.
For a theme, if a persistent subscriber terminates, it has consumed an unsigned message and will be retained until it is transmitted again to the user. For non-persistent subscriptions, ATIVEMQ deletes these messages when the user session closes.
If you use queues and persistent subscriptions, and the session does not use a transaction, you can use the Recover method of the session to stop the session, and then start again and receive the first message that it has not signed, in fact, After restarting the session a series of messages are sent from the last signed message to the next entry as the starting point. If a message expires or a high-priority message arrives, then the message will be routed differently than initially. For Non-persistent subscribers, it is possible for ACTIVEMQ to delete all messages that have not been signed after reboot.
4.3.1.2 Specifies the message delivery mode
ACTIVEMQ supports two message delivery modes: Persistent and non_persistent two.
1. Persistent (persistent message)
This is the default delivery mode for ACTIVEMQ, which guarantees that the messages are delivered only once and used successfully once. For these messages, reliability is a priority. Another important aspect of reliability is ensuring that when a persistent message is delivered to a target, the message service does not lose the message until it is delivered to the consumer. This means that when a persistent message is delivered to a target, the messaging service puts it into the persistent data store. If the message service fails for some reason, it can recover the message and deliver the message to the appropriate consumer. While this increases the overhead of messaging, it increases reliability.
2. Non_persistent (non-persistent messages)
Ensure that these messages are transmitted at most once. For these messages, reliability is not a major consideration. This pattern does not require persistent data storage, nor does it guarantee that the message service will not be lost if it fails for some reason.
There are two ways to specify the delivery mode:
1. Use the Setdeliverymode method so that all messages use this transfer mode;
2. Use the Send method to set the transfer mode for each message;
Java Client:
The transfer modes are:
1. Deliverymode.persistent
2. Deliverymode.non_persistent
Activemqmessageproducer Method:
void Setdeliverymode (int newdeliverymode);
Or
void send (destination destination, message message, int deliverymode, int priority,
Long TimeToLive);
void send (Message message, int deliverymode, int priority, long timetolive);
Where DeliveryMode is the transfer mode, priority is the message priority, TimeToLive is the message expiration time.
For example:
Producer.setdeliverymode (deliverymode.non_persistent);
If you do not specify a delivery mode, the default is persistence messages. If you tolerate message loss, using Non-persistent messages can improve performance and reduce storage overhead.
4.3.1.3 Set Message priority
In general, you can ensure that all messages sent to the destination by a single session are routed to the consumer in the order in which they are sent. However, if different priorities are assigned to these messages, the messaging system will first attempt to deliver higher-priority messages.
There are two ways to set the priority of a message:
1. Use the Setdeliverymode method so that all messages use this transfer mode;
2. Use the Send method to set the transfer mode for each message;
Java Client:
Activemqmessageproducer Method:
void setpriority (int newdefaultpriority);
Or
void send (destination destination, message message, int deliverymode, int priority,
Long TimeToLive);
void send (Message message, int deliverymode, int priority, long timetolive);
Where DeliveryMode is the transfer mode, priority is the message priority, TimeToLive is the message expiration time.
For example:
Producer.setpriority (4);
Message priority is from 0-9 10 levels, 0-4 is a normal message, and 5-9 is an expedited message. If you do not specify a priority, the default is 4. JMS does not require a message to be sent strictly according to these 10 priorities, but must ensure that the expedited message arrives prior to the normal message.
4.3.1.4 allow messages to expire
By default, messages will never expire. If a message loses meaning within a specific cycle, you can set an expiration time.
There are two ways to set the expiration time of a message in milliseconds:
1. Use the Settimetolive method to set the expiration time for all messages;
2. Use the Send method to set the expiration time for each message;
Java Client:
Activemqmessageproducer Method:
void Settimetolive (long timetolive);
Or
void send (destination destination, message message, int deliverymode, int priority,
Long TimeToLive);
void send (Message message, int deliverymode, int priority, long timetolive);
Where DeliveryMode is the transfer mode, priority is the message priority, TimeToLive is the message expiration time.
For example:
Producer.settimetolive (1000);
Message expiration time, the TimeToLive value in the Send method plus the GMT time value for the sending time. If the TimeToLive value is equal to zero, the jmsexpiration is set to zero, indicating that the message never expires. If the message has not been sent to the destination after the message expires after it is sent, the message is cleared.
4.3.1.5 Create a temporary target
ACTIVEMQ creates temporary targets through createtemporaryqueue and createtemporarytopic that continue to the connection shutdown that created it. Only clients created by connection that create temporary targets can receive messages from temporary targets, but any producer can send messages to a temporary destination. If the connection that created this goal is turned off, the temporary target is closed and the content disappears.
Java Client:
Activemqsession Method:
Temporaryqueue Createtemporaryqueue ();
Temporarytopic Createtemporarytopic ();
Some clients need a target to receive replies to messages sent to other clients. Temporary targets can be used at this time. One of the attributes of the message is the Jmsreplyto property, which is used for this purpose. You can create a temporary destination and put it in the Jmsreplyto attribute of the message, and the consumer who receives the messages can use it to respond to the producer.
Java Client:
As shown in the code snippet below, a temporary destination is created and placed in the Jmsreplyto property of TextMessage:
Create a temporary queue for replies ...
Destination Tempqueue = Session.createtemporaryqueue ();
Set ReplyTo to temporary queue ...
Msg.setjmsreplyto (Tempqueue);
When the consumer receives this message, it extracts the temporary destination from the Jmsreplyto field and constructs a messageproducer through the application to send the response message back to the producer. This shows how to use the properties of the JMS message and shows the usefulness of a private temporary destination. It also shows that the client can be both a producer of the message and a consumer of the message.
Get the temporary queue from the Jmsreplyto
The message ...
Destination Tempqueue = Msg.getjmsreplyto ();
...
Create a Sender for the temporary queue
MessageProducer Sender = session. Createproducer (Tempqueue);
TextMessage msg = Session.createtextmessage ();
Msg.settext (Replyto_text);
...
Send the message to the temporary queue ...
Sender.send (msg);
4.3.2 Advanced Reliability mechanism 4.3.2.1 Create a persistent subscription
By setting the persistent transfer mode for the Publisher, a persistent subscription is used for the subscriber, which guarantees that the PUB/SUB program will receive all published messages.
Message subscriptions are divided into Non-persistent subscriptions (non-durable subscription) and persistent subscriptions (durable subscription), and non-persistent subscriptions only when the client is active That is, the ACTIVEMQ remain connected to receive messages sent to a topic, and when the client is offline, the message to the topic will be lost and never received. A persistent subscription, the client registers an ID with ACTIVEMQ, and when the client is offline, ACTIVEMQ saves all messages sent to the topic for that ID, and when the client connects to ACTIVEMQ again, it is based on its own ID Get all messages that are sent to the subject when you are offline. Persistent subscriptions increase overhead, with only one active user in a persistent subscription at the same time.
To establish a persistent subscription:
1. Set up a customer ID for the connection;
2. Specify a subscription name for the subject of the subscription;
The above combination must be unique.
4.3.2.1.1 Create a persistent subscription
Java Client:
Activemqconnection Method:
void Setclientid (String newclientid)
And
Activemqsession Method:
TopicSubscriber Createdurablesubscriber (Topic Topic, String name)
TopicSubscriber Createdurablesubscriber (Topic Topic, string name, string
Messageselector, Boolean nolocal)
Where Messageselector is the message selector, the NOLOCAL flag defaults to False, and when set to true, the consumer can only receive messages that are published by the same connection (Connection), which applies only to topics, not to queues ; name identifies the subscription name that corresponds to the subscription topic, which you set when you persist the subscription.
4.3.2.1.2 Delete Persistent Subscriptions
Java Client:
Activemqsession Method:
void unsubscribe (String name);
4.3.2.2 Use local transaction
When a message is generated or used in a transaction, ACTIVEMQ tracks the individual send and receive processes and completes them when the client makes a call to commit the transaction. If a specific send or receive operation in a transaction fails, an exception occurs. The client code handles the exception by ignoring the exception, retrying the operation, or rolling back the entire transaction. When a transaction commits, all successful operations are completed. When a transaction is rolled back, all successful operations are canceled.
The scope of a local transaction is always a session. That is, one or more producer or consumer actions executed in the context of a single session can be made into a local transaction.
Not only can a single session access Queue or Topic (