写点什么

使用 JBoss ESB 和 LegStar 实现大型机整合

  • 2009-05-15
  • 本文字数:7575 字

    阅读完需:约 25 分钟

AI 大模型超全落地场景&金融应用实践,8 月 16 - 19 日 FCon x AICon 大会联诀来袭、干货翻倍!

介绍

2008 年 10 月发行的 Dr Dobbs 杂志中,Michael Swaine 撰写了题为《您的下一代语言是 COBOL 吗?》的文章。他指出,“每年新增的数十亿行 COBOL 代码”证明了当前传统大型机应用的规模和强度仍在继续发展。毫无疑问,整合大型机应用和分布式系统,尤其是基于 Java 的系统,仍然是一个重要的课题。

这些年来人们在大型机集成中积累了很多经验,其中一个惨痛教训是系统间的紧耦合是不可取的。当然,除了大型机应用之外,应用间的技术差异正在进一步 扩大:比如一些应用是基于 COBOL、CICS/IMS,另一些应用是基于 Java、J2EE 、Eclipse 的。具有不同生命周期、由不同开发者使用不同工具开发出的应用之间存在着过多的依赖,这些导致了系统的脆弱和不稳定。

大型机集成商很早就采用了面向服务架构(SOA),这导致了受 SOA 启发的第一代大型机集成解决方案的出现。这些解决方案的大多数是以大型机为中心的,在某种程度上是将 COBOL 绑定到 XML 和直接运行在大型机之上的 SOAP 消息传递系统。

最近,由于某大型 IT 社区对企业集成模式的推广和作为SOA 基础设施的企业服务总线(ESB)的出现,大型机集成有了新的可选架构。本文中,我们将提倡一种以ESB 为中心的大型机集成的新观点,同时也将介绍一种实现这个架构的开源解决方案,即在JBoss ESB 中使用LegStar 实现大型机整合。

以大型机为中心的第一代整合框架所突显出的局限性和成本

Michael Swaine 指出,COBOL 语言正在通过自身不断地发展来支持 XML,像 CICS 系统现在也支持 SOAP。除了 IBM,还有许多供应商在大型机上将 COBOL 绑定到 XML 和 SOAP 协议栈上。近几年来,专注于遗留集成系统的分析师一直赞同这种以大型机为中心的整合方式,即将 XML 和 SOAP 直接运行 在大型机上。

由于当时标准的大型机 SOAP 栈还没有出现,大部分以大型机为中心的集成商不得不开发自己的 SOAP 栈。有些甚至还自己开发 XML 解析器。

然而从那之后,SOA 和 Web 服务发展非常迅速。几年前,只要提供基本的 XML 处理和 SOAP 1.1 就足以声称是面向服务的。再后来,客户对 SOA 的期望和认识逐步清晰,开始采用新标准,如 WS-*。因此对集成商而言,维护自己开发的 SOAP 栈的成本快速增长。

大型机开发人员缺少像开源所能提供的大型开源社区和丰富资源。因此,一些大型机的 SOAP 栈还不支持 SOAP 1.2 或者 WS-Addressing 规范,而这些规范则是许多 WS-* 规范的基础。相比之下,Apache 中最新发布的 Axis2,其大小为 20MB, 其中包括了 59 个 lib,覆盖了 SAAJ(SOAP1.1 和 SOAP1.2)、XML Schema、WSDL 1.1 和 WSDL 2.0、WS-Addressing、Fastinfoset、WS-MetadataExchange、MTOM、WS-Policy 等规范。

另外,许多新技术还在不断涌现,如 RESTful Web Services。在 Google、Yahoo 和 Amazon 的支持下,这类架构越来越受欢迎,并且针对 RESTful Web Services 的 Java API 已经成为 JSR 311 规范,这足以说明 RESTful Web Services 的受欢迎程度。作为 XML 的轻量级替代品的 JSON 也备受关注。比如 Axis2 已经支持 JSON 。在不久的将来,使用 RESTful Web Services 集成大型机应用和对 JSON 的支持很可能会成为需求,而且还可能会给本来就已经很长的需求列表中增加更多的项目。除了基本 Web 服务功能 外,对 Web 服务编排和脚本语言的需求也已经出现,这给以大型机为中心的开发团队带来了更大的压力。

SOAP 出现后,这些以大型机为中心的解决方案,不仅在功能方面长期滞后,而且也遭受了因草率而做出的设计决定所带来的痛苦。

例如,以大型机为中心的解决方案往往将绑定层、消息传递层和传输层紧耦合在一起。相反,开源社区则强调将语言绑定(比如,从 Java 到 XML 的绑 定)从传输和消息传递中清楚地划分出来。在 Java 中,符合 JSR 222 的 Java for XML binding(JAXB)通常是独立于任何 Web 服务技术而实现的;可以将它同 SOAP 或者 RESTful Web Services 一起使用。同样,消息传递和传输通常也是相互独立的,除了可以将 SOAP 消息使用 HTTP/HTTPS 传输之外,也可以将它使用 JMS 或 TCP 传输。因此,以大型机为中心的解决方案很难适应不断变化的 SOA。

在设计上,以大型机为中心的集成解决方案也把大型机作为 IT 基础设施的中心来考虑。分布式应用被看作是大型机的外围应用。这导致了一种非对称的大型 机集成愿景,其中唯一的需求(或是最重要的需求)是这些外围应用消费大型机资源。随着分布式应用重要性的日益显现,大型机应用不再相互孤立。最近,许多以 大型机为中心的集成商感觉到了威胁,并开始提供向外发送请求的功能,但是它们极少经过彻底改造,而这正是支持一个使 IT 基础设施中的大型机角色更为平衡的 愿景所需要的。在大型机上的 SOAP 客户端功能非常薄弱和有限,这严重制约了对外部分布式服务的访问。

最后,以大型机为中心的集成的另一个重要问题就是成本。大型机的软件许可证和维护费用非常昂贵。开源不会或许永远不会涉及到这些费用问题。另外,XML 和 SOAP 处理是一种 CPU 密集型活动。大型机的 CPU 成本仍然相对较高,虽然 IBM 的某些举措对此有所缓解。

总之,对于以大型机为中心的整合提供商,要遵循最新的 Web 服务标准,响应新需求,适应大型机应用的变化角色以及由开源普及的新费用结构,变得越来越困难。

以 ESB 为中心的下一代大型机集成

在开源社区中,企业服务总线(ESB)已成为 SOA 的最佳基础设施。ESB 支持多种传输协议、注册服务、消息转换、服务编排等功能。从某种程度上,它们涵盖了曾经由私有的企业应用集成(EAI)平台涉及的领域。

以 ESB 为中心的大型机集成解决方案通过建立在 ESB 架构之上,充分利用了这些优势。例如,将 COBOL 绑定到 Java 或 XML 就是作为 ESB 的内 部转换活动处理的。大型机中的消息交换可以使用 ESB 标准传输协议或现有的传输协议。大型机应用程序还没意识到 ESB 的优势,ESB 也可以与其他大型机交 换数据。

在开源社区中,ESB 社区非常活跃,与大型机相比,社区中的年轻开发人员能更好地理解 ESB。ESB 得益于大型的开源社区,同时它也直接面临着新技 术的挑战,如 BPM、动态语言和 RESTful Web Services。BPM 和 BPEL 已经广泛运用于 ESB,但以大型机为中心的集成解决方案却面临着很多挑战。借助以 ESB 为中心的集成,大型机集成能直 接参与复杂的业务流程。

和以大型机为中心的解决方案一样,以 ESB 为中心的大型机集成工具在设计时和运行时都起到了作用。相同的是,设计时工具需要将 COBOL 映射成复杂 的数据类型。不同的是,以 ESB 为中心的设计时工具所生成的制品是专门针对 ESB 的。这些制品一旦部署到 ESB,它们将把大型机的数据流转换成开放世界中 的对象。数据转换是 ESB 的功能之一,并受益于 ESB 的多线程、可伸缩架构。

ESB 为中心的大型机集成还得益于丰富的 XML 优化技术,如今在开放社区,这些技术广泛用于减少内存消耗,以及降低处理 XML 所消耗的 CPU 使用 率。可以说,分布式平台上的 CPU 成本比大型机上的要便宜得多,但最重要的是,像 profiler 这样成熟的工具已经广泛地在 Java 中使用,而在大型机 中尤为少见。以 ESB 为中心的解决方案可以更好地监测和控制 CPU 或内存消耗,从而降低整体集成成本。

在以 ESB 为中心的解决方案中,所生成制品与任何可以部署在 ESB 上的制品(Java,XML,jars 等) 是一致的。这意味着这些制品可以使用丰 富的管理工具(源代码控制、构建控制、依赖管理和持续集成等)来管理,而且可以被单元测试、测量和保护。集成制品是非常重要的开发制品。它们往往是事务性 系统的关键部分。在以 ESB 的为中心的解决方案中,这些制品可以看作是软件开发生态系统中的一等公民。

和以大型机为中心的 SOAP 堆栈相比,ESB 还提供了一个更高层次的抽象层。为了说明这一点,可参考下面的用例:在分布式平台中,大型机应用所消费的服务 是由大型机之外提供的。因为分布式环境的特性日益增多和在 IT 资产中发挥越来越大的作用,分布式环境提供引用数据和流程也越来越常见。在这种情况下,大型 机上原有流程需要使用这些分布式功能。在以大型机为中心的集成解决方案中,COBOL 程序会发出 SOAP 请求。相反,在以 ESB 为中心的集成解决方案 中,COBOL 程序对某次特殊的消息传递或者对它正在对话的分布式平台一无所知。它只需是将大型机数据放入一个 WebSphere MQ 队列中或是一个 HTTP 有效负载中。目标服务和协议的细节被隔离在 ESB 的内部。以 ESB 的为中心的解决方案提供了更高层次的解耦,这正是系统集成最 期望得到的特性。

一种以 ESB 为中心的大型机集成解决方案:LegStar 和 JBoss ESB

LegStar for JBoss ESB 是一种开源的大型机集成技术,它是第一个专门面向 ESB 作为整合平台的方案。本文演示了如何使用 Redhat 的开源 ESB——JBoss ESB 和 LegStart 让大型机的 COBOL 程序访问外部系统。这种组合架构使用同步或异步消息传递(这是大型机极少涉及的技术)有效地将大型机应用和 分布式流程进行了解耦。

用例

我们将为 COBOL 消费者暴露一个 Java 对象(Plain Old Java Objec 或者 POJO )。

LegStar for JBoss 也能满足更经典的用例,即 COLOBL 程序被暴露给 Java 消费者。但当 COBOL 代码作为客户端时,尤其是对松耦合要求比较高时,会面临一些特殊挑战。

LegStar for JBoss 也可以让 COBOL 代码访问 ESB 服务和 Web 服务。出于简单考虑,本用例中我们选择消费一个 POJO。

架构

在大型机一侧,我们假设 COBOL 是开发语言,WebSphere MQ 是传输机制。

在服务器端,我们使用免费的开源技术: JBoss ESB LegStar

部署架构如下:

对于这个架构选择有如下几点值得说明:

WebSphere MQ 和 JBoss ESB 之间的数据交换使用原始数据

你也可以选择使用 HTTP 与 ESB 交换数据,但 WebSphere MQ 已在大型机上得到广泛使用,与 HTTP 相比它能提供更好的异步消息。COBOL 代码可运行在 TSO 中,作为一个批处理程序运行在 CICS 或 IMS 中。 WebSphere MQ API 正好适用于这些环境,甚至更多。

COBOL 程序将原始的大型机数据发送到 WebSphere MQ 队列。在大型机上这个内容不需要转换。这意味着 JBoss ESB 只需要接收原始的大型机数据。这样做有两个优点:

  • 在大型机上减少了 CPU 消耗(无数据转换)
  • 大型机并不需要知道它在跟一个非大型机平台交换数据

就解耦来说,第二点尤其重要。

虽然架构图显示了一个在 z/OS 上运行的 WebSphere MQ 管理器,但是在分布式平台可能存在另外一个 WebSphere MQ 管理器。为了架构简单,我们并没有给出额外的管理器,同时也因为这样做并不是必需的。

从 ESB 的角度来看,我们使用一个标准的监听器与 JBoss ESB 连接在一起。这是一个高性能、多线程的监听器,它能够支持来自大型机的高负荷传入消息、并发和请求。

在大型机上,客户端代码的交互可以是同步的或异步的

COBOL 客户端代码可以使用标准 WebSphere MQ API 等待响应,也可只要请求发送后就返回。异步通信模式是通过使用 WebSphere MQ 标准的触发机制实现的,在收到应答后 COBOL 程序可以处理应答。

异步是可取的,因为它减少了系统间的依赖。这种消息交换模式同样也适用于 ESB。

JBoss ESB 服务是 COBOL 客户端程序和 POJO 之间的一个代理

JBoss ESB 支持多种传输协议并提供了我们这里使用的通用管道的概念。

JMS 网关是一个标准的 JBoss ESB 的监听器,它负责监听 WebSphere MQ 队列,当接收到消息时会触发一系列动作。JBoss 自带了一些开箱即用的工具,比如我们这里会用到的对象调用器或 JMS 路由器。

列集 / 散集(marhaling/unmarshaling)原始大型机数据所需要的消息转换动作是由 LegStart 在设计时产生的,其细节将在下一节中描述。LegStar 生成的制品是特定于 JBoss ESB 的,而且经过专门优化。

在某种程度上,ESB 代理服务使 COBOL 客户端不受那些可能会导致目标 POJO 改变的变更的影响。首先,改变 POJO 位置或软件包的名字不会影响 COBOL 客户端。你还可以在不影响客户端的前提下为 POJO 添加新特性。当然如果发生较大变化时,如删除属性或者改变属性的类型,仍会对 COBOL 代码 产生一定的影响。

实现步骤

本小节中我们描述了为 POJO 创建 ESB 服务代理的主要步骤,开发者可以按照这些步骤来操作。LegStar 提供了 Eclipse 插件,简化了开发。另外,相同的工具也可作为 ant 脚本获得,但我们选择 LegStar 的 Eclipse 插件,因为它更友好。

本实例的 Eclipse 项目代码可以在这里下载。

目标 Java 对象(POJO)

在本文中我们使用 POJO,相同的做法也适用于 JBoss ESB 服务或 ESB 外的 Web 服务。

它不仅是一个 Java 对象,我们还期望该类被暴露成一个粗粒度的方法,接受参数为一个复杂对象,输出则为一个对象,如果发生错误还会抛出异常。这种行为涉及到远程门面模式( Remote Facade pattern )。在这一模式中,输入和输出对象被称为数据传输对象( Data Transfer Objects )。在下文中,我们将称这些对象为数据对象。

这里显示了一种独特的方法。表示请求的输入数据对象被称为 JVMQueryRequest。它包含一组环境变量名。被称为 JVMQueryReply 的输出数据对象将包含一组被请求环境变量的值,以及一组本地化相关的值。

复制代码
public class JVMQuery {
public JVMQueryReply queryJvm(JVMQueryRequest request) throws JVMQueryException {
List envVarValues = new ArrayList ();
try {
for (String envVarName : request.getEnvVarNames()) {
if (envVarName == null) {
throw new JVMQueryException("Invalid variable name");
}
String value = System.getenv(envVarName);
if (value == null) {
envVarValues.add("Not found");
} else {
envVarValues.add(value);
}
}
} catch (SecurityException e) {
throw new JVMQueryException(e);
}
JVMQueryReply reply = new JVMQueryReply();
reply.setEnvVarValues(envVarValues);
Locale locale = Locale.getDefault();
reply.setCountry(locale.getDisplayCountry());
reply.setLanguage(locale.getDisplayLanguage());
reply.setFormattedDate(
DateFormat.getDateTimeInstance(DateFormat.FULL, DateFormat.FULL,
locale).format(new Date()));
reply.setCurrencySymbol(Currency.getInstance(locale).getSymbol());
return reply;
}
}

将 Java 数据对象映射到 COBOL 结构

当原始大型机数据被传送到 ESB 时,LegStar 会将这个数据列集(marshal)到一个 Java 数据对象。这是 LegStar 所起到的作用。 LegStar 提供了设计时工具将 COBOL 结构映射到 XML Schema 和 Java。它还提供了一个运行时绑定框架来完成原始大型机数据的列集 / 散集(marhaling/unmarshaling)。

LegStar 还提供了 Eclipse 插件,允许用户选择 Java 对象和请求自动映射到 COBOL 结构:

其结果是一个具有特殊 COBOL 注解的 XML Schema。下图中 Eclipse 的标准 XML Schema 编辑器显示了 JVMQueryReply 的数据结构:

您可能会注意到,有些COBOL 属性有默认值。例如,字符串的默认大小是32。这是因为COBOL 只支持固定大小的字符串。类似的,COBOL 不支持非固定的数组。在XML Schema 编辑器中可以方便地修改这些默认值。

生成COBOL 绑定类

LegStar 的 COBOL 绑定类是 Java 类,这些 Java 类完成原始大型机数据到 Java 数据对象的列集 / 散集(marhaling/unmarshaling)。

在 Eclipse 插件中,可以从 XML Schemas 提取复杂类型(complext type)。然后你可以选择需要生成绑定类的复杂类型。在下面的例子中,我们选择输入和输出类型:

LegStar 的 COBOL 绑定机制是建立在 Java 到 XML 的绑定框架之上的,它被称为 JAXB 或 JSR 222 。绑定过程会产生带有 COBOL 注解的 JAXB 类。如果你打开一个已生成的 JAXB 类,就能看到 Java 对象中的每个属性如何持有 COBOL 注释:

生成JBoss ESB 的动作(Action)和简单配置

最后一步会生成一系列制品,以帮助部署和测试JBoss ESB 的代理服务。在Eclipse 中,我们选择WebSphere MQ 选项并指定目标JBoss ESB 服务应当部署的位置:

LegStar 会生成 JBoss ESB 示例配置文件,文件包含了处理管道的完整动作,以供测试。它还生成了 COBOL 客户端示例代码,这些代码可以调用 JBoss ESB 的服务,并为开发做好准备。

结论

在 JBoss ESB 中使用 LegStar 是一个以 ESB 为中心的下一代大型机集成解决方案的例子。

这种新架构具备如下特征:

  • 真正实现了双向通信,根据情况,大型机代码既可以是服务器,也可以是客户端。
  • 对分布式服务而言,大型机 COBOL 程序是高度松耦合的。在本文的例子中,COBOL 程序使用普通的 WebSphere MQ 队列名作为其目标服务。至于 COBOL 程序,目标服务在网络中其它大型机上,它可以使用 Java 或者 PHP 实现,借此,它可以在网络的任何地方。 ESB 知道服务在哪里实现,或者至少知道如何将请求转发给它。
  • ESB 可以在大型机代码和目标服务之间实现松耦合。总之,即使技术迅速发展,当目标服务发生变化时,也可以减少对 COBOL 程序的修改。
  • 大型机程序可以随时参与复杂的工作流。不像本文中所描述的简单管道,JBoss jBPM 或 Active Endpoints 公司的 ActiveBPEL 能够提供工作流和服务编排,大型机程序可以作为活动的参与者。
  • 使用标准、开放的技术,如 XML Schema、JAXB、JAX -WS、JMS 或 HTTP,可以确保大型开源社区保持其活力。这与当前以大型机为中心的 SOAP 协议栈形成鲜明对比,因为以大型机为中心的 SOAP 协议栈 有些是使用汇编语言写的,这些协议栈都是封闭、专有的,并且发展缓慢。
  • 所有生成的制品是友好、开放的:Java 代码、XML Schema、XML 配置文件等。这样可以使用强大的工具来管理这些制品,这些工具在 Java 社区中非常常见。
  • 减少了大型机内存消耗。在我们的这种场景下,针对大型机根本没有外来技术。使用 COBOL 编译器和 WebSphere MQ(或者可以使用 HTTP)就足够了。CPU 密集型活动,如数据转换和 XML 处理等,全部在大型机上消失,转而移到 CPU 成本更低的平台上。

COBOL 和大型机应用程序将在很长时间内继续存在。许多这样的应用程序可以很好地履行其职责。与此同时,以 SOA 和 ESB 为基石的开源应用也正在逐步扩大规模。在这种背景下,以 ESB 为中心的大型机集成带来的独特优势是值得我们考虑的。

作者简介

Fady Moussallam LegSem 的首席执行官,拥有 20 多年的大型机应用和集成技术经验。 Mark Little Redhat 的 SOA 技术研发经理以及 JBoss 分公司的技术主管。查看英文原文 Mainframe Integration with JBoss ESB and LegStar


给 InfoQ 中文站投稿或者参与内容翻译工作,请邮件至 editors@cn.infoq.com 。也欢迎大家加入到 InfoQ 中文站用户讨论组中与我们的编辑和其他读者朋友交流。

2009-05-15 03:333003

评论

发布
暂无评论
发现更多内容

社交泛娱乐出海如何抓住AIGC?我在融云WICC上看到了答案

融云 RongCloud

社交 融云 泛娱乐 出海 通讯

聊聊数科公司如何与现有数智平台厂商协同作战

用友BIP

数科公司 数智平台 数智平台白皮书

大模型热潮来袭,AI基础软件深度赋能金融行业数智化升级

九章云极DataCanvas

如今做泛娱乐出海,你需要融云《社交泛娱乐出海作战地图》

融云 RongCloud

产品 互联网 融云 泛娱乐 出海

社交app源码技术屏幕的两大实用功能

山东布谷科技

App 软件开发 社交娱乐 源码实现

如何在 Jupyter Notebook 用一行代码启动 Milvus?

Zilliz

Jupyter Notebook 非结构化数据 Colab AIGC 向量数据库

蚂蚁集团变更管控平台 AlterShield 正式开源

TRaaS

GitHub 开源 蚂蚁集团 蚂蚁技术风险TRaaS

快速掌握Kubernetes中的核心概念

穿过生命散发芬芳

k8s 6 月 优质更文活动

KW 新闻 | KaiwuDB 受邀亮相 IOTE 2023 第十九届国际物联网展

KaiwuDB

工业物联网 KaiwuDB IOTE

Last Week in Milvus

Zilliz

非结构化数据 Milvus Zilliz 向量数据库 zillizcloud

专注开发者体验 | GitOps 实现 Kuberentes 持续部署

亚马逊云科技 (Amazon Web Services)

云原生

C语言编程—可变参数

芯动大师

C语言 可变参数 6 月 优质更文活动

提升用户体验:在小程序环境中充分利用Ionic框架

FinFish

Ionic 跨端开发 小程序容器 跨端框架 小程序容器技术

翻车了,被读者找出 BUG

捉虫大师

Go 性能优化

Postman Runner 中的参数自增技巧

Liam

Java Postman API 接口开发 接口工具

你会怎样设计云原生场景下的IOC框架?

K

原创 云原生 ioc spring ioc

出海如何从0到1?融云《社交泛娱乐出海作战地图》实战经验揭秘

融云 RongCloud

互联网 社交 融云 泛娱乐 出海

瓴羊Quick BI:可视化大屏让数据呈现更直观

夜雨微澜

助力金融业数字化转型,原点安全将出席“2023 中国金融业数字化转型发展大会”

原点安全

数据安全 金融行业 uDSP 消费者个人信息保护

飞桨AI4S污染物扩散快速预测模型,亮相全国数据驱动计算力学研讨会

飞桨PaddlePaddle

飞桨 #人工智能

使用containerd从0搭建k8s(kubernetes)集群

tiandizhiguai

k8s

DevStudio编辑器使用技巧

坚果

OpenHarmony3.2 6 月 优质更文活动

2023-06-12:如果一个正整数自身是回文数,而且它也是一个回文数的平方,那么我们称这个数为超级回文数。 现在,给定两个正整数 L 和 R (以字符串形式表示), 返回包含在范围 [L, R] 中

福大大架构师每日一题

算法、 福大大架构师每日一题

KW 新闻 | KaiwuDB 发布智慧矿山解决方案

KaiwuDB

智慧矿山 KaiwuDB 世界智能大会

扬帆启航丨九科信息亮相2023全球数字经济大会(GDEC)新加坡分会场

九科Ninetech

​“前端已死”甚嚣尘上,全栈工程师卷到起飞

引迈信息

前端 低代码 全栈 JNPF

KW 喜报 | KaiwuDB 斩获 2023 数博会“优秀科技成果”奖

KaiwuDB

KaiwuDB 离散制造业解决方案 2023数博会

把钢铁侠战衣交给Z世代,没想到联想商用PC可以这么炫酷!

脑极体

联想 PC

高能预警!融云WICC发布《社交泛娱乐出海作战地图》

融云 RongCloud

互联网 地图 融云 即时通信 出海

开源共建下一代智能终端操作系统根社区 OpenHarmony携手伙伴聚力前行

科技汇

揭秘阿里云 Flink 智能诊断利器——Flink Job Advisor

Apache Flink

大数据 flink 实时计算

使用JBoss ESB 和 LegStar实现大型机整合_SOA_Fady Moussallam_InfoQ精选文章