/*
* JBoss, Home of Professional Open Source Copyright 2006, JBoss Inc., and
* individual contributors as indicated by the @authors tag. See the
* copyright.txt in the distribution for a full listing of individual
* contributors.
*
* This is free software; you can redistribute it and/or modify it under the
* terms of the GNU Lesser General Public License as published by the Free
* Software Foundation; either version 2.1 of the License, or (at your option)
* any later version.
*
* This software is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
* FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
* details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this software; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA, or see the FSF
* site: http://www.fsf.org.
*/
package org.jboss.soa.esb.notification.jms;
import java.net.URI;
import javax.jms.JMSException;
import javax.jms.Message;
import org.apache.log4j.Logger;
import org.jboss.soa.esb.message.Properties;
import org.jboss.util.Strings;
/**
* Default impl of JMSPropertiesSetter.
* </p>
* The following JMS Header fields are set from the ESB Message instance:
* <lu>
* <li> Call.setMessagID -> JMSMessageID
* <li> Call.setRelatesTo -> JMSCorrelationID
* <li> Properties( key = JSMPropertiesSetter.JMS_EXPIRATION ) -> JMSExpiration
* </lu>
*
* @author <a href="daniel.bevenius@redpill.se">Daniel Bevenius</a>
*
*/
public class DefaultJMSPropertiesSetter implements JMSPropertiesSetter
{
private Logger log = Logger.getLogger( DefaultJMSPropertiesSetter.class );
/**
* Client JMSX Group ID.
*/
private static final String JMSX_GROUP_ID = "JMSXGroupID" ;
/**
* Client JMSX Group Seq.
*/
private static final String JMSX_GROUP_SEQ = "JMSXGroupSeq" ;
/**
* Set JMS Header fields on the outgoing JMS Message.
* </p>
* This implementation will simply set the JMSCorrelationID to
* the MessageID of the Message object.<br>
* Subclasses may override this method set other properties.
* </p>
*
* @param toJMSMessage the out-going JMSMessage object
* @param esbMsg the Message object from the ESB
* @throws JMSException
*/
public void setJMSProperties( final org.jboss.soa.esb.message.Message fromESBMessage , final Message toJMSMessage ) throws JMSException
{
setJMSMessageID( fromESBMessage, toJMSMessage );
setJMSCorrelationID( fromESBMessage,toJMSMessage );
setJMSExpiration( fromESBMessage,toJMSMessage );
setProperties( fromESBMessage, toJMSMessage );
}
private void setJMSCorrelationID( final org.jboss.soa.esb.message.Message fromESBMessage , final Message toJMSMessage ) throws JMSException
{
final URI correlationID = fromESBMessage.getHeader().getCall().getRelatesTo();
if ( correlationID != null )
{
log.debug( "Setting outgoing JMSCorreletionID to : " + correlationID.getFragment() );
toJMSMessage.setJMSCorrelationID( correlationID.getFragment() );
}
}
private void setJMSMessageID( final org.jboss.soa.esb.message.Message fromESBMessage , final Message toJMSMessage ) throws JMSException
{
final URI messageID = fromESBMessage.getHeader().getCall().getMessageID();
if ( messageID != null )
{
String msgID = messageID.toString();
if ( msgID.contains("<") )
msgID = msgID.replace( "<", "<" );
if ( msgID.contains(">") )
msgID = msgID.replace( ">", ">" );
log.debug( "Setting outgoing JMSCorreletionID to : " + msgID );
toJMSMessage.setJMSCorrelationID( msgID );
}
}
private void setJMSExpiration( final org.jboss.soa.esb.message.Message fromESBMessage, final Message toJMSMessage ) throws JMSException
{
final Object expirationObj = fromESBMessage.getProperties().getProperty( JMS_EXPIRATION );
if ( expirationObj instanceof Long )
{
final Long expire = (Long) expirationObj;
log.debug( "Setting outgoing JMSExpiration to : " + expire );
toJMSMessage.setJMSExpiration( expire );
}
}
/**
* Set ESB Message object properties on the outgoing JMS Message object instance.
* <p>
* Property names must obey the rules for a message selector identifier, See section 3.8.1.1,
* "Message Selector Syntax" on the JMS Spec.
* </p>
* Values must also by set with the correct type so that selector expressions work as
* expected.
* For example:
* myMessage.setStringProperty("NumberOfOrders", "2");
* The following expression in a message selector would evaluate to false,
* because a string cannot be used in an arithmetic expression:
* "NumberOfOrders > 1"
* <p/>
* Note that this method does not allow the setting of JMS Header properties, that is
* properites that start with 'JMSX', nor does it allow JMS Vendor specific properties, those
* that start with 'JMS_' to be set.
*
* @param fromESBMessage ESB Message object instance from which properties will be retrevied
* @param toJMSMessage JMS Message object instance upon which the properties will be set
*
* @throws JMSException
*/
private void setProperties( final org.jboss.soa.esb.message.Message fromESBMessage, final Message toJMSMessage ) throws JMSException
{
Properties properties = fromESBMessage.getProperties();
for ( String key : properties.getNames() )
{
if ( !Strings.isValidJavaIdentifier( key ))
continue;
if (key.startsWith("JMSX"))
{
if (!JMSX_GROUP_ID.equals(key) && !JMSX_GROUP_SEQ.equals(key))
{
continue ;
}
}
else if (key.startsWith("JMS_"))
{
continue ;
}
Object value = properties.getProperty( key );
log.debug( "Setting outgoing JMSProperty, key : " + key + ", value : " + value );
if ( value instanceof String )
toJMSMessage.setStringProperty( key, (String) value );
else if ( value instanceof Boolean )
toJMSMessage.setBooleanProperty( key, (Boolean)value );
else if ( value instanceof Short )
toJMSMessage.setShortProperty( key, (Short)value );
else if ( value instanceof Integer )
toJMSMessage.setIntProperty( key, (Integer)value );
else if ( value instanceof Long )
toJMSMessage.setLongProperty( key, (Long)value );
else if ( value instanceof Float )
toJMSMessage.setFloatProperty( key, (Float)value );
else if ( value instanceof Double )
toJMSMessage.setDoubleProperty( key, (Double)value );
else if ( value instanceof Byte )
toJMSMessage.setByteProperty( key, (Byte)value );
}
}
}