package br.ufms.dct.simplerep.handlers; import java.util.Iterator; import org.apache.axiom.om.OMElement; import org.apache.axiom.soap.SOAPFactory; import org.apache.axiom.soap.SOAPHeader; import org.apache.axiom.soap.SOAPHeaderBlock; import br.ufms.dct.simplerep.ar.MessageContext; import br.ufms.dct.simplerep.ar.OperationContext; import br.ufms.dct.simplerep.ar.ProcessingStatus; import br.ufms.dct.simplerep.enums.AddressingConstants; import br.ufms.dct.simplerep.enums.SimpleRepConstants; public class AddressingOutSeqIdHandler implements AbstractHandler { public ProcessingStatus invoke(MessageContext context) { OperationContext opContext = context.getOperationContext(); int lastSeqId = -1; try { lastSeqId = Integer.parseInt(opContext.get(SimpleRepConstants.LAST_SEQUENCE_ID).toString()); } catch (NumberFormatException ex) { System.err.println("[AddressingOutSeqIdHandler] LastSequenceID could not be read."); return ProcessingStatus.CONTINUE; } catch (NullPointerException ex) { System.err.println("[AddressingOutSeqIdHandler] LastSequenceID was not defined in the OperationContext."); return ProcessingStatus.CONTINUE; } if (lastSeqId <= 0) { // very unlikely, exceptions should be caugth above. System.err.println("[AddressingOutSeqIdHandler] LastSequenceID is negative!"); return ProcessingStatus.CONTINUE; } SOAPFactory factory = (SOAPFactory) context.getEnvelope().getOMFactory(); return ProcessingStatus.CONTINUE; } public ProcessingStatus oldinvoke(MessageContext context) { System.out.println("[AddressingOutSeqIdHandler] invoke()"); SOAPHeader soapHeader = context.getEnvelope().getHeader(); OMElement refParams = null; SOAPHeaderBlock replyToBlock = null; OMElement address = null; // if there is no LastSequenceID in the message, // we assume it's the first message int lastSeqId = getLastSeqId(context); if (lastSeqId > 0) lastSeqId++; // generating the next one else lastSeqId = 1; SOAPFactory factory = (SOAPFactory) context.getEnvelope().getOMFactory(); // The LastSequenceID is transmitted via ReferenceParameters // More: http://www.w3.org/TR/2006/REC-ws-addr-soap-20060509 if (refParams == null) { refParams = factory.createOMElement("ReferenceParameters", AddressingConstants.ADDRESSING_NAMESPACE, AddressingConstants.WSA_DEFAULT_PREFIX); } OMElement lastSeqIdElement = factory.createOMElement( "LastSequenceID", SimpleRepConstants.SIMPLEREP_NAMESPACE, SimpleRepConstants.SIMPLEREP_NAMESPACE_PREFIX); lastSeqIdElement.addChild(factory.createOMText(String.valueOf(lastSeqId))); refParams.addChild(lastSeqIdElement); if (replyToBlock == null) { // The ReferenceParameter must be encapsulated in an EndpointReference replyToBlock = soapHeader.addHeaderBlock( "ReplyTo", soapHeader.declareNamespace( AddressingConstants.ADDRESSING_NAMESPACE, AddressingConstants.WSA_DEFAULT_PREFIX)); // Axis2 uses the ReplyTo (none) for their ServiceGroupId parameter, we're are doing the same // More: http://wso2.org/print/4666 address = factory.createOMElement("Address", AddressingConstants.ADDRESSING_NAMESPACE, AddressingConstants.WSA_DEFAULT_PREFIX); address.addChild(factory.createOMText("http://www.w3.org/2005/08/addressing/none")); replyToBlock.addChild(address); } replyToBlock.addChild(refParams); return ProcessingStatus.CONTINUE; } private SOAPHeaderBlock getReplyTo(MessageContext context) { SOAPHeader soapHeader = context.getEnvelope().getHeader(); // checking if the ReplyTo and ReferenceParameters are already present // in the message, so we don't override them Iterator addressingHeaders = soapHeader.getHeadersToProcess(null, AddressingConstants.ADDRESSING_NAMESPACE); while (addressingHeaders.hasNext()) { SOAPHeaderBlock soapHeaderBlock = (SOAPHeaderBlock) addressingHeaders.next(); String localName = soapHeaderBlock.getLocalName(); if (localName.equals("ReplyTo")) { return soapHeaderBlock; } } return null; } private OMElement getReferenceParametersElement(SOAPHeaderBlock replyToBlock) { Iterator replyToIt = replyToBlock.getChildrenWithNamespaceURI(AddressingConstants.ADDRESSING_NAMESPACE); while (replyToIt.hasNext()) { OMElement replyToChildElement = (OMElement) replyToIt.next(); String replyToChildName = replyToChildElement.getLocalName(); if (replyToChildName.equals("ReferenceParameters")) { Iterator refParamsIt = replyToChildElement.getChildrenWithNamespaceURI(SimpleRepConstants.SIMPLEREP_NAMESPACE); while(refParamsIt.hasNext()) { OMElement refParamsChildElement = (OMElement) replyToIt.next(); if (refParamsChildElement.getLocalName().equals("LastSequenceID")) { try { return Integer.parseInt(refParamsChildElement.getText()); } catch(NumberFormatException ex) { return -1; } } } } } return null; } }