View Javadoc
1   /*
2    * Copyright (c) MuleSoft, Inc.  All rights reserved.  http://www.mulesoft.com
3    * The software in this package is published under the terms of the CPAL v1.0
4    * license, a copy of which has been included with this distribution in the
5    * LICENSE.txt file.
6    */
7   package org.mule.construct;
8   
9   import org.mule.MessageExchangePattern;
10  import org.mule.api.MuleContext;
11  import org.mule.api.construct.FlowConstructInvalidException;
12  import org.mule.api.endpoint.InboundEndpoint;
13  import org.mule.api.endpoint.OutboundEndpoint;
14  import org.mule.api.processor.MessageProcessorChainBuilder;
15  import org.mule.api.source.MessageSource;
16  import org.mule.config.i18n.MessageFactory;
17  import org.mule.construct.processor.FlowConstructStatisticsMessageProcessor;
18  import org.mule.interceptor.LoggingInterceptor;
19  import org.mule.interceptor.ProcessingTimeInterceptor;
20  
21  import org.apache.commons.lang.Validate;
22  
23  /**
24   * A simple bridge between a single inbound endpoint and a single outbound endpoint.
25   * It enforces a consistent exchange pattern across its endpoints. If declared
26   * transactional, it ensures that the correct endpoint configuration is in place.
27   */
28  public class Bridge extends AbstractFlowConstruct
29  {
30      private final OutboundEndpoint outboundEndpoint;
31      private final MessageExchangePattern exchangePattern;
32      private final boolean transacted;
33  
34      public Bridge(String name,
35                    MuleContext muleContext,
36                    MessageSource messageSource,
37                    OutboundEndpoint outboundEndpoint,
38                    MessageExchangePattern exchangePattern,
39                    boolean transacted)
40      {
41          super(name, muleContext);
42  
43          Validate.notNull(messageSource, "messageSource can't be null");
44          Validate.notNull(outboundEndpoint, "outboundEndpoint can't be null");
45          Validate.notNull(exchangePattern, "exchangePattern can't be null");
46  
47          this.messageSource = messageSource;
48          this.outboundEndpoint = outboundEndpoint;
49          this.exchangePattern = exchangePattern;
50          this.transacted = transacted;
51      }
52  
53      @Override
54      protected void configureMessageProcessors(MessageProcessorChainBuilder builder)
55      {
56          builder.chain(new ProcessingTimeInterceptor());
57          builder.chain(new LoggingInterceptor());
58          builder.chain(new FlowConstructStatisticsMessageProcessor());
59          builder.chain(outboundEndpoint);
60      }
61  
62      @Override
63      protected void validateConstruct() throws FlowConstructInvalidException
64      {
65          super.validateConstruct();
66  
67          if (messageSource instanceof InboundEndpoint)
68          {
69              validateInboundEndpoint((InboundEndpoint) messageSource);
70          }
71  
72          validateOutboundEndpoint();
73      }
74  
75      private void validateOutboundEndpoint() throws FlowConstructInvalidException
76      {
77          if (outboundEndpoint.getExchangePattern() != exchangePattern)
78          {
79              throw new FlowConstructInvalidException(
80                  MessageFactory.createStaticMessage("Inconsistent bridge outbound endpoint exchange pattern, expected "
81                                                     + exchangePattern
82                                                     + " but was "
83                                                     + outboundEndpoint.getExchangePattern()), this);
84          }
85  
86          if (transacted
87              && ((outboundEndpoint.getTransactionConfig() == null) || (!outboundEndpoint.getTransactionConfig()
88                  .isConfigured())))
89          {
90              throw new FlowConstructInvalidException(
91                  MessageFactory.createStaticMessage("A transacted bridge requires a transacted outbound endpoint"),
92                  this);
93          }
94  
95          if ((!transacted) && (outboundEndpoint.getTransactionConfig() != null)
96              && (outboundEndpoint.getTransactionConfig().isConfigured()))
97          {
98              throw new FlowConstructInvalidException(
99                  MessageFactory.createStaticMessage("A non-transacted bridge requires a non-transacted outbound endpoint"),
100                 this);
101         }
102     }
103 
104     private void validateInboundEndpoint(InboundEndpoint inboundEndpoint)
105         throws FlowConstructInvalidException
106     {
107         if (inboundEndpoint.getExchangePattern() != exchangePattern)
108         {
109             throw new FlowConstructInvalidException(
110                 MessageFactory.createStaticMessage("Inconsistent bridge inbound endpoint exchange pattern, expected "
111                                                    + exchangePattern
112                                                    + " but was "
113                                                    + inboundEndpoint.getExchangePattern()), this);
114         }
115 
116         if (transacted
117             && ((inboundEndpoint.getTransactionConfig() == null) || (!inboundEndpoint.getTransactionConfig()
118                 .isConfigured())))
119         {
120             throw new FlowConstructInvalidException(
121                 MessageFactory.createStaticMessage("A transacted bridge requires a transacted inbound endpoint"),
122                 this);
123         }
124 
125         if ((!transacted) && (inboundEndpoint.getTransactionConfig() != null)
126             && (inboundEndpoint.getTransactionConfig().isConfigured()))
127         {
128             throw new FlowConstructInvalidException(
129                 MessageFactory.createStaticMessage("A non-transacted bridge requires a non-transacted inbound endpoint"),
130                 this);
131         }
132     }
133 
134     @Override
135     public String getConstructType()
136     {
137         return "Bridge";
138     }
139 }