ESB - 消息格式





5.00/5 (4投票s)
关于在实施 ESB 时消息格式选项的讨论
引言
在我的上一篇文章中,我讨论了ESB路由机制,展示了如何为ESB创建一个简单的报告框架,并创建了ESB中所需的组件,以演示运行ESB所需的工作量(或很少)。其目的是对ESB的所有部分进行务实的讨论,并揭示在实施或重构实施时应指导您选择的一些因素。
在本文中,我将讨论消息、它们的格式和转换。在后面的文章中,我打算更广泛地讨论自研与商业实现。
消息
在这种上下文中,消息显然是从一个系统流向另一个系统的消息,或者更具体地说,是从一个系统发布,并转换后被一个或多个其他系统消费的消息。因此可以看出,描述相同“事务”的消息不止一个,并且有几个因素应指导这些消息最终应该是什么样子。
格式
消息可以采用各种格式。然而,通常源系统的应用程序设计者会选择一些标准来遵守,以便在创建消息时为自己提供便利,更重要的是为消费者提供便利,因为他们可能了解格式规范,从而知道期望什么。像SAP一样定义自己的格式(idoc)需要很大的自信,而且很难看到这样做的好处。无论如何,发布数据的格式通常由发布系统的限制决定。
在大多数情况下,系统能够生成json或XML格式的消息,在更好的方案出现之前,我强烈建议将其中一种用于事务消息,并尽可能避免自定义格式。Json和XML都有巨大的好处,即它们是自解释和明确的,因为它们是可读和易于理解的,无论是数据是什么(如果值已被赋予合理的名称)还是它们的类型。
在其他上下文中,例如更面向批处理的集成,其中大量统一消息以固定间隔移动,显式格式(如json和XML)的开销可能没有意义,更压缩、解释性更低的格式(如CSV文件)可能更受欢迎——但这不在本文讨论的范围之内。
同样,消费系统的通用方法是公开一个API,一些Web服务——SOAP或REST或两者兼有——并将这些API调用的主体设为json或XML。我的印象是,目前json在SaaS世界中正在迅速普及。有些提供两者之间的选择。
Json和XML并非等同,尽管它们之间的选择讨论常常带有宗教色彩,但有些差异值得考虑。
首先,XML可以通过XSD伴随特定消息类型的定义,即:描述消息应遵守定义的上下文、消息的结构、可能或必须存在的各个字段、它们的基数和数据类型以及任何其他属性。这是数据生产者创建的定义,可以说是一种描述所交付内容的描述。基于此,可以对当前消息进行非常严格的验证。对于某些应用程序,如果XML不伴随至少一个命名空间,则它无效——XML文档/消息类型由其命名空间和其根元素名称唯一定义。然而,XML也可以以更宽松、无命名空间的方式使用。
Json没有这些。它更精简——这可能是它受欢迎的原因——而且它非常易读。然而,仍然可以创建一个模式来描述json应该是什么样子。这种契约可以在RAML文件中描述,但与XML不同的是,这通常由消息的接收方设置,以确保对接收到的消息应该是什么样子有规则,并提供一种拒绝不符合格式的消息的方法。
其次,XML拥有遍历、查询和转换消息的标准工具。XPath、XQuery和XSLT在各自领域都是非常强大的标准工具。在ESB上下文中,XSLT转换工具当然具有特别的意义。
我认为可以公平地说,这些工具中的每一个在json世界中都有几个同样有效的对应物,但它们不是标准,这意味着大多数开发人员需要经历一个学习曲线,如果你遇到问题,在巨大的谷歌世界中往往只有有限的知识可以帮助你。
转换
我想,此时听起来我像是XML的拥护者。我不是。我发现json非常灵活——它与Java对象的紧密相似性以及易于转换为Java和JavaScript对象,使json在许多上下文中都非常有吸引力。在之前的一篇文章中,我展示了如何在精简的ESB实现中的所有点使用json,以及如何使用基于模板的转换工具进行转换。此实现只是初步的,主要用作启发,但它确实勾勒出了一个原则,并且模板工具的使用可以成熟到企业级别。
但我认为这些格式的优点以及它们与ESB的关系值得考虑。
Json简单且被广泛支持(很难找到不支持json的编程语言),它不一定绑定到格式规范,但可以在接收端进行验证——简而言之,它非常适合ESB的API/前端。
另一方面,XML在转换上下文中非常强大。它拥有用于识别和查找元素(XPath
)以及转换整个文档(XSLT)的标准化语言。
为了让事情变得更有趣,市面上有很多库可以实现json到XML(反之亦然)的完全通用转换。我认为提供一个接收json并将其转换为XML的API是一个有趣的案例。然后,消费者可以利用XSLT提取/转换为相关文档,如果需要,该文档可以在交付前转换回json。
(请注意,在所描述的方案中,将XML转换为json时遇到的结构性挑战之一——标签属性——可以完全避免)。
当然,这只是一个思想实验,但我认为它有很多值得借鉴之处。这也意味着开发人员需要精通处理json和XML。然而,这个提议也触及了另一个常见需求:在单个消息的处理中需要更多步骤。在所描述的方案中,所有传入消息都将转换为XML,然后发布到路由机制,例如,发布到Rabbit MQ中的一个或多个交换机。然后,每个消费者将通过XSLT转换相关(订阅的)消息。最后,XML文档可能会被转换为json以交付给目标系统。
创建这些步骤的简单方法是在每个步骤之间将消息发布到路由机制。这会带来队列或通道等开销,但它也提供了对问题可能出在哪里以及提供了出色的调试机会的良好洞察。
这种设计的优点在于所有组件都可以是完全通用的:接收 JSON 消息并将其转换为 XML 的 Web 服务。转换都是相同的,只有消息和 XSLT 不同,因此这应该在消费者实例化时可配置。最后,从 XML 到 JSON 的转换又可以是通用的。
另一个有趣的方面是,每个组件都可以被视为一个完全独立的应用程序。因此,每个应用程序可以用自己的语言编写(例如,利用特定语言库),并且它们可以运行在不同的服务器上。为了可伸缩性,单个消费者实例甚至可以在不同的服务器上运行,它所需要的只是这些服务器能够访问消息队列。
有了这些最后的评论,我将接近一种不同类型的讨论:技术选择和配置。我将在后续文章中探讨这一点。