@Override public void handleMessage(final Exchange exchange) throws HandlerException { _messages.offer(exchange); if (_behavior == null || exchange .getContract() .getProviderOperation() .getExchangePattern() .equals(ExchangePattern.IN_ONLY)) { return; } switch (_behavior) { case FORWARD_IN_TO_OUT: exchange.send(exchange.getMessage().copy()); break; case FORWARD_IN_TO_FAULT: exchange.sendFault(exchange.getMessage().copy()); break; case REPLY_WITH_OUT: exchange.send(exchange.createMessage().setContent(_replyContent)); break; case REPLY_WITH_FAULT: exchange.sendFault(exchange.createMessage().setContent(_replyContent)); break; } }
@Test public void testAllExchangeEventsReceived() throws Exception { EventCounter counter = new EventCounter(); _domain.addEventObserver(counter, ExchangeInitiatedEvent.class); _domain.addEventObserver(counter, ExchangeCompletionEvent.class); // send 10 in-only messages and check the counters for (int i = 0; i < 10; i++) { ServiceReference inOnlyService = _domain.createInOnlyService(new QName("ExchangeEvent-0" + i)); Exchange inOnly = inOnlyService.createExchange(); inOnly.send(inOnly.createMessage()); } Assert.assertEquals(10, counter.initiatedCount); Assert.assertEquals(10, counter.completedCount); // initialize counters counter.initiatedCount = 0; counter.completedCount = 0; // send 10 in-out and check the count for (int i = 0; i < 10; i++) { ServiceReference inOutService = _domain.createInOutService( new QName("ExchangeEvent-1" + i), new MockHandler().forwardInToOut()); Exchange inOut = inOutService.createExchange(new MockHandler()); inOut.send(inOut.createMessage()); } Assert.assertEquals(10, counter.initiatedCount); Assert.assertEquals(10, counter.completedCount); }
@Test public void testInFaultMessageTrace() throws Exception { ServiceReference service = _domain.registerService(new QName("InFaultTrace"), new MockHandler().forwardInToFault()); Exchange exchange = _domain.createExchange(service, ExchangeContract.IN_OUT, new MockHandler()); exchange.send(exchange.createMessage()); }
@Test public void testMessageIdSetOnSend() { ServiceReference service = _domain.createInOnlyService(new QName("IdTest")); Exchange exchange = service.createExchange(); exchange.send(exchange.createMessage()); Assert.assertNotNull(exchange.getMessage().getContext().getProperty(Exchange.MESSAGE_ID)); }
@Test public void testPhaseIsInAfterInputMessage() { ServiceReference service = _domain.createInOnlyService(new QName("InPhase")); Exchange exchange = service.createExchange(); exchange.send(exchange.createMessage()); Assert.assertEquals(ExchangePhase.IN, exchange.getPhase()); }
/** Verify consumer callback is called when fault occurs on InOnly. */ @Test public void testFaultReportedOnInOnly() { ServiceReference ref = registerInOnlyService("inOut", new ErrorExchangeHandler()); MockHandler consumer = new MockHandler(); Exchange exchange = ref.createExchange(consumer); exchange.send(exchange.createMessage().setContent("test")); Assert.assertEquals(1, consumer.waitForFaultMessage().getFaults().size()); }
@Test public void testPhaseIsOutAfterFaultMessage() { MockHandler replyHandler = new MockHandler(); ServiceReference service = _domain.createInOutService(new QName("FaultPhase"), new MockHandler().forwardInToFault()); Exchange exchange = service.createExchange(replyHandler); exchange.send(exchange.createMessage()); replyHandler.waitForFaultMessage(); Assert.assertEquals(ExchangePhase.OUT, exchange.getPhase()); }
@Test public void testSendFaultOnNewExchange() { Exchange exchange = new ExchangeImpl(_domain, _dispatch); try { exchange.sendFault(exchange.createMessage()); Assert.fail("Sending a fault on a new exchange is not allowed"); } catch (IllegalStateException illEx) { return; } }
/** {@inheritDoc} */ @Override public Message compose(StreamableRecordBindingData source, Exchange exchange, boolean create) throws Exception { final org.switchyard.Message message = create ? exchange.createMessage() : exchange.getMessage(); getContextMapper().mapFrom(source, exchange.getContext(message)); ByteArrayOutputStream baos = new ByteArrayOutputStream(); source.getRecord().write(baos); message.setContent(new ByteArrayInputStream(baos.toByteArray())); return message; }
@Before public void before() { _exchange = Mockito.mock(ExchangeImpl.class, Mockito.RETURNS_DEEP_STUBS); _message = new DefaultMessage(); Mockito.when(_exchange.createMessage()).thenReturn(_message); _composer = new SOAPMessageComposer(); _composer.setContextMapper( new SOAPContextMapper() { public void mapFrom(SOAPBindingData sbd, Context context) { return; } }); }
@Test public void testExchangeCompletedEvent() { EventCounter counter = new EventCounter(); _domain.addEventObserver(counter, ExchangeCompletionEvent.class); // send in-only and check the count ServiceReference inOnlyService = _domain.createInOnlyService(new QName("ExchangeCompleteEvent-1")); Exchange inOnly = inOnlyService.createExchange(); inOnly.send(inOnly.createMessage()); Assert.assertEquals(1, counter.completedCount); // reset count counter.completedCount = 0; // send in-out and check the count ServiceReference inOutService = _domain.createInOutService( new QName("ExchangeCompleteEvent-2"), new MockHandler().forwardInToOut()); Exchange inOut = inOutService.createExchange(new MockHandler()); inOut.send(inOut.createMessage()); Assert.assertEquals(1, counter.completedCount); }
@Test public void testExceptionOnSendOnFaultExchange() throws Exception { final QName serviceName = new QName("testExceptionOnSendOnFaultExchange"); // Provide the service MockHandler provider = new MockHandler().forwardInToFault(); ServiceReference service = _domain.createInOutService(serviceName, provider); // Consume the service MockHandler consumer = new MockHandler(); Exchange exchange = service.createExchange(consumer); exchange.send(exchange.createMessage()); // wait, since this is async provider.waitForOKMessage(); consumer.waitForFaultMessage(); // Now try send another message on the Exchange... should result in an IllegalStateException... try { exchange.send(exchange.createMessage()); } catch (IllegalStateException e) { Assert.assertEquals("Exchange instance is in a FAULT state.", e.getMessage()); } }
@Test public void testRelatesToSetOnReply() { ServiceReference service = _domain.createInOutService(new QName("ReplyTest"), new MockHandler().forwardInToOut()); MockHandler replyHandler = new MockHandler(); Exchange exchange = service.createExchange(replyHandler); Message message = exchange.createMessage(); exchange.send(message); String requestId = message.getContext().getPropertyValue(Exchange.MESSAGE_ID); String replyId = exchange.getMessage().getContext().getPropertyValue(Exchange.MESSAGE_ID); String replyRelatesTo = exchange.getMessage().getContext().getPropertyValue(Exchange.RELATES_TO); Assert.assertEquals(requestId, replyRelatesTo); Assert.assertFalse(requestId.equals(replyId)); }
@Test public void testNoNPEOnInOnlyFault() throws Exception { QName serviceName = new QName("testNoNPEOnNoConsumer"); MockHandler provider = new MockHandler() { @Override public void handleMessage(Exchange exchange) throws HandlerException { throw new HandlerException("explode"); } }; ServiceReference service = _domain.createInOnlyService(serviceName, provider); // Don't provide a consumer... Exchange exchange = service.createExchange(); exchange.send(exchange.createMessage()); }
@Test public void testFaultWithNoHandler() throws Exception { final QName serviceName = new QName("testFaultWithNoHandler"); // Provide the service MockHandler provider = new MockHandler() { @Override public void handleMessage(Exchange exchange) throws HandlerException { throw new HandlerException("Fault With No Handler!"); } }; ServiceReference service = _domain.createInOnlyService(serviceName, provider); // Consume the service Exchange exchange = service.createExchange(); exchange.send(exchange.createMessage()); // Make sure the exchange is in fault status Assert.assertEquals(ExchangeState.FAULT, exchange.getState()); }
@Test public void testFaultTransformSequence() throws Exception { final QName serviceName = new QName("testFaultTransformSequence"); // Provide the service MockHandler provider = new MockHandler() { @Override public void handleMessage(Exchange exchange) throws HandlerException { Message fault = exchange.createMessage(); fault.setContent(new Exception("testFaultTransformSequence")); exchange.sendFault(fault); } }; InOutOperation providerContract = new InOutOperation( "faultOp", JavaTypes.toMessageType(String.class), // input JavaTypes.toMessageType(String.class), // output JavaTypes.toMessageType(Exception.class)); // fault InOutOperation consumerContract = new InOutOperation( "faultOp", JavaTypes.toMessageType(String.class), // input JavaTypes.toMessageType(String.class), // output JavaTypes.toMessageType(String.class)); // fault _domain.registerService(serviceName, new InOutService(providerContract), provider); _domain.getTransformerRegistry().addTransformer(new ExceptionToStringTransformer()); ServiceReference service = _domain.registerServiceReference(serviceName, new InOutService(consumerContract)); // Consume the service Exchange exchange = service.createExchange(new MockHandler()); exchange.send(exchange.createMessage()); // Make sure the exchange is in fault status Assert.assertEquals(String.class, exchange.getMessage().getContent().getClass()); Assert.assertEquals(exchange.getMessage().getContent(), "testFaultTransformSequence"); }
/** Make sure that the current message is set correctly when an exchange is sent. */ @Test public void testGetMessage() throws Exception { final QName serviceName = new QName("bleh"); final String inMsgContent = "in message"; final String outMsgContent = "out message"; // create a handler to test that the in and out content match // expected result from getMessage() ExchangeHandler provider = new BaseHandler() { public void handleMessage(Exchange exchange) { Assert.assertEquals(exchange.getMessage().getContent(), inMsgContent); Message outMsg = exchange.createMessage(); outMsg.setContent(outMsgContent); try { exchange.send(outMsg); } catch (Exception ex) { Assert.fail(ex.toString()); } } }; ExchangeHandler consumer = new BaseHandler() { public void handleMessage(Exchange exchange) { Assert.assertEquals(exchange.getMessage().getContent(), outMsgContent); } }; ServiceReference service = _domain.createInOutService(serviceName, provider); Exchange exchange = service.createExchange(consumer); Message inMsg = exchange.createMessage(); inMsg.setContent(inMsgContent); exchange.send(inMsg); }
/** * Create a Message from the given SOAP message. * * @param soapMessage the SOAP message to be converted * @param exchange The message Exchange. * @return a Message * @throws SOAPException If the SOAP message is not correct. */ public Message compose(final SOAPMessage soapMessage, final Exchange exchange) throws SOAPException { Message message = exchange.createMessage(); final SOAPBody soapBody = soapMessage.getSOAPBody(); if (soapBody == null) { throw new SOAPException("Missing SOAP body from request"); } final Iterator children = soapBody.getChildElements(); boolean found = false; try { while (children.hasNext()) { final Node node = (Node) children.next(); if (node instanceof SOAPElement) { if (found) { throw new SOAPException("Found multiple SOAPElements in SOAPBody"); } node.detachNode(); message.setContent(node); found = true; } } } catch (Exception ex) { if (ex instanceof SOAPException) { throw (SOAPException) ex; } throw new SOAPException(ex); } if (!found) { throw new SOAPException("Could not find SOAPElement in SOAPBody"); } return message; }
/** {@inheritDoc} */ @Override public void handleAction(Exchange exchange, KnowledgeAction action) throws HandlerException { RulesActionType actionType = (RulesActionType) action.getType(); switch (actionType) { case EXECUTE: { KnowledgeSession session = newStatelessSession(); setGlobals(exchange, action, session, true); List<Object> input = getInputList(exchange, action); session.getStateless().execute(input); break; } case INSERT: case FIRE_ALL_RULES: { /* if (!isContinue(exchange)) { disposeStatefulSession(); } */ KnowledgeSession session = getStatefulSession(); setGlobals(exchange, action, session, true); List<Object> input = getInputList(exchange, action); for (Object fact : input) { session.getStateful().insert(fact); } if (RulesActionType.FIRE_ALL_RULES.equals(actionType)) { session.getStateful().fireAllRules(); } if (isDispose(exchange)) { disposeStatefulSession(); } break; } case FIRE_UNTIL_HALT: { /* if (!isContinue(exchange)) { disposeStatefulSession(); } */ KnowledgeSession session = getStatefulSession(); setGlobals(exchange, action, session, false); if (_fireUntilHaltThread == null) { FireUntilHalt fireUntilHalt = new FireUntilHalt(this, session, getLoader()); session.addDisposals(fireUntilHalt); _fireUntilHaltThread = fireUntilHalt.startThread(); } final String undefinedVariable = toVariable(exchange); Map<String, List<Object>> listMap = getListMap(exchange, action.getInputExpressionMappings(), true, undefinedVariable); if (listMap.size() > 0) { for (Entry<String, List<Object>> entry : listMap.entrySet()) { String key = entry.getKey(); if (undefinedVariable.equals(key)) { String id = Strings.trimToNull(action.getId()); if (id != null) { key = id; } } List<Object> input = entry.getValue(); if (undefinedVariable.equals(key)) { for (Object fact : input) { session.getStateful().insert(fact); } } else { SessionEntryPoint sep = session.getStateful().getEntryPoint(key); if (sep != null) { for (Object fact : input) { sep.insert(fact); } } else { throw new HandlerException( "Unknown entry point: " + sep + "; please check your rules source."); } } } } else { Object content = exchange.getMessage().getContent(); if (content != null) { session.getStateful().insert(content); } } if (isDispose(exchange)) { disposeStatefulSession(); } break; } default: { throw new HandlerException("Unsupported action type: " + actionType); } } Object output = getOutput(exchange, action); if (ExchangePattern.IN_OUT.equals( exchange.getContract().getProviderOperation().getExchangePattern())) { Message message = exchange.createMessage().setContent(output); exchange.send(message); } }
@Test public void testInMessageTrace() { ServiceReference service = _domain.registerService(new QName("InTrace"), new MockHandler()); Exchange exchange = _domain.createExchange(service, ExchangeContract.IN_ONLY); exchange.send(exchange.createMessage()); }
private Exchange sendMessage(ServiceReference ref, Object content) { Exchange exchange = ref.createExchange(new MockHandler()); exchange.send(exchange.createMessage().setContent(content)); return exchange; }
/** {@inheritDoc} */ @Override public void handleMessage(Exchange exchange) throws HandlerException { if (!ExchangePhase.IN.equals(exchange.getPhase())) { return; } Context context = exchange.getContext(); ServiceOperation serviceOperation = exchange.getContract().getServiceOperation(); ProcessActionModel processActionModel = _actionModels.get(serviceOperation.getName()); ProcessActionType processActionType = getProcessActionType(context, processActionModel); Message messageIn = exchange.getMessage(); Long processInstanceId = null; ProcessInstance processInstance = null; switch (processActionType) { case START_PROCESS: if (_processId != null) { Object messageContentIn = messageIn.getContent(); if (messageContentIn != null) { Map<String, Object> parameters = new HashMap<String, Object>(); parameters.put(_messageContentInName, messageContentIn); processInstance = _ksession.startProcess(_processId, parameters); } else { processInstance = _ksession.startProcess(_processId); } processInstanceId = Long.valueOf(processInstance.getId()); } else { throwNullParameterException(processActionType, PROCESS_ID_VAR); } break; case SIGNAL_EVENT: String processEventType = getProcessEventType(context, processActionModel); Object processEvent = getProcessEvent(context, messageIn); processInstanceId = getProcessInstanceId(context); if (processInstanceId != null) { _ksession.signalEvent(processEventType, processEvent, processInstanceId.longValue()); } else { throwNullParameterException(processActionType, PROCESS_INSTANCE_ID_VAR); } break; case ABORT_PROCESS_INSTANCE: processInstanceId = getProcessInstanceId(context); if (processInstanceId != null) { _ksession.abortProcessInstance(processInstanceId.longValue()); } else { throwNullParameterException(processActionType, PROCESS_INSTANCE_ID_VAR); } break; } if (processInstanceId != null) { context.setProperty(PROCESS_INSTANCE_ID_VAR, processInstanceId, Scope.EXCHANGE); ExchangePattern exchangePattern = serviceOperation.getExchangePattern(); if (ExchangePattern.IN_OUT.equals(exchangePattern)) { if (processInstance == null) { processInstance = _ksession.getProcessInstance(processInstanceId.longValue()); } Message messageOut = exchange.createMessage(); Object messageContentOut = null; if (processInstance != null) { messageContentOut = ((WorkflowProcessInstance) processInstance).getVariable(_messageContentOutName); } if (messageContentOut != null) { messageOut.setContent(messageContentOut); } exchange.send(messageOut); } } }
/** * Send a message hash to the specified operation. * * @param operationName The operation name. * @param rubyHash The message hash. * @return The response object if an IN_OUT operation was invoked, otherwise null. * @throws Throwable An exception occurred while invoking the target operation. */ public Object send(String operationName, RubyHash rubyHash) throws Throwable { if (operationName == null) { throw new IllegalArgumentException("null 'operationName' argument."); } if (rubyHash == null) { throw new IllegalArgumentException("null 'rubyHash' argument."); } ServiceOperation operation = _serviceReference.getInterface().getOperation(operationName); if (operation == null) { throw new IllegalArgumentException( "Unknown operation name '" + operationName + "' on Service '" + _serviceReference.getName() + "'."); } // Clone the RubyHash to convert it to a normal Map based graph. This makes it possible // to more safely transport the payload data out of the ruby app via a SwitchYard Exchange... Map<String, Object> payload = deepClone(rubyHash); // Create the exchange contract... BaseExchangeContract exchangeContract = new BaseExchangeContract(operation); // Set the input type... exchangeContract .getInvokerInvocationMetaData() .setInputType(JavaService.toMessageType(payload.getClass())); if (operation.getExchangePattern() == ExchangePattern.IN_OUT) { final BlockingQueue<Exchange> responseQueue = new ArrayBlockingQueue<Exchange>(1); AtomicReference<ExchangeHandler> responseExchangeHandler = new AtomicReference<ExchangeHandler>( new ExchangeHandler() { public void handleMessage(Exchange exchange) throws HandlerException { responseQueue.offer(exchange); } public void handleFault(Exchange exchange) { responseQueue.offer(exchange); } }); Exchange exchange = _serviceReference.createExchange(exchangeContract, responseExchangeHandler.get()); Message message = exchange.createMessage().setContent(payload); exchange.send(message); Exchange exchangeOut = null; try { exchangeOut = responseQueue.take(); } catch (InterruptedException e) { throw new SwitchYardException( "Operation '" + operationName + "' on Service '" + _serviceReference.getName() + "' interrupted.", e); } if (exchangeOut.getState() == ExchangeState.OK) { return exchangeOut.getMessage().getContent(); } else { Object failureObj = exchangeOut.getMessage().getContent(); if (failureObj instanceof Throwable) { if (failureObj instanceof InvocationTargetException) { throw ((Throwable) failureObj).getCause(); } else { throw (Throwable) failureObj; } } else { throw new SwitchYardException( "Service invocation failure. Service '" + _serviceReference.getName() + "', operation '" + operationName + "'. Non Throwable failure message payload: " + failureObj); } } } else { Exchange exchange = _serviceReference.createExchange(exchangeContract); Message message = exchange.createMessage().setContent(payload); exchange.send(message); } return null; }