org.coos.messaging.impl.DefaultEndpointExtension Maven / Gradle / Ivy
package org.coos.messaging.impl;
import java.util.Hashtable;
import java.util.Random;
import org.coos.messaging.Channel;
import org.coos.messaging.Endpoint;
import org.coos.messaging.ExchangePattern;
import org.coos.messaging.Link;
import org.coos.messaging.Message;
import org.coos.messaging.MessageContext;
import org.coos.messaging.ProcessorException;
import org.coos.messaging.ProcessorInterruptException;
import org.coos.messaging.Service;
import org.coos.messaging.impl.DefaultProcessor;
import org.coos.messaging.util.Log;
import org.coos.messaging.util.LogFactory;
import org.coos.messaging.util.URIHelper;
public abstract class DefaultEndpointExtension extends DefaultProcessor implements Service{
private boolean started = false;
//currentChannel is instantiated in processMessage
private Link currentLink;
private Hashtable leList = new Hashtable();
public abstract void process(Message msg) throws ProcessorException;
public abstract void processInbound(Message msg) throws ProcessorException;
public abstract void processOutbound(Message msg) throws ProcessorException;
public abstract void startup() throws ProcessorException;
public abstract void shutdown() throws ProcessorException;
private static Log LOG;
private boolean useOutLink = true;
private Channel currentChannel;
public boolean isUseOutLink() {
return useOutLink;
}
/**
* Default true. Set to false if
* @param useOutLink
*/
public void setUseOutLink(boolean useOutLink) {
this.useOutLink = useOutLink;
}
public void start() throws Exception {
if (!started) {
startup();
started = true;
String name = getName();
LOG = LogFactory.getLog(DefaultEndpointExtension.class.getName()+ "("+name+")");
}
}
public void stop() throws Exception {
if (started) {
shutdown();
started = false;
}
}
/**
* Helper method that sends a message in reply to a request message
*
* @param response A new message that will be sent in reply to the request message
* @param request The message that requests a reply
* @throws ProcessorException
*/
public void reply(Message request, Message response) throws ProcessorException {
//Get current link
Link curLink = request.getMessageContext().getCurrentLink();
Link replyLink = null;
if(curLink.isOutLink()){
//If this is an outlink, reverse the response and send it back on inlink of current channel
replyLink = request.getMessageContext().getCurrentChannel().getInLink();
} else {
//If this is an inlink, reverse the response and send it back on outlink of current channel
replyLink = request.getMessageContext().getCurrentChannel().getOutLink();
}
//The receiver URI
response.setReceiverEndpointUri(request.getSenderEndpointUri());
//The sender URI
response.setSenderEndpointUri(request.getReceiverEndpointUri());
if(request.getHeader(Message.EXCHANGE_PATTERN).equals(ExchangePattern.OutIn)){
//Must contain the exchange id of the originating message to reach the sender
response.setHeader(Message.EXCHANGE_ID, request.getHeader(Message.EXCHANGE_ID));
//Must be set to InOut to reply to an OutIn
response.setHeader(Message.EXCHANGE_PATTERN, ExchangePattern.InOut);
}
//process the message
replyLink.processMessage(response);
}
public void processMessage(Message msg) throws ProcessorException {
if (msg.getType().equalsIgnoreCase(Message.TYPE_MSG)) {
LOG.debug("Processing message: "+msg.getName()+" from "+msg.getSenderEndpointUri()+" to "+msg.getReceiverEndpointUri());
LocalExchange le = (LocalExchange) leList.get(msg.getHeader(Message.EXCHANGE_ID));
if (le != null) {
synchronized (le) {
le.setIn(msg);
le.notify();
}
}
//Get the current link
MessageContext mc = msg.getMessageContext();
Link curLink = mc.getCurrentLink();
if (currentChannel == null) {
currentChannel = mc.getCurrentChannel();
}
if(curLink.isOutLink())
processOutbound(msg);
else
processInbound(msg);
URIHelper helper = new URIHelper(msg.getReceiverEndpointUri());
if(helper.getPath().startsWith("/"+getName())) {
process(msg);
throw new ProcessorInterruptException("Arrived at endpoint extension: "+getName());
}
}
}
public Message prepareMessage(Message msg) {
if (msg.getHeader(Message.EXCHANGE_PATTERN).equals(ExchangePattern.OutIn) && msg.getHeader("xId") == null) {
Random random = new Random();
String exchangeID = "xId-"+random.nextInt()+""+System.currentTimeMillis();
msg.setHeader("xId", exchangeID);
}
if (msg.getReceiverEndpointName() == null) {
URIHelper helper = new URIHelper(msg.getReceiverEndpointUri());
String receiver = helper.getEndpoint();
msg.setHeader(Message.RECEIVER_ENDPOINT_NAME, receiver);
}
if (msg.getSenderEndpointName() == null) {
URIHelper helper = new URIHelper(msg.getSenderEndpointUri());
String sender = helper.getEndpoint();
msg.setHeader(Message.SENDER_ENDPOINT_NAME, sender);
}
return msg;
}
public LocalExchange sendMessage(Message msg) throws ProcessorException {
msg = prepareMessage(msg);
if (msg.getHeader(Message.EXCHANGE_PATTERN).equals(ExchangePattern.OutIn)) {
LocalExchange le = new LocalExchange();
le.setOut(msg);
leList.put(msg.getHeader("xId"), le);
synchronized (le) {
if (useOutLink)
currentChannel.getOutLink().processMessage(msg);
else
currentChannel.getInLink().processMessage(msg);
try {
le.wait(Endpoint.DEFAULT_TIMEOUT);
if (le.getIn() == null)
LOG.error("Exchange timeout in endpoint extension "+getName()+" on message "+msg.getName()+" with id "+msg.getHeader("xId"));
leList.remove(le);
return le;
} catch (InterruptedException e) {
System.out.println("Interrupted in Endpoint Extension");
e.printStackTrace();
}
}
} else
if (useOutLink)
currentChannel.getOutLink().processMessage(msg);
else
currentChannel.getInLink().processMessage(msg);
return null;
}
}