【问题标题】:How does DataWeave know what reader/writer to use? (Mule 4)DataWeave 是如何知道使用什么读写器的? (骡子 4)
【发布时间】:2018-03-23 15:15:28
【问题描述】:
【问题讨论】:
标签:
esb
dataweave
mule-esb
【解决方案1】:
我将尝试解释 DW 在 mule 中的工作原理:
输入部分
- Mule 有一个特殊的对象调用 TypedValue,这个类代表一个 Pair,DataType = Pair。
- 所有变量、有效负载都是 TypedValue。它也可能出现在更多嵌套的地方。例如 File 中的 list 操作返回一个 List ,所以 payload 将是 TypedValue, DataType> 所以这允许我们同时列出不同类型的文件 json, xml 等,dw 来读取它们。
DW 使用 DataType 部分根据 MimeType 确定要使用的阅读器以及如何根据 mimetype 属性配置该阅读器(编码、阅读器属性)
输出部分
DW 总是输出一个 TypedValue。现在有趣的部分是 DW 如何推断驱动编写器使用的 DataType 部分。
- 如果用户使用输出指令在脚本中指定它,那么这很容易
- 如果正在执行的脚本分配给消息处理器字段,那么引擎将根据该字段的元数据向 DW 提示预期类型是什么。例如。如果它是 Pojo,那么 DW 将知道要实例化什么类,并且知道它需要使用 Java Writer,因此用户不需要知道所有内部内容。
-
有趣的部分是当我们不知道例如 set-payload 时。那么逻辑是这样的:
DW 将查看脚本并查看正在使用的输入,如果它们都是相同/兼容的 DataType,那么它将使用它。这意味着如果在您的脚本中输入<set-payload value="#[payload.foo]/>,我们将查看有效负载的类型,如果有效负载是 Json,那么我们将使用 Json 编写器。现在,如果使用了多个输入并且它们来自不同的 DataType,则会引发错误,即 <set-payload value="#[payload.foo ++ vars.bar]/> 是 xml 类型的 vars.bar 和 Json 类型的 payload。因此,有时特别是在 xml 上,您可能会在一组有效负载上编写表达式,但您可能会失败,因为它最终成为无效的 xml(例如多个根)。
如果没有使用输入,则使用 Java 编写器。所以<set-payload value="#[{a: true}]/> 将输出一个带有条目的 java.util.Map ("a", true)
对于Logger 消息处理器,我们做了一个特殊的事情来避免日志错误。我们尝试使用#3 下的逻辑,但如果由于编写器无法发出该数据结构而失败,那么我们使用 DataWeave 编写器,它可以编写任何可能的数据结构,因为 dw 语言基本上是它处理的所有格式的超集(它包含了它们的所有特性:对象、数组、命名空间、数字、字符串等......)
希望这能解释清楚