9.3. 开发 Fuse Online 扩展


如果 Fuse Online 不提供创建集成所需的功能,则专家开发人员可编写提供所需行为的扩展。Syndesis 扩展存储库 https://github.com/syndesisio/syndesis-extensions 包含扩展示例。

商业集成商共享对扩展代码的开发人员共享要求。开发人员提供了一个包含该扩展名的 .jar 文件。商业集成商上传 Fuse Online 中的 .jar 文件,使自定义连接器、自定义步骤或库资源可在 Fuse Online 中使用。

Red Hat Developer Studio 的 Fuse 工具插件提供了一个向导,可帮助您开发步骤扩展或连接器扩展。无论您选择是在 Developer Studio 中开发一个步骤扩展还是在一些其他 IDE 中开发一个连接器,是个人选择。有关使用 Developer Studio 插件的详情,请参考为 Fuse 在线集成开发扩展

在本文档中,以下主题概述了流程,描述要求,并提供您在您选择的 IDE 中开发扩展的其他示例。

9.3.1. 开发扩展的一般步骤

在开始开发扩展之前,请先熟悉需要完成的任务。

先决条件

  • 熟悉 Maven
  • 如果您正在开发一个扩展来提供连接器或者提供连接间数据的集成步骤,请熟悉 Camel
  • 体验编程
Important

集成 pod 在带有扁平类路径的 Java 进程中运行。为了避免版本冲突,请确保扩展使用的依赖项与从所有这些源导入的材料(BOM)一致:

  • org.springframework.boot:spring-boot-dependencies:$SPRING_BOOT_VERSION
  • org.apache.camel:camel-spring-boot-dependencies:$CAMEL_VERSION
  • io.syndesis.integration:integration-bom:$SYNDESIS_VERSION

如果其他依赖项不是导入的 BOM 的一部分,您必须:

  • 将它们打包在 lib 目录中的扩展 JAR 文件中。
  • 从扩展名的 JSON 描述符文件的 dependencies 属性中省略它们。

流程

  1. 了解扩展功能必须做什么。请联系您的业务同事了解功能要求。
  2. 确定您是否需要开发步骤扩展名、连接器扩展或库扩展。
  3. 设置用于开发扩展的 Maven 项目。
  4. 如果要开发一个步骤扩展:

    1. 决定是否将其实施为 Camel 路由或使用 Syndesis Step API 实现它。Syndesis API 的信息是 http://javadoc.io/doc/io.syndesis.extension/extension-api
    2. 如果您选择将扩展作为 Camel 路由实施,则决定是否实施 XML 片段、RouteBuilder 类或 bean。
    3. 在 Maven 项目中,指定所需的元数据,如 schemaVersion、扩展 名称extensionId 等等。
  5. 对实施该功能的类进行编码。
  6. 将依赖项添加到项目的 pom.xml 文件中。
  7. 对于连接器和库扩展,以及您在 XML 中实施的步骤扩展,请创建用于定义该扩展的 JSON 文件。

    对于您在 Java 中实施的步骤扩展,当您在 Maven 项目中指定对应的数据结构值时,Maven 可以为您生成 JSON 扩展名文件。

  8. 运行 Maven 来构建扩展并创建扩展名的 JAR 文件。
  9. 通过将 JAR 文件上传到 Fuse 在线开发环境来测试扩展。
  10. 提供 JAR 文件,向您的公司同事打包扩展,并将其上传到 Fuse 在线生产环境。提供 JAR 文件时,使您的业务同事了解所有需要在 Fuse Online Web 界面中出现的信息的配置设置。

9.3.2. 扩展类型的描述

扩展定义如下之一:

  • 对连接间的集成数据执行一个或多个自定义步骤。每个自定义步骤都执行一个操作。这是步骤扩展。
  • 集成运行时使用的库资源。例如,库扩展可以提供 JDBC 驱动程序以连接到专有 SQL 数据库,如 Oracle。
  • 单个自定义连接器,用于创建到您要集成的特定应用程序或服务的连接。这是一个连接器扩展。

    注意

    Fuse Online 可以使用 OpenAPI 文档为 REST API 客户端创建连接器。请参阅 开发 REST API 客户端连接器

商业集成商共享对扩展代码的开发人员共享要求。开发人员提供了一个包含该扩展名的 .jar 文件。商业集成商上传 Fuse Online 中的 .jar 文件,使自定义连接器、自定义步骤或库资源可在 Fuse Online 中使用。

您上传到 Fuse Online 的扩展 .jar 文件始终包含一个扩展名。

有关上传和使用一个扩展的示例,它提供在连接间的数据上运行的步骤,请参阅 AMQ 到 REST API 示例集成指南

9.3.3. 扩展内容和结构概述

扩展是打包至 .jar 文件中的类、依赖项和资源的集合。

Fuse Online 使用 Spring Boot 来加载扩展。因此,您必须根据 Spring Boot 的可执行 JAR 格式打包扩展。例如,确保使用 ZipEntry.STORED() 方法保存嵌套的 JAR 文件。

软件包扩展的 .jar 文件的结构如下:

extension.jar
|
+- META-INF
|  |
|  +- syndesis
|     |
|     +- syndesis-extension-definition.json 
1

|
+- mycompany
|  |
|  +-project
|    |
|    +-YourClasses.class 
2

|
+- lib 
3

  |
  +-dependency1.jar
  |
  +-dependency2.jar
Copy to Clipboard Toggle word wrap
1
指定定义扩展的数据结构的 JSON 模式文件。这称为扩展定义 JSON 文件。
2
实施扩展提供行为的 Java 类
3
构建和执行自定义功能所需的其他依赖项。

9.3.4. 扩展定义 JSON 文件中的要求

每个扩展都必须有一个 .json 文件,通过为数据结构指定值来定义扩展,如名称、描述、支持的操作和依赖项。对于每种扩展类型,下表表示 Maven 是否可以生成扩展定义 JSON 文件以及需要哪些数据结构。

Expand
扩展类型Maven Can 生成扩展定义所需的数据结构

Java 中的步骤扩展

schemaVersion
name
description
version
extensionId
extensionType
actions
dependencies *

XML 中的步骤扩展

schemaVersion
name
description
version
extensionId
extensionType
actions
dependencies *

连接器扩展

schemaVersion
name
description
version
extensionId
extensionType
properties
actions
dependencies *
componentScheme
connectorCustomizers
connectorFactory

库扩展

schemaVersion
name
description
version
extensionId
extensionType
dependencies *

* 虽然在实践中不严格地指定依赖项,但始终存在您需要指定的依赖关系。

通常,扩展定义文件有以下布局:

{
  "schemaVersion": "v1",
  "name": "",
  "description": "",
  "version": "",
  "extensionId": "",
  "extensionType": "",
  "properties": {
  },
  "actions": [
  ],
  "dependencies": [
  ],
}
Copy to Clipboard Toggle word wrap
  • schemaVersion 定义 schema 的版本。在内部,Syndesis 使用 schemaVersion 来确定如何将扩展定义映射到内部模型。这允许根据旧版本的 Syndesis 进行开发,以部署在较新版本的 Syndesis 中。
  • name 是扩展名。当您将扩展上传到 Fuse Online 时,会显示此名称。
  • description 是您要指定的任何有用信息。Fuse Online 对这个值没有运行。
  • 为方便起见,版本 会方便您区分扩展的更新。Fuse Online 对这个值没有运行。
  • extensionId 为扩展定义唯一 ID。这应该最少在 Syndesis 环境间唯一。
  • extensionType 指示扩展提供的内容。从 Syndesis 版本 1.3 开始,支持以下扩展类型:

    • 步骤
    • 连接器
  • 需要使用连接器扩展中顶级 的属性。它控制 Fuse Online 用户选择连接器来创建连接时显示的 Fuse Online。此属性 对象包含一组属性,用于为每个表单控制创建连接。例如:

    "myControlName": {
      "deprecated": true|false,
      "description": "",
      "displayName": "",
      "group": "",
      "kind": "",
      "label": "",
      "required": true|false,
      "secret": true|false,
      "javaType": "",
      "type": "",
      "defaultValue": "",
      "enum": {
      }
    }
    Copy to Clipboard Toggle word wrap

    在连接器扩展中,嵌套属性对象定义 HTML 表单控制来配置连接操作。在步骤扩展中,actions 对象包含 属性 对象。properties 对象定义一组属性,用于配置步骤的每个表单控制。另请参阅: 用户界面属性的描述

  • 操作 定义连接器可以执行的操作,或者连接间步骤执行的操作。只有连接器和步骤扩展使用您指定的操作。操作规格的格式如下:

    {
        "id": "",
        "name": "",
        "description": "",
        "actionType": "step|connector",
        "descriptor": {
        }
    }
    Copy to Clipboard Toggle word wrap
    • id 是操作的唯一 ID。这至少应在 Syndesis 环境中唯一。
    • name 是 Fuse Online 中显示的操作名称。该集成商将此值视为连接操作的名称,或作为在连接间集成数据的一个步骤名称。
    • description 是 Fuse Online 中显示的操作描述。使用此字段来帮助集成商了解该操作的作用。
    • actionType 指示某个连接是否由连接间的步骤执行。
    • 描述符 指定嵌套属性,如 kindentrypointinputDataTypeoutputDatatype 等等。
  • 依赖项 定义扩展需要 Fuse Online 来提供的资源。

    定义依赖项,如下所示:

    {
      "type": "MAVEN",
      "id"   : "org.apache.camel:camel-telegram:jar:2.21.0"
    }
    Copy to Clipboard Toggle word wrap
    • type 表示依赖项的类型。指定 MAVEN。(预计将来会支持其他类型。)
    • id 是 Maven 依赖项的 ID,它是一个 Maven GAV。

9.3.5. 用户界面属性描述

在连接器扩展和步骤扩展中,在扩展定义 JSON 文件或 Java 类文件中指定用户界面属性。这些属性的设置定义 HTML 表单控制,Fuse Online 用户在 Fuse Online 用户创建连接时显示,配置连接操作,或者配置扩展提供的步骤。

您必须为每个要出现在 Fuse Online 控制台中的扩展用户界面中的格式控制指定属性。对于每个形式控制,以任何顺序指定部分或所有属性。

用户界面属性规格示例

在 IRC 连接器一部分的 JSON 文件中,顶级 属性 对象定义了在 Fuse Online 用户选择 IRC 连接器后出现的 HTML 表单控制来创建连接。有三种形式控制的属性定义: 主机名密码 和端口

"properties": {
   "hostname": {
     "description": "IRC Server hostname",
     "displayName": "Hostname",
     "labelHint": "Hostname of the IRC server to connect to",
     "order": "1",
     "required": true,
     "secret": false,
     "type": "string"
   },
   "password": {
     "description": "IRC Server password",
     "displayName": "Password",
     "labelHint": "Required if IRC server requires it to join",
     "order": "3",
     "required": false,
     "secret": true,
     "type": "string"
   },
   "port": {
     "description": "IRC Server port",
     "displayName": "Port",
     "labelHint": "Port of the IRC server to connect to",
     "order": "2",
     "required": true,
     "secret": false,
     "tags": [],
     "type": "int"
   }
 },
Copy to Clipboard Toggle word wrap

根据这些属性规范,当 Fuse Online 用户选择 IRC 连接器时,Fuse Online 会显示以下对话框:用户在两个必填字段中输入值后,Fuse Online 创建一个 IRC 连接,该连接配置了 Fuse Online 用户输入的值。

Hostname

关于扩展定义 JSON 文件中的 属性 对象

在连接器扩展中:

  • 顶级 属性 对象是必需的。它控制 Fuse Online 用户选择连接器来创建连接时显示的 Fuse Online。此属性 对象包含一组属性,用于为每个表单控制创建连接。
  • actions 对象中,每个操作都有一个 属性 对象。在每个 属性 对象中,每个表单控制都有一个属性来配置该操作。

在步骤扩展中,actions 对象包含 属性 对象。properties 对象定义一组属性,用于配置步骤的每个表单控制。JSON 层次结构如下:

"actions": [
   {
      ...

      "propertyDefinitionSteps": [
         {
            ...

            "properties":
               {
                  "control-ONE": {
                     "type": "string",
                     "displayName": "Topic Name",
                     "order": "2",
                     ...,
                     }

                  "control-TWO": {
                     "type": "boolean",
                     "displayName": "Urgent",
                     "order": "3",
                     ...
                     }

                  "control-THREE": {
                     "type": "textarea",
                     "displayName": "Comment",
                     "order": "1",
                     ...,
                     }
 } } ]
Copy to Clipboard Toggle word wrap

关于 Java 文件中的用户界面属性

要在 Java 文件中定义用户界面表单控制,请在每个类文件中导入 io.syndesis.extension.api.annotations.ConfigurationProperty,用于定义连接、操作或步骤的用户配置。对于您希望 Fuse Online 控制台显示的每个表单控制,请指定 @ConfigurationProperty 注释,后跟属性列表。有关您可以指定的属性的详情,请查看本节末尾的用户界面属性参考表。

以下代码显示了一种表单控制的属性定义。此代码位于示例中,使用 RouteBuilder 开发 Camel 路由:

public class LogAction extends RouteBuilder {
    @ConfigurationProperty(
        name = "prefix",
        description = "The Log body prefix message",
        displayName = "Log Prefix",
        type = "string")
Copy to Clipboard Toggle word wrap

以下代码显示了两个控制的属性定义。这个代码来自使用 Syndesis Step API 的示例:

@Action(id = "split", name = "Split", description = "Split your exchange")
public class SplitAction implements Step {

    @ConfigurationProperty(
        name = "language",
        displayName = "Language",
        description = "The language used for the expression")
    private String language;

    @ConfigurationProperty(
        name = "expression",
        displayName = "Expression",
        description = "The expression used to split the exchange
     private String language;
Copy to Clipboard Toggle word wrap

控制表单输入类型的描述

在各个 HTML 表单控制的属性集合中,type 属性定义 Fuse Online 显示的形式输入类型。有关 HTML 表单输入类型的详情,请参考 https://www.w3schools.com/html/html_form_input_types.asp

下表列出了 Fuse Online 形式控制的可能输入类型。在控制的属性集合中,如果您指定了未知 类型 值,Fuse Online 会显示一个输入字段,它接受一行文本。也就是说,默认值为 "type": "text"

Expand
type 属性的值HTMLFuse Online 显示

布尔值

<input type="checkbox">

用户可以选择或不能选择的复选框。

duration

此自定义控制使 Fuse 在线用户选择时间单位:毫秒、秒、分钟、小时或天。用户还输入了一个数字,Fuse Online 返回了几毫秒。例如:
"properties": {
"period": {
"type": "duration"
"defaultValue": 60000,
"description": "Period",
"displayName": "Period",
"labelHint": "Delay between integration executions.",
"required": true,
"secret": false,
}
}

hidden

<input type="hidden">

此字段没有出现在 Fuse Online 控制台中。您可以使用其他属性指定与此字段关联的数据,如某种文本数据。虽然 Fuse Online 用户无法看到或修改这些数据,但如果用户为 Fuse Online 页面选择 View Source,但隐藏字段在源显示中可见。因此,不要将隐藏字段用于安全目的。

int整数数字

<input type="number">

接受数字的输入字段。

password

<input type="password">

Fuse Online 屏蔽用户输入字段(通常以星号)的输入字段。

选择

一个 & lt;select& gt; 元素,例如:
<select name="targets">
<option value="queue">Queue</option>
<option value="topic">Topic</option>
</select>

具有每个标签/值对条目的下拉列表,您按照表单的 enum 属性来指定。

文本字符串 或任何未知值

<input type="text">'

接受一行文本的输入字段。

textarea

<input type="textarea"

使用 textarea 元素

控制表单用户界面属性的描述

在连接器或步骤扩展中,对于 Fuse Online 控制台中出现的每个 HTML 表单控制,您可以指定下表中所述的一个或多个属性。有关 HTML 表单输入类型的详情,请参考 https://www.w3schools.com/html/html_form_input_types.asp

Expand
属性名称类型描述

type

字符串

控制 Fuse Online 显示的格式控制。详情请查看上表。

cols

number

如果为 textarea 字段设置,控制最初为文本area 控制显示的列数。

controlHintcontrolTooltip

字符串

如果设置,则该值映射到表单控制元素的 HTML title 属性。与具有 title 属性的其他元素一样,当光标悬停在控制上时,会出现一个工具提示。工具提示的内容来自 controlHintcontrolTooltip 属性的值。

dataList

array

如果 type 属性的值是 文本,Fuse Online 将使用 dataList 属性的值来添加 typeahead 支持。指定字符串数组。

defaultValue

根据 type 属性的值而有所不同。

Fuse Online 最初以表单字段中显示这个值。defaultValue 属性的设置的类型应与 type 属性的值匹配。例如,当 type 属性设为 number 时,defaultValue 设置应为数字。如果用户没有更改这个初始字段值,Fuse Online 使用 defaultValue

description

字符串

如果设置,Fuse Online 会在表单控制的下面显示这个值。通常,这是有关控制的简短、有用的消息。

displayName

字符串

Fuse Online 显示这个值。

enum

array

如果设置,Fuse Online 会覆盖 type 属性的任何设置,并实施 选择 控制。将数组指定为一组标签 和值 属性。label 属性在用户界面中作为选择项目的标签出现在用户界面中。value 属性变为对应的选择项的值。

labelHintlabelTooltip

字符串

如果设置,则显示名称旁边会出现一个 ? 图标。当 Fuse Online 用户单击 ? 图标时,将显示 labelHint 属性的值。

max

number

如果为 数字 字段设置,则定义最高可接受的值。

分钟

number

如果为 数字 字段设置,则定义最低的可接受值。

multiple

布尔值

如果选择字段或设置了 enum 属性的字段设置为 true,Fuse Online 会显示一个多选控制,而不是选择下拉菜单。

order

number

决定 Fuse 在线控制台中的控制顺序。Fuse Online 应用一个升序,即首先显示 "order": "1" 的控制。如果没有指定 order 属性,Fuse Online 会以 JSON 文件定义的顺序显示控制。

placeholder

字符串

如果设置,Fuse Online 在输入字段中在 hazed 字体中显示这个值,以帮助用户了解预期的输入。

required

布尔值

控制是否对控制设置 required 属性。若为 true,则 Fuse Online 用户必须输入一个值供该控制使用。

number

如果 type 属性的值是 textarea,则 rows 属性的值控制在文本区域控制中最初显示的行数。

secret

布尔值

如果指定,Fuse Online 会将 control 的 type 属性设置为 password (如果尚未设置)。

9.3.6. 支持扩展的 Maven 插件描述

extension-maven-plugin 支持扩展开发,方法是将扩展名打包为有效的 Spring Boot 模块。对于您在 Java 中实施的步骤扩展,此插件可生成扩展定义 JSON 文件。

在 Maven 项目的 pom.xml 文件中,添加以下插件声明:

<plugin>
    <groupId>io.syndesis.extension</groupId>
    <artifactId>extension-maven-plugin</artifactId>
    <version>${syndesis.version}</version>
    <executions>
        <execution>
        <goals>
            <goal>generate-metadata</goal>
            <goal>repackage-extension</goal>
        </goals>
        </execution>
    </executions>
</plugin>
Copy to Clipboard Toggle word wrap

extension-maven-plugin 定义以下目标:

  • generate-metadata 生成 JSON 扩展定义文件,该文件将位于生成的 JAR 文件中,如下所示:

    1. Maven 从 META-INF/syndesis/syndesis-extension-definition.json 文件中的数据结构规格开始。

      如果您在 XML 中编码,则必须自己定义扩展定义 JSON 文件,且必须指定所有必需的数据结构。

      如果要开发连接器或库扩展,则必须自己定义扩展定义 JSON 文件,且必须指定所有必需的数据结构。

      如果您要在 Java 中开发一个步骤扩展,您可以:

      • 自行创建扩展定义 JSON 文件。
      • 在您的 Java 代码中,指定定义所有必要数据结构的注解。您没有创建扩展定义 JSON 文件。
      • 创建扩展定义 JSON 文件,并指定 some,但不指定所有数据结构。
    2. 对于您在 Java 中开发的步骤扩展,Maven 从代码注解中获取缺少的规格
    3. Maven 添加 dependencies 列表,它指定所提供的依赖项,范围通过 扩展 正文来管理。
  • 重新打包 -extension 软件包扩展名。

    • 未通过 extension-bom 管理的依赖关系和相关传输依赖关系位于生成的 JAR 的 lib 文件夹中。
    • 对于库扩展,其范围是 系统 位于生成的 JAR 的 lib 文件夹中。

例如,假设您的 Maven 项目有以下 pom.xml 文件:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">

  <modelVersion>4.0.0</modelVersion>
  <groupId>com.company</groupId>
  <artifactId>my-extension</artifactId>
  <version>1.0.0</version>
  <name>MyExtension</name>
  <description>A Sample Extension</description>
  <packaging>jar</packaging>

  <dependencyManagement>
    <dependencies>
      <dependency>
        <groupId>io.syndesis.extension</groupId>
        <artifactId>extension-bom</artifactId>
        <version>1.3.10</version>
        <type>pom</type>
        <scope>import</scope>
      </dependency>
    </dependencies>
  </dependencyManagement>

  <dependencies>
    <dependency>
      <groupId>io.syndesis.extension</groupId>
      <artifactId>extension-api</artifactId>
      <scope>provided</scope>
    </dependency>
    <dependency>
      <groupId>com.github.lalyos</groupId>
      <artifactId>jfiglet</artifactId>
      <version>0.0.8</version>
    </dependency>
  </dependencies>

  <build>
    <plugins>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>3.7.0</version>
        <configuration>
          <source>1.8</source>
          <target>1.8</target>
        </configuration>
      </plugin>
      <plugin>
        <groupId>io.syndesis.extension</groupId>
        <artifactId>extension-maven-plugin</artifactId>
        <version>1.3.10</version>
        <executions>
          <execution>
            <goals>
              <goal>generate-metadata</goal>
              <goal>repackage-extension</goal>
            </goals>
          </execution>
        </executions>
      </plugin>
    </plugins>
  </build>
</project>
Copy to Clipboard Toggle word wrap

基于此 pom.xml 文件,生成的扩展定义 JSON 文件如下所示:

{
  "name": "MyExtension",
  "description": "A Sample Extension",
  "extensionId": "com.company:my-extension",
  "version": "1.0.0",
  "dependencies": [ {
    "type": "MAVEN",
    "id": "io.syndesis.extension:extension-api:jar:1.3.10"
  } ],
  "extensionType": "Libraries",
  "schemaVersion": "v1"
}
Copy to Clipboard Toggle word wrap

生成的存档具有此结构和内容:

my-extension-1.0.0.jar
|
+- lib
|  |
|  + jfiglet-0.0.8.jar
|
+- META-INF
  |
  +- MANIFEST.MF
     |
     +- syndesis
        |
        +- syndesis-extension-definition.json
Copy to Clipboard Toggle word wrap

9.3.7. 如何在扩展中指定形成的数据

数据形成保管数据类型元数据,供 data mapper 使用。数据映射器将此元数据转换为内部文档,用于显示数据映射器用户界面中的源和目标数据字段。在连接器或自定义步骤的扩展定义 JSON 文件中,每个操作规格定义一个输入数据图(inputDataShape)和输出数据形成(outputDataShape)。

当您开发扩展时,务必要指定数据形式的属性,允许数据映射程序正确处理和显示源和目标字段。以下数据形成属性会影响数据映射程序行为:

  • kind
  • type
  • 规格
  • name
  • description

关于 kind 属性

数据形成 属性DataShapeKinds enum 代表。kind 属性的可能值有:

  • 任何 表示数据类型不是结构化的。例如,可以是字节阵列或空闲格式文本。当数据映射属性设置为 任何 时,数据映射会忽略形成的数据。换句话说,数据不会出现在 datamapper 中,因此您无法将任何字段映射到或从此数据映射。

    但是,对于自定义连接器,当其 kind 属性设置为 任何 时,Fuse Online 会提示您在配置从自定义连接器中创建的连接时指定输入和/或输出数据类型。当您向集成添加连接时会出现这种情况。您可以指定数据形成的模式类型、您指定的模式类型的适当文档,以及数据类型的名称。

  • 表示没有数据类型。对于形成的输入数据,这表明连接或步骤没有读取数据。对于形成的输出数据,这表明连接或步骤不会修改数据。例如,当输入消息正文传输到输出消息正文时,将 kind 属性设为 none,表示数据仅通过。当 kind 设为 none 时,数据映射会忽略形成的数据。换句话说,数据不会出现在 datamapper 中,因此您无法将任何字段映射到或从此数据映射。
  • Java 表示数据类型由 Java 类表示。按照 "kind": "java" 声明,为 type 属性指定完全限定类名称。例如:

    "outputDataShape": {
         "kind": "java",
         "type": "org.apache.camel.component.telegram.model.IncomingMessage"
    },
    Copy to Clipboard Toggle word wrap
  • JSON-schema 表示数据类型由 JSON 架构表示。当 kind 设为 json-schema 时,请将 JSON 模式指定为数据创建 规范 属性的值。例如:

    "inputDataShape": {
      "description": "Person data",
      "kind": "json-schema",
      "name": "Person",
      "specification": "{\"$schema\":\"http://json-schema.org/draft-04/schema#\",\"title\":\"Person\",\"type\":\"object\",\"properties\":{\"firstName\":{...}}}"
    }
    Copy to Clipboard Toggle word wrap

    SAP Concur 连接器的代码 包含由 JSON 模式 指定的数据图示例

  • JSON-instance 表示数据类型由 JSON 实例表示。当 kind 设为 json-instance 时,请将 JSON 实例指定为数据创建 规范 属性的值。例如:

    "inputDataShape": {
      "description": "Person data",
      "kind": "json-instance",
      "name": "Person",
      "specification": "{\"firstName\":\"John\",...}"
    }
    Copy to Clipboard Toggle word wrap
  • XML-schema 表示数据类型由 XML 模式表示。当 kind 设为 xml-schema 时,请将 XML 架构指定为数据创建 规范 属性的值。例如:

    "inputDataShape": {
      "description": "Person data",
      "kind": "xml-schema",
      "name": "Person",
      "specification": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?><xs:schema xmlns:xs=\"http://www.w3.org/2001/XMLSchema\">...</xs:schema>"
    }
    Copy to Clipboard Toggle word wrap
  • xml-instance 表示数据类型由 XML 实例表示。当 kind 设为 xml-instance 时,请将一个 XML 实例指定为数据创建 规范 属性的值。例如:

    "inputDataShape": {
      "description": "Person data",
      "kind": "xml-instance",
      "name": "Person",
      "specification": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?><Person><firstName>Jane</firstName></Person>"
    }
    Copy to Clipboard Toggle word wrap
  • csv-instance 表示数据类型由 CSV 实例表示。

    kind 设为 csv-instance 时,请将 CSV 实例指定为数据创建 规范 属性的值。例如:

    "inputDataShape": {
      "description": "Person data",
      "kind": "csv-instance",
      "name": "Person",
      "specification":  "John,Doe,120 Jefferson Street,Riverside, NJ, 08075"
    }
    Copy to Clipboard Toggle word wrap

    kind 设为 csv-instance 时,您可以指定以下 布尔值 (true/false)参数:

    Expand
    标签名称描述

    允许 Duplicate Header Names

    allowDuplicateHeaderNames

    允许 CSV 数据的标头行中重复名称。

    Allow Missing Column Names

    allowMissingColumnNames

    在解析 CSV 数据标题行时允许缺少字段名称。

    注释 Marker

    commentMarker

    指定指定 CSV 数据中注释行开头的字符。

    Delimiter

    delimiter

    指定限制 CSV 数据中的值的字符(通常为 ";", "," 或 "\t")。

    Escape

    escape

    指定 CSV 数据的转义字符。

    第一个记录为标头

    firstRecordAsHeader

    使用 CSV 数据中的第一个记录作为标题行。

    忽略 Empty Lines

    ignoreEmptyLines

    忽略 CSV 数据中的任何空行。

    忽略标头问题单

    ignoreHeaderCase

    忽略 CSV 数据标题行中的字母大小写。

    忽略 Surrounding Spaces

    ignoreSurroundingSpaces

    忽略 CSV 数据周围的所有空格字符。

    null String

    nullString

    指定在 CSV 数据中转换为和来自 null 时使用的字符串。

    跳过标头记录

    skipHeaderRecord

    跳过 CSV 数据中的标头记录。

关于 type 属性

kind 属性的值为 java 时,"kind": "java" 声明后跟 类型 声明,用于指定完全限定的 Java 类名称。例如:

"outputDataShape": {
     "kind": "java",
     "type": "org.apache.camel.component.telegram.model.IncomingMessage"
},
Copy to Clipboard Toggle word wrap

kind 属性设为 java 以外的任何其他设置时,type 属性的任何设置将被忽略。

关于 规格 属性

kind 属性的设置决定了 specification 属性的设置,如下表中所示。

Expand
kind 属性设置规格 属性设置

java

Java 检查结果.

对于您在 Java 中写入的每个扩展,请使用 extension-maven-plugin 并至少获取 Java 检查结果。该插件将 Java 检查结果插入到 JSON 扩展文件中,作为 specification 属性的设置。这是获取 Java 检查结果的唯一方法,这是 Fuse Online 中数据映射的唯一方法。

提醒,对于以 Java 编写的步骤扩展,extension-maven-plugin 生成 JSON 扩展定义文件,并使用必要的内容填充该文件。对于连接器扩展,而 extension-maven-plugin 会将 Java 检查结果插入到 JSON 扩展定义文件中,您需要手动添加插件不会插入的内容。

json-schema

实际的 JSON 模式文档。设置不能引用文档,JSON 模式不能通过引用指向其他 JSON 架构文档。

json-instance

包含示例数据的实际 JSON 文档。数据映射程序从示例数据中获取数据类型。此设置不能引用文档。

xml-schema

实际的 XML 模式文档。设置无法引用文档,而 XML 模式无法通过引用指向其他 XML 架构文档。

xml-instance

实际的 XML 实例文档。此设置不能引用文档。

csv-instance

实际的 CSV 实例文档。此设置不能引用文档。

any

specification 属性不是必需的。任何设置都会被忽略。

none

specification 属性不是必需的。任何设置都会被忽略。

关于 name 属性

数据形成的 name 属性指定数据类型的人类可读名称。数据映射程序在其用户界面中显示这个名称作为数据字段的标签。在以下镜像中,Person 是您在其中看到 name 属性的值的示例。

Name example

此名称也会出现在 Fuse Online 流视觉化中的数据类型指示器。

关于 description 属性

数据形成的 description 属性指定当光标悬停在数据映射用户界面中数据类型名称时作为工具提示的文本。

9.3.8. 开发步骤扩展示例

步骤扩展实施一个或多个自定义步骤。每个自定义步骤都实施一个操作,用于在连接间处理集成数据。以下示例演示了开发步骤扩展的替代方案:

Syndesis 提供自定义 Java 注解,您可以与 syndesis-extension-plugin 结合使用。当您在 Java 中实现步骤扩展或连接器扩展时,您可以指定启用 Maven 将操作定义添加到扩展定义 JSON 文件的注解。要启用注解处理,请在 Maven 项目中添加以下依赖项:

<dependency>
  <groupId>io.syndesis.extension</groupId>
  <artifactId>extension-annotation-processor</artifactId>
  <optional>true</optional>
</dependency>
Copy to Clipboard Toggle word wrap

因为 Spring Boot 是集成运行时,要将 Bean 注入 Camel 上下文,请务必遵循标准的 Spring Boot 实践。例如,创建一个自动配置类,并在那里创建 Bean。但是,默认行为是扩展代码不受软件包扫描的影响。因此,您必须在步骤扩展中创建并填充 META-INF/spring.factories 文件。

9.3.8.1. 使用 XML 片段开发 Camel 路由示例

要开发自定义步骤,您可以将操作作为 XML 片段实施,该片段是一个带有 直接输入 的 Camel 路由。Syndesis 运行时会按照调用任何其他 Camel 路由的方式调用此路由。

例如,假设您要创建一个步骤来记录带有可选前缀的消息正文。以下 XML 定义了实现此目的的 Camel 路由。

<?xml version="1.0" encoding="UTF-8"?>
<routes xmlns="http://camel.apache.org/schema/spring"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="
      http://camel.apache.org/schema/spring
      http://camel.apache.org/schema/spring/camel-spring.xsd">

  <route id="log-body-with-prefix">
    <from uri="direct:log"/>
    <choice>
      <when>
        <simple>${header.prefix} != ''</simple>
        <log message="${header.prefix} ${body}"/>
      </when>
      <otherwise>
        <log message="Output ${body}"/>
      </otherwise>
    </choice>
  </route>

</routes>
Copy to Clipboard Toggle word wrap

当您在 XML 中开发扩展时,您必须自行创建扩展定义 JSON 文件。对于这个 XML 片段,src/main/resources/META-INF/syndesis/syndesis-extension-definition.json 文件可以定义操作,如下所示:

{
  "actionType": "step",
  "id": "log-body-with-prefix",
  "name": "Log body with prefix",
  "description": "A simple body log with a prefix",
  "descriptor": {
    "kind": "ENDPOINT", 
1

    "entrypoint": "direct:log", 
2

    "resource": "classpath:log-body-action.xml", 
3

    "inputDataShape": {
      "kind": "none"
    },
    "outputDataShape": {
      "kind": "none"
    },
  "propertyDefinitionSteps": [ {
    "description": "extension-properties",
    "name": "extension-properties",
    "properties": { 
4

      "prefix": {
        "componentProperty": false,
        "deprecated": false,
        "description": "The Log body prefix message",
        "displayName": "Log Prefix",
        "javaType": "String",
        "kind": "parameter",
        "required": false,
        "secret": false,
        "type": "string"
      }
    }
  } ]
  }
}
Copy to Clipboard Toggle word wrap
1
操作的类型设置为 ENDPOINT。运行时调用 Camel 端点来执行此自定义步骤所提供的操作。
2
要调用的 Camel 端点是 direct:log。这是路由中的 来自 规格。
3
这是 XML 片段的位置。
4
这些是在自定义步骤中定义的操作的属性公开到将这一步添加到集成的集成器中。在 Fuse Online 中,集成人员在用户界面中指定的每个值都会映射到与属性同名的消息标头中。在本例中,集成商将看到一个输入字段,Log Prefix 显示名称。如需了解更多详细信息,请参阅 用户界面属性 的描述
警告

Syndesis 不支持完整的 Camel XML 配置。Syndesis 仅支持 <routes> 标签。

9.3.8.2. 使用 RouteBuilder开发 Camel 路由示例

您可通过将操作开发为带 RouteBuilder 类支持的 Camel 路由来实施自定义步骤。此类路由具有输入,如 direct。Syndesis 调用此路由的方式与调用任何其他 Camel 路由一样。

要实现这个示例,请创建一个使用可选前缀记录消息正文的步骤,您可以编写类似如下的内容:

import org.apache.camel.builder.RouteBuilder;

import io.syndesis.extension.api.annotations.Action;
import io.syndesis.extension.api.annotations.ConfigurationProperty;

@Action( 
1

    id = "log-body-with-prefix",
    name = "Log body with prefix",
    description = "A simple body log with a prefix",
    entrypoint = "direct:log")
public class LogAction extends RouteBuilder {
    @ConfigurationProperty( 
2

        name = "prefix",
        description = "The Log body prefix message",
        displayName = "Log Prefix",
        type = "string")
    private String prefix;

    @Override
    public void configure() throws Exception {
        from("direct::start") 
3

            .choice()
                .when(simple("${header.prefix} != ''"))
                    .log("${header.prefix} ${body}")
                .otherwise()
                    .log("Output ${body}")
            .endChoice();
    }
}
Copy to Clipboard Toggle word wrap
1
@Action 注释表示操作定义。
2
@ConfigurationProperty 注释指示用户界面表单控制的定义。详情请查看 用户界面属性 的描述
3
这是操作实施。

此 Java 代码使用 Syndesis 注解,这意味着 extension-maven-plugin 可以自动生成操作定义。在扩展定义 JSON 文件中,操作定义如下:

{
  "id": "log-body-with-prefix",
  "name": "Log body with prefix",
  "description": "A simple body log with a prefix",
  "descriptor": {
    "kind": "ENDPOINT", 
1

    "entrypoint": "direct:log", 
2

    "resource": "class:io.syndesis.extension.log.LogAction", 
3

    "inputDataShape": {
      "kind": "none"
    },
    "outputDataShape": {
      "kind": "none"
    },
    "propertyDefinitionSteps": [ {
      "description": "extension-properties",
      "name": "extension-properties",
      "properties": { 
4

        "prefix": {
          "componentProperty": false,
          "deprecated": false,
          "description": "The Log body prefix message",
          "displayName": "Log Prefix",
          "javaType": "java.lang.String",
          "kind": "parameter",
          "required": false,
          "secret": false,
          "type": "string",
          "raw": false
        }
      }
    } ]
  },
  "actionType": "step"
}
Copy to Clipboard Toggle word wrap
1
的操作类型是 ENDPOINT。运行时调用 Camel 端点来执行此步骤实施的操作。
2
这是要调用的 Camel 端点。它是路由中的 from specification。
3
这是实现 RoutesBuilder 的类。
4
这些是在自定义步骤中定义的操作的属性公开到将这一步添加到集成的集成器中。在 Fuse Online 中,集成人员在用户界面中指定的每个值都会映射到与属性同名的消息标头中。在本例中,集成商将看到一个输入字段,Log Prefix 显示名称。如需更多信息,请参阅 用户界面属性 的描述

您可以通过将操作作为 Camel 路由(支持 RouteBuilder 类以及 Spring Boot)来实施自定义步骤。在本例中,Spring Boot 是在 Camel 上下文中注册 RouteBuilder 对象的工具。Syndesis 调用此路由的方式与调用任何其他 Camel 路由一样。

要实现这个示例,请创建一个使用可选前缀记录消息正文的步骤,您可以编写类似如下的内容:

import io.syndesis.extension.api.annotations.Action;
import io.syndesis.extension.api.annotations.ConfigurationProperty;
import org.apache.camel.builder.RouteBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class ActionsConfiguration {

    @Action( 
1

        id = "log-body-with-prefix",
        name = "Log body with prefix",
        description = "A simple body log with a prefix",
        entrypoint = "direct:log")
    @ConfigurationProperty( 
2

        name = "prefix",
        description = "The Log body prefix message",
        displayName = "Log Prefix",
        type = "string")
    @Bean 
3

    public RouteBuilder logBodyWithprefix() {
        return new RouteBuilder() {
            @Override
            public void configure() throws Exception {
                from("direct::start") 
4

                    .choice()
                        .when(simple("${header.prefix} != ''"))
                            .log("${header.prefix} ${body}")
                        .otherwise()
                            .log("Output ${body}")
                    .endChoice();
             }
        };
    }
}
Copy to Clipboard Toggle word wrap
1
@Action 注释表示操作定义。
2
@ConfigurationProperty 注释指示用户界面表单控制的定义。详情请查看 用户界面属性 的描述
3
RouteBuilder 对象注册为 bean。
4
这是操作实施。

此 Java 代码使用 Syndesis 注解,这意味着 extension-maven-plugin 可以自动生成操作定义。在扩展定义 JSON 文件中,操作定义如下:

{
  "id": "log-body-with-prefix",
  "name": "Log body with prefix",
  "description": "A simple body log with a prefix",
  "descriptor": {
    "kind": "ENDPOINT", 
1

    "entrypoint": "direct:log", 
2

    "inputDataShape": {
      "kind": "none"
    },
    "outputDataShape": {
      "kind": "none"
    },
    "propertyDefinitionSteps": [ {
      "description": "extension-properties",
      "name": "extension-properties",
      "properties": { 
3

        "prefix": {
          "componentProperty": false,
          "deprecated": false,
          "description": "The Log body prefix message",
          "displayName": "Log Prefix",
          "javaType": "java.lang.String",
          "kind": "parameter",
          "required": false,
          "secret": false,
          "type": "string",
          "raw": false
        }
      }
    } ]
  },
  "actionType": "step"
}
Copy to Clipboard Toggle word wrap
1
的操作类型是 ENDPOINT。运行时调用 Camel 端点来执行此步骤实施的操作。
2
这是要调用的 Camel 端点。它是路由中的 from specification。
3
这些是在自定义步骤中定义的操作的属性公开到将这一步添加到集成的集成器中。在 Fuse Online 中,集成人员在用户界面中指定的每个值都会映射到与属性同名的消息标头中。在本例中,集成商将看到一个输入字段,Log Prefix 显示名称。如需了解更多详细信息,请参阅 用户界面属性 的描述
重要

要使配置类可以被 Spring Boot 发现,您必须在名为 META-INF/spring.factories 的文件中列出它们,例如:

org.springframework.boot.autoconfigure.EnableAutoConfiguration=com.company.ActionsConfiguration

在 Spring Boot 时,您最终在配置类中注册的每个 bean 都可用于 Camel 上下文。详情请参阅 Spring Boot 文档,以了解您自己的自动配置

9.3.8.4. 使用 Camel Bean 的示例

您可以通过将操作作为 Camel Bean 处理器来实施自定义步骤。要实现这个示例,请创建一个使用可选前缀记录消息正文的步骤,您可以编写类似如下的内容:

import org.apache.camel.Body;
import org.apache.camel.Handler;
import org.apache.camel.Header;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import io.syndesis.extension.api.annotations.Action;
import io.syndesis.extension.api.annotations.ConfigurationProperty;

@Action(
    id = "log-body-with-prefix",
    name = "Log body with prefix",
    description = "A simple body log with a prefix")
public class LogAction  {
    private static final Logger LOGGER = LoggerFactory.getLogger(LogAction.class);

    @ConfigurationProperty(
        name = "prefix",
        description = "The Log body prefix message",
        displayName = "Log Prefix",
        type = "string")
    private String prefix;

    @Handler 
1

    public void process(@Header("prefix") String prefix, @Body Object body) {
        if (prefix == null) {
            LOGGER.info("Output {}", body);
        } else {
            LOGGER.info("{} {}", prefix, body);
        }
    }
}
Copy to Clipboard Toggle word wrap
1
这是实施该操作的功能。

此 Java 代码使用 Syndesis 注解,这意味着 extension-maven-plugin 可以自动生成操作定义。在扩展定义 JSON 文件中,操作定义如下:

{
  "id": "log-body-with-prefix",
  "name": "Log body with prefix",
  "description": "A simple body log with a prefix",
  "descriptor": {
    "kind": "BEAN", 
1

    "entrypoint": "io.syndesis.extension.log.LogAction::process", 
2

    "inputDataShape": {
      "kind": "none"
    },
    "outputDataShape": {
      "kind": "none"
    },
    "propertyDefinitionSteps": [ {
      "description": "extension-properties",
      "name": "extension-properties",
      "properties": {
        "prefix": { 
3

          "componentProperty": false,
          "deprecated": false,
          "description": "The Log body prefix message",
          "displayName": "Log Prefix",
          "javaType": "java.lang.String",
          "kind": "parameter",
          "required": false,
          "secret": false,
          "type": "string",
          "raw": false
        }
      }
    } ]
  },
  "actionType": "step"
}
Copy to Clipboard Toggle word wrap
1
操作的类型是 BEAN。运行时调用 Camel Bean 处理器,以便在此自定义步骤中执行操作。
2
这是要调用的 Camel Bean。
3
这些是在自定义步骤中定义的操作的属性公开到将这一步添加到集成的集成器中。在 Fuse Online 中,集成人员在用户界面中指定的每个值都会映射到与属性同名的消息标头中。在本例中,集成商将看到一个输入字段,Log Prefix 显示名称。如需了解更多详细信息,请参阅 用户界面属性 的描述

使用 Bean 时,您可能会方便地将用户属性注入 bean,而不是从交换标头中检索它们。为此,请为您要注入的属性实施 getter 和 setter 方法。操作实施如下所示:

import org.apache.camel.Body;
import org.apache.camel.Handler;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import io.syndesis.extension.api.annotations.Action;
import io.syndesis.extension.api.annotations.ConfigurationProperty;

@Action(
    id = "log-body-with-prefix",
    name = "Log body with prefix",
    description = "A simple body log with a prefix")
public class LogAction  {
    private static final Logger LOGGER = LoggerFactory.getLogger(LogAction.class);

    @ConfigurationProperty(
        name = "prefix",
        description = "The Log body prefix message",
        displayName = "Log Prefix",
        type = "string")
    private String prefix;

    public void setPrefix(String prefix) { 
1

        this.prefix = prefix;
    }

    public String getPrefix() { 
2

        return prefix;
    }

    @Handler
    public void process(@Body Object body) {
        if (this.prefix == null) {
            LOGGER.info("Output {}", body);
        } else {
            LOGGER.info("{} {}", this.prefix, body);
        }
    }
}
Copy to Clipboard Toggle word wrap
1
这是属性 setter 方法。
2
这是属性 getter 方法。

9.3.8.5. 使用 Syndesis 步骤 API 的示例

您可以使用 Syndesis Step API 来实施自定义步骤。这提供了一种与运行时路由创建交互的方法。您可以使用 ProcessorDefinition 类提供的任何方法,您可以创建更复杂的路由。Syndesis API 的信息是 http://javadoc.io/doc/io.syndesis.extension/extension-api

以下是一个步骤扩展示例,它使用 Syndesis Step API 来实现拆分操作:

import java.util.Map;
import java.util.Optional;

import io.syndesis.extension.api.Step;
import io.syndesis.extension.api.annotations.Action;
import io.syndesis.extension.api.annotations.ConfigurationProperty;
import org.apache.camel.CamelContext;
import org.apache.camel.model.ProcessorDefinition;
import org.apache.camel.util.ObjectHelper;
import org.apache.camel.Expression;
import org.apache.camel.builder.Builder;
import org.apache.camel.processor.aggregate.AggregationStrategy;
import org.apache.camel.processor.aggregate.UseOriginalAggregationStrategy;
import org.apache.camel.spi.Language;

@Action(id = "split", name = "Split", description = "Split your exchange")
public class SplitAction implements Step {

    @ConfigurationProperty(
        name = "language",
        displayName = "Language",
        description = "The language used for the expression")
    private String language;

    @ConfigurationProperty(
        name = "expression",
        displayName = "Expression",
        description = "The expression used to split the exchange")
    private String expression;

    public String getLanguage() {
        return language;
    }

    public void setLanguage(String language) {
        this.language = language;
    }

    public String getExpression() {
        return expression;
    }

    public void setExpression(String expression) {
        this.expression = expression;
    }

    @Override
    public Optional<ProcessorDefinition> configure(
            CamelContext context,
            ProcessorDefinition route,
            Map<String, Object> parameters) { 
1


        String languageName = language;
        String expressionDefinition = expression;

        if (ObjectHelper.isEmpty(languageName) && ObjectHelper.isEmpty(expressionDefinition)) {
            route = route.split(Builder.body());
        } else if (ObjectHelper.isNotEmpty(expressionDefinition)) {

            if (ObjectHelper.isEmpty(languageName)) {
                languageName = "simple";
            }

            final Language splitLanguage = context.resolveLanguage(languageName);
            final Expression splitExpression = splitLanguage.createExpression(expressionDefinition);
            final AggregationStrategy aggreationStrategy = new UseOriginalAggregationStrategy(null, false);

            route = route.split(splitExpression).aggregationStrategy(aggreationStrategy);
        }

        return Optional.of(route);
    }
}
Copy to Clipboard Toggle word wrap
1
这是自定义步骤执行的操作的实施。

此 Java 代码使用 Syndesis 注解,这意味着 extension-maven-plugin 可以自动生成操作定义。在扩展定义 JSON 文件中,操作定义如下:

{
  "id": "split",
  "name": "Split",
  "description": "Split your exchange",
  "descriptor": {
    "kind": "STEP", 
1

    "entrypoint": "io.syndesis.extension.split.SplitAction", 
2

    "inputDataShape": {
      "kind": "none"
    },
    "outputDataShape": {
      "kind": "none"
    },
    "propertyDefinitionSteps": [ {
      "description": "extension-properties",
      "name": "extension-properties",
      "properties": {
        "language": {
          "componentProperty": false,
          "deprecated": false,
          "description": "The language used for the expression",
          "displayName": "Language",
          "javaType": "java.lang.String",
          "kind": "parameter",
          "required": false,
          "secret": false,
          "type": "string",
          "raw": false
        },
        "expression": {
          "componentProperty": false,
          "deprecated": false,
          "description": "The expression used to split the exchange",
          "displayName": "Expression",
          "javaType": "java.lang.String",
          "kind": "parameter",
          "required": false,
          "secret": false,
          "type": "string",
          "raw": false
        }
      }
    } ]
  },
  "tags": [],
  "actionType": "step"
}
Copy to Clipboard Toggle word wrap
1
操作的类型是 STEP
2
这是实施 Step 接口的类。

其他资源

有关用户界面属性的详情,请参阅 用户界面属性 的描述

9.3.9. 开发连接器扩展示例

如果 Fuse Online 没有为您希望在集成中使用的应用程序或服务提供连接器,则经验丰富的开发人员可以编码一个扩展功能,为 Fuse Online 提供新的连接器。本文档介绍了开发连接器扩展名的介绍。有关开发连接器的详情,请参阅在 Syndesis 社区网站上开发 Syndesis 连接器

重要

对于连接器扩展,还无法从 Java 代码自动生成扩展定义 JSON 文件。

连接器本质上是 Camel 组件的代理。连接器配置底层组件,并根据在扩展定义中定义的选项以及 Fuse Online Web 界面收集的选项中创建端点。

连接器扩展定义使用下列额外数据结构扩展了步骤扩展所需的扩展定义:

  • componentScheme

    定义连接器使用的 Camel 组件。您可以为连接器或操作设置 componentScheme。如果您为连接器和动作设置了 componentScheme,则操作的设置具有优先权。

  • 连接器客户

    指定实施 ComponentProxyCustomizer 类的类列表。每个类自定义连接器的行为。例如,在类应用到底层组件/endpoint,或者类可能会添加 pre/post 端点逻辑前,一个类可能会对属性进行操作。对于每个类,指定实施的完整类名称,如 com.mycomponent.MyCustomizer。您可以对动作和 连接器设置连接器定制器。根据设置的内容,Fuse Online 首先将自定义程序应用于连接器,然后再进行操作。

  • connectorFactory

    定义实现 component ProxyonnectionFactoryy 类的类,该类创建和/或配置底层组件/端点。指定实施的完整类名称。您可以为 连接器或 动作设置连接器。操作具有优先权。

Customizer 示例

以下定制示例从单独的选项中设置 DataSource:

public class DataSourceCustomizer implements ComponentProxyCustomizer, CamelContextAware {
    private final static Logger LOGGER = LoggerFactory.getLogger(DataSourceCustomizer.class);

    private CamelContext camelContext;

    @Override
    public void setCamelContext(CamelContext camelContext) { 
1

        this.camelContext = camelContext;
    }

    @Override
    public CamelContext getCamelContext() { 
2

        return this.camelContext;
    }

    @Override
    public void customize(ComponentProxyComponent component, Map<String, Object> options) {
        if (!options.containsKey("dataSource")) {
            if (options.containsKey("user") && options.containsKey("password") && options.containsKey("url")) {
                try {
                    BasicDataSource ds = new BasicDataSource();

                    consumeOption(camelContext, options, "user", String.class, ds::setUsername); 
3

                    consumeOption(camelContext, options, "password", String.class, ds::setPassword); 
4

                    consumeOption(camelContext, options, "url", String.class, ds::setUrl); 
5


                    options.put("dataSource", ds);
                } catch (@SuppressWarnings("PMD.AvoidCatchingGenericException") Exception e) {
                    throw new IllegalArgumentException(e);
                }
            } else {
                LOGGER.debug("Not enough information provided to set-up the DataSource");
            }
        }
    }
}
Copy to Clipboard Toggle word wrap
1 2
 通过实施 CamelContextAware,Syndesis 注入 Camel 上下文,然后调用自定义方法。
3 4 5
 处理选项,然后从选项映射中删除这些选项。

注入属性示例

如果定制的 Java 约定,您也可以注入属性,如上例的这个修订版本所示:

public class DataSourceCustomizer implements ComponentProxyCustomizer, CamelContextAware {
    private final static Logger LOGGER = LoggerFactory.getLogger(DataSourceCustomizer.class);

    private CamelContext camelContext;
    private String userName;
    private String password;
    private String url;

    @Override
    public void setCamelContext(CamelContext camelContext) { 
1

        this.camelContext = camelContext;
    }

    @Override
    public CamelContext getCamelContext() { 
2

        return this.camelContext;
    }

    public void setUserName(String userName) { 
3

      this.userName = userName;
    }

    public String getUserName() { 
4

      return this.userName;
    }

    public void setPassword(String password) { 
5

      this.password = password;
    }

    public String getPassword() { 
6

      return this.password;
    }

    public void setUrl(String url) { 
7

      this.url = url;
    }

    public String getUrl() { 
8

      return this.url;
    }

    @Override
    public void customize(ComponentProxyComponent component, Map<String, Object> options) {
        if (!options.containsKey("dataSource")) {
            if (userName != null && password != null && url != null) {
                try {
                    BasicDataSource ds = new BasicDataSource();
                    ds.setUserName(userName);
                    ds.setPassword(password);
                    ds.setUrl(url);

                    options.put("dataSource", ds);
                } catch (@SuppressWarnings("PMD.AvoidCatchingGenericException") Exception e) {
                    throw new IllegalArgumentException(e);
                }
            } else {
                LOGGER.debug("Not enough information provided to set-up the DataSource");
            }
        }
    }
}
Copy to Clipboard Toggle word wrap
1 2 3
 通过实施 CamelContextAware,Syndesis 注入 Camel 上下文,然后调用自定义方法。此示例代码会覆盖 setCamelContext()getCamelContext() 方法,并设置用户名。
4 5 6 7 8
 示例代码处理注入的选项,并从选项映射中自动删除它们。

使用自定义器配置 before/after 逻辑

您可以使用一个自定义器配置 before/after 逻辑,如下例所示:

public class AWSS3DeleteObjectCustomizer implements ComponentProxyCustomizer {
  	private String filenameKey;

    public void setFilenameKey(String filenameKey) {
      this.filenameKey = filenameKey;
    }

    public String getFilenameKey() {
        return this.filenameKey;
    }

    @Override
    public void customize(ComponentProxyComponent component, Map<String, Object> options) {
      	component.setBeforeProducer(this::beforeProducer);
    }

    public void beforeProducer(final Exchange exchange) throws IOException {
      	exchange.getIn().setHeader(S3Constants.S3_OPERATION, S3Operations.deleteObject);

    	  if (filenameKey != null) {
    		    exchange.getIn().setHeader(S3Constants.KEY, filenameKey);
    	  }
    }
}
Copy to Clipboard Toggle word wrap

自定义 component ProxyComponent的行为

component ProxyonnectionFactory y 类创建 和/或配置底层组件/端点。要自定义 ComponentProxyComponent 对象的行为,您可以覆盖 component Proxy onnectionFactoryy 创建的任何行为:

  • createDelegateComponent()

    Syndesis 在代理启动时调用这个方法,它最终使用 componentScheme 选项定义的方案创建组件的专用实例。

    这个方法的默认行为是决定是否在组件级别应用任何连接器/操作选项。只有在端点无法应用同一选项时,方法会创建一个自定义组件实例,并根据适用的选项进行配置。

  • configureDelegateComponent()

    只有在创建了自定义组件实例来配置委派的组件实例的额外行为时,Syndesis 调用这个方法。

  • createDelegateEndpoint()

    当代理创建端点时,Syndesis 调用这个方法,默认情况下,使用 Camel 目录工具创建端点。

  • configureDelegateEndpoint()

    创建委派的端点后,Syndesis 调用此方法来配置委派的端点实例的额外行为,例如:

    public class IrcComponentProxyFactory implements ComponentProxyFactory {
    
        @Override
        public ComponentProxyComponent newInstance(String componentId, String componentScheme) {
            return new ComponentProxyComponent(componentId, componentScheme) {
                @Override
                protected void configureDelegateEndpoint(ComponentDefinition definition, Endpoint endpoint, Map<String, Object> options) throws Exception {
                    if (!(endpoint instanceof IrcEndpoint)) {
                        throw new IllegalStateException("Endpoint should be of type IrcEndpoint");
                    }
    
                    final IrcEndpoint ircEndpoint = (IrcEndpoint)endpoint;
                    final String channels = (String)options.remove("channels");
    
                    if (ObjectHelper.isNotEmpty(channels)) {
                        ircEndpoint.getConfiguration().setChannel(
                            Arrays.asList(channels.split(","))
                        );
                    }
                }
            };
        }
    }
    Copy to Clipboard Toggle word wrap

9.3.10. 如何开发库扩展

库扩展提供了在运行时集成需要的资源。库扩展不会向 Fuse Online 贡献步骤或连接器。

保存集成时,您可以选择要与集成包括的一个或多个导入库扩展。

库扩展不会定义任何操作。以下是库扩展的示例定义:

{
  "schemaVersion" : "v1",
  "name" : "Example Library Extension",
  "description" : "Syndesis Extension for adding a runtime library",
  "extensionId" : "io.syndesis.extensions:syndesis-library",
  "version" : "1.0.0",
  "tags" : [ "my-libraries-extension" ],
  "extensionType" : "Libraries"
}
Copy to Clipboard Toggle word wrap

另请参阅示例库扩展: https://github.com/syndesisio/syndesis-extensions

除操作之外,库扩展的结构与步骤或连接器扩展的结构相同。

在用于创建库扩展的 Maven 项目中,添加来自 Maven 存储库无法的依赖项,指定 系统依赖项,例如:

<dependency>
    <groupId>com.company</groupId>
    <artifactId>my-library-extension</artifactId>
    <version>1.0</version>
    <scope>system</scope>
    <systemPath>${project.basedir}/lib/my-library-extension.jar</systemPath>
</dependency>
Copy to Clipboard Toggle word wrap

9.3.11. 创建 JDBC 驱动程序库扩展

要连接到 Apache Derby、MySQL 和 PostgreSQL 以外的 SQL 数据库,您可以创建一个库扩展来打包您要连接到的数据库的 JDBC 驱动程序。将这个扩展上传到 Fuse Online 后,Fuse 在线提供的数据库连接器可以访问驱动程序以验证并创建专有数据库的连接。您不能为特定数据库创建新连接器。

Syndesis 开源社区提供了一个项目,用于创建一个可嵌套 JDBC 驱动程序的扩展。

仅打包扩展中的一个驱动程序。这样可以更轻松地管理扩展,作为管理特定数据库的一部分。但是,可以创建可包装多个驱动程序的库扩展。

先决条件

要使用 Syndesis 项目,您必须有一个 GitHub 帐户。

流程

  1. 通过执行以下操作之一,确保连接到的数据库访问 JDBC 驱动程序:

    1. 确认该驱动程序位于 Maven 存储库中。
    2. 下载驱动程序。
  2. 在浏览器标签页中,访问 https://github.com/syndesisio/syndesis-extensions
  3. syndesis-extensions 存储库派生到您的 GitHub 帐户。
  4. 从您的 fork 创建本地克隆。
  5. syndesis-extensions 克隆中:

    1. 如果驱动程序不在 Maven 存储库中,请将驱动程序复制到 syndesis-library-jdbc-driver/lib 文件夹中。
    2. 编辑 syndesis-library-jdbc-driver/pom.xml 文件:

      1. Name 元素的值更新为您为这个扩展选择的名称。
      2. 更新 Description 元素的值,以提供有关此扩展的信息。
      3. 如果您已经将驱动程序复制到 syndesis-library-jdbc-driver/lib,请确保 pom.xml 中的 systemPath 指向该驱动程序文件。(可选)更改 groupIdartifactIdversion,以根据驱动程序反映正确的值。
      4. 如果驱动程序位于 Maven 存储库中,请确保对 Maven 依赖项的引用位于 pom.xml 文件中。
      5. 检查 pom.xml 文件的其余内容,并根据需要更改所有相关元数据。
    3. 执行 ./mvnw -pl :syndesis-library-jdbc-driver clean 软件包 以构建扩展。

生成的 .jar 文件位于 syndesis-library-jdbc-driver/target 文件夹中。将这个 .jar 文件导入为 Fuse Online 中的扩展。

导入库扩展后,当您在 Fuse Online 中保存集成时,您可以选择导入的库扩展并将其与集成相关联。

返回顶部
Red Hat logoGithubredditYoutubeTwitter

学习

尝试、购买和销售

社区

关于红帽文档

通过我们的产品和服务,以及可以信赖的内容,帮助红帽用户创新并实现他们的目标。 了解我们当前的更新.

让开源更具包容性

红帽致力于替换我们的代码、文档和 Web 属性中存在问题的语言。欲了解更多详情,请参阅红帽博客.

關於紅帽

我们提供强化的解决方案,使企业能够更轻松地跨平台和环境(从核心数据中心到网络边缘)工作。

Theme

© 2025 Red Hat