Apache Camel - CamelContext


CamelContext提供对 Camel 中所有其他服务的访问,如下图所示 -

Camel上下文

让我们看看各种服务。默认情况下, Registry模块是一个 JNDI 注册表,保存应用程序使用的各种 Javabean 的名称。如果您将 Camel 与 Spring 一起使用,这将是 Spring ApplicationContext。如果你在 OSGI 容器中使用 Camel,这将是OSGI 注册表。顾名思义,类型转换器包含各种加载的类型转换器,它们将您的输入从一种格式转换为另一种格式您可以使用内置类型转换器或提供您自己的转换机制。组件模块包含您的应用程序使用组件。这些组件是通过自动发现加载到您指定的类路径上的。对于 OSGI 容器,只要激活新包,就会加载这些容器。我们已经在前面的章节中讨论了端点路由。数据格式模块包含加载的数据格式,最后语言模块表示加载的语言。

这里的代码片段将让您了解如何在 Camel 应用程序中创建CamelContext -

CamelContext context = new DefaultCamelContext();
try {
   context.addRoutes(new RouteBuilder() {
      // Configure filters and routes
   }
}
);

DefaultCamelContext类提供了CamelContext的具体实现。在addRoutes方法中,我们创建RouteBuilder的匿名实例。您可以创建多个RouteBuilder实例来定义多个路由。同一上下文中的每个路由必须有唯一的 ID。可以在运行时动态添加路由。与之前定义的 ID 相同的路由将替换旧路由。

接下来描述RouteBuilder实例内部的内容。

路线

路由器定义将消息从某个位置移动到某个位置的规则。您可以使用RouteBuilder在 Java DSL 中定义路由。您可以通过扩展内置RouteBuilder类来创建路线。该路线以起始端点开始,并以一个或多个终点结束。在两者之间,您实现处理逻辑。您可以在单个配置方法中配置任意数量的路由。

这是如何创建路线的典型示例 -

context.addRoutes(new RouteBuilder() {
   @Override
   public void configure() throws Exception {
      from("direct:DistributeOrderDSL")
      .to("stream:out");
   }
}

我们重写RouteBuilder类的configure方法并在其中实现我们的路由和过滤机制。在当前情况下,我们将从 Endpoint DistributeOrderDSL接收的输入重定向到控制台,该控制台由 Endpoint stream:out指定。

语言选择

您可以用不同的语言创建路线。以下是如何用三种不同语言定义相同路线的一些示例 -

JavaDSL

from ("file:/order").to("jms:orderQueue");

Spring DSL

<route>
   <from uri = "file:/order"/>
   <to uri = "jms:orderQueue"/>
</route>

斯卡拉DSL

from "file:/order" -> "jms:orderQueue"

过滤器

您使用过滤器来选择输入内容的一部分。要设置过滤器,您可以使用任意谓词实现。然后,过滤后的输入将发送到您所需的目标端点。在此示例中,我们过滤掉肥皂的所有订单,以便将这些订单集中发送给肥皂供应商。

from("direct:DistributeOrderDSL")
   .split(xpath("//order[@product = 'soaps']/items"))
      .to("stream:out");

在示例中,我们使用xpath谓词进行过滤。如果您更喜欢使用 Java 类进行过滤,请使用以下代码 -

from("direct:DistributeOrderDSL")
   .filter()
      .method(new Order(),"filter")
         .to("stream:out");

Order是您的自定义 Java 类具有您自己的过滤机制。

您可以在单个路由中组合多个谓词,如下所示 -

from("direct:DistributeOrderDSL")
   .choice()
      .when(header("order").isEqualTo("oil"))
         .to("direct:oil")
      .when(header("order").isEqualTo("milk"))
         .to("direct:milk")
      .otherwise()
         .to("direct:d");

因此,现在所有“石油”订单将发送给石油供应商,“牛奶”订单将发送给牛奶供应商,其余订单将发送给公共池。

定制处理器

您还可以使用自定义处理。下面的示例创建一个名为myCustomProcessor的自定义处理器,并在路由构建器中使用它。

Processor myCustomProcessor = new Processor() {
   public void process(Exchange exchange) {
      // implement your custom processing
   }
};
RouteBuilder builder = new RouteBuilder() {
   public void configure() {
      from("direct:DistributeOrderDSL")
      .process(myProcessor);
   }
};

您可以使用自定义处理器以及选择和过滤来更好地控制您的中介和路由 -

from("direct:DistributeOrderDSL")
   .filter(header("order").isEqualTo("milk"))
      .process(myProcessor);

使用XML

如果您愿意,可以使用更庞大的 XML 来定义路由。以下 XML 片段展示了如何通过 Spring XML 创建路由以及一些过滤 -

<camelContext xmlns = "http://camel.apache.org/schema/spring">
   <route>
      <from uri = "direct:DistributeOrderXML"/>
      <log message = "Split by Distribute Order"/>
      <split>
         <xpath>//order[@product = 'Oil']/items</xpath>
         <to uri = "file:src/main/resources/order/"/>
         <to uri = "stream:out"/>
      </split>
   </route>
</camelContext>

了解了如何构建路由后,我们现在将了解创建端点的各种技术。