操作指南

端点 DSL

师成师成· 更新于 2026-09-28· 阅读 13 分钟· 0 次阅读

登录后可跨设备保存划线和私人笔记登录

Endpoint DSL

Endpoint DSL 是一套构建器 API,可用于使用类型安全的端点 URL 配置。

Endpoint DSL 仅作为 Java DSL 的一部分提供。

访问该 DSL 有多种方式,其中最主要的方式是改用 EndpointRouteBuilder 代替通常的 RouteBuilder。该构建器通过 org.apache.camel.builder.endpoint.EndpointRouteBuilder 上的继承关系,提供了对 Camel 所有端点构建器的访问权限。

使用 Endpoint DSL

下面是一个使用标准 RouteBuilder Java DSL 编写的 FTP 路由示例:

仅 Java:使用标准基于字符串的 URI 的 FTP 路由

public class MyRoutes extends RouteBuilder {
    @Override
    public void configure() {
        from("ftp://foo@myserver?password=secret&recursive=true&" +
                "ftpClient.dataTimeout=30000&" +
                "ftpClientConfig.serverLanguageCode=fr")
                .to("bean:doSomething");
    }
}

同样的一条 Java 语句,可以借助新的 EndpointRouteBuilder 以更具类型安全性、更易阅读的方式重写,该类允许使用端点 DSL(Endpoint-DSL):

仅 Java:使用类型安全的端点 DSL 重写的同一条 FTP 路由

public class MyRoutes extends EndpointRouteBuilder {
    @Override
    public void configure() throws Exception {
        from(ftp("myserver").account("foo").password("secret").recursive(true)
            .advanced()
                .ftpClientParameters(Collections.singletonMap("dataTimeout", 30000))
                .ftpClientConfig(Collections.singletonMap("serverLanguageCode", "fr")))
            .to(bean("something"));
    }
}

类型安全

与 Component DSL 类似,Endpoint DSL 使用从源代码中提取并写入各种 JSON 文件的元模型,为每个组件生成流式 DSL。该流式 DSL 为参数提供了类型安全。

使用自定义组件名称

Endpoint DSL 使用 Component 的默认名称,因此在上面的示例中名称为 ftp。有些场景下,你可能以不同名称注册了多个同类型的 Camel 组件。例如你有两个 JMS broker 系统(比如 ActiveMQ 和 WebSphereMQ)。

此时你可以设置两个具有唯一名称的 Camel JMS 组件,例如:myAMQ 和 myWMQ

Endpoint DSL 可以通过 jms 流式构建器使用这些名称,如下所示:

纯 Java 方式:在 Endpoint DSL 中使用自定义组件名称

from(jms("myWMQ", "cheese").concurrentConsumers(5))
    .to(jms("myAMQ", "smelly"));

注意我们可以如何在 jms 流式构建器中将它们的名称作为第一个参数引用。这样该示例将从名为 cheese 的 WebSphereMQ 队列中消费消息,并路由到名为 smely 的 ActiveMQ 队列。

Header 名称

endpoint-dsl 提供了对组件 header 名称的类型安全访问,因此你无需记住确切的 header 名称字符串,也无需导入每个组件的常量类。

推荐的方式是使用 headers() 方法,它为所有组件的 header 名称构建器提供了一个专用的入口:

仅 Java:使用类型安全的 header 名称构建器

public class MyRoutes extends EndpointRouteBuilder {
    @Override
    public void configure() {
        from(/*some endpoint*/)
            .setHeader(headers().file().fileName(), constant("foo.txt"))
            .setHeader(headers().kafka().kafkaKey(), constant("myKey"))
            ;
    }
}

headers() 方法也可作为静态方法使用,因此可以通过静态导入 EndpointHeaderBuilders 来使用它:

import static org.apache.camel.builder.endpoint.EndpointHeaderBuilders.*;

.setHeader(kafka().kafkaKey(), constant("myKey"))
每个组件的标头名称构建器都包含 Javadoc,其中说明了标头的描述、类型,以及它适用于消费者、生产者还是两者。

在路由构建器之外使用 Endpoint DSL

你可以在路由构建器之外使用类型安全的 Endpoint DSL,方式包括:

  • 使用 FluentProducerTemplate 发送消息
  • 创建 Endpoint

例如,要向 Kafka 发送消息,可以使用 FluentProducerTemplate

仅 Java:使用 FluentProducerTemplate 结合 Endpoint DSL 发送消息

import static org.apache.camel.builder.endpoint.StaticEndpointBuilders.kafka;

context.createFluentProducerTemplate()
    .to(kafka("start").clientId("myClient").brokers("{{myBrokers}}").partitionKey("myKey"))
    .withBody("Hello World")
    .send();

要在 Kafka 中使用 endpoint-dsl,你需要静态导入 org.apache.camel.builder.endpoint.StaticEndpointBuilders 类中的 kafka 方法,该类包含了所有 Camel 组件。

也可以在 Java 代码中通过 endpoint-dsl 创建端点,如下所示:

仅限 Java:使用 Endpoint DSL 创建端点并解析它

import static org.apache.camel.builder.endpoint.StaticEndpointBuilders.paho;

Endpoint mqtt = paho("sensor").clientId("myClient").userName("scott").password("tiger")
    .resolve(context);

你就可以通过类型安全的 DSL 设置所有选项,然后调用以 CamelContext 为参数的 resolve 来解析(创建)该端点。

如果你想使用 endpoint-dsl 将端点注入到你的 POJO 或 RouteBuilder 类中,可以采用与前面示例类似的方式,但有一个重要区别:

仅限 Java:将 Endpoint DSL 构建器注入 POJO

import org.apache.camel.BindToRegistry;
import org.apache.camel.EndpointInject;
import org.apache.camel.Produce;
import org.apache.camel.builder.EndpointProducerBuilder;
import static org.apache.camel.builder.endpoint.StaticEndpointBuilders.paho;

@BindToRegistry
public class MyPojo {

    @Produce
    private FluentProducerTemplate producer;

    private final EndpointProducerBuilder mqtt = paho("sensor").clientId("myClient").userName("scott").password("tiger");

    public void sendToSensor(String data) {
        producer.withBody(data).to(mqtt).send();
    }

}

MyPojo 是一个类,在独立的 Camel 中可以通过 @BindToRegistry 注解被发现并注册。如果你使用 Spring Boot 或 Quarkus 等框架,则应使用它们对应的注解来实现。

不过这并不是本示例的重点,本示例的重点是使用 Endpoint DSL 来配置 MQTT 端点(camel-paho)。与之前一样,通过静态导入 paho 方法,然后使用其流式构建方法来配置类型安全的 endpoint-dsl,从而完成端点的配置。注意其返回类型是 EndpointProducerBuilder。该类型并不是 Endpoint 实例,因为它尚未被解析(即它只是一个端点的构建器)。这意味着该构建器可以在 CamelContext 创建并启动之前就编写代码并完成编译。

在运行时,我们希望使用该端点向 MQTT 服务器发送消息;这在 sendToSensor 方法中完成,我们使用 FluentProducerTemplate,它能够将 EndpointProducerBuilder 作为端点使用,如 .to(mqtt) 所示。

依赖

Maven 用户需要在 pom.xml 中为该组件添加以下依赖:

pom.xml

<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-endpointdsl</artifactId>
    <version>x.x.x</version>
</dependency>

评论

登录后参与评论

正在加载评论…