让我们想象一下,我们有一个比萨店要设计和构建的订单处理系统。
要求是:
R1。系统应该与客户端和用例无关,这意味着系统可以被客户端访问,这在初始设计期间没有考虑到。例如,如果披萨店决定其许多客户稍后使用三星 Bada 智能手机,则为 Bada OS 编写客户端将不需要重写系统的 API 和系统本身;或者例如,如果事实证明使用 iPad 而不是 Android 设备对送货司机来说更好,那么创建 iPad 客户端将很容易,并且不会以任何方式影响系统的 API;
R2。可重用性,这意味着如果业务流程发生变化,系统可以很容易地重新配置,而无需重写太多代码。例如,如果稍后披萨店将开始接受在线付款以及接受送货司机的现金(接受订单前付款 VS 接受货到付款),那么系统很容易适应新的业务流程;
R3。高可用性和容错性,这意味着系统应该在线并且应该 24/7 全天候接受订单。
因此,为了满足 R3,我们可以使用 Erlang/OTP 并具有以下架构:
这里的问题是这种架构中有很多“硬编码”的功能。例如,如果比萨店从接受货到付款转变为接受下单前的在线支付,那么重写整个系统和修改系统的 API 将需要大量的时间和精力。
此外,如果披萨店需要对其 CRM 客户端进行一些改进,那么我们将不得不再次重写 API、客户端和系统本身。
因此,以下架构旨在解决这些问题,从而帮助满足 R1、R2 和 R3:
系统中的每个“服务”都是一个带有 RESTful API 的 Webmachine 网络服务器。这种方法有以下好处:
- Erlang/OTP 的所有优点,因为每个 Web 机器都是一个 Erlang 应用程序,可以被监督并且可以放入一个 Erlang 版本中;
- 具有 SOA 的所有优点的面向服务的架构;
- 易于适应业务流程的变化;
- 易于向客户端(例如 CRM 客户端)添加新客户端和新功能,因为客户端可以使用系统中所有服务的 RESTful API,而不是一个“中央”API(SOA 方面的服务可组合性)。
因此,本质上,第二张图片中提出的系统架构是面向服务的架构,其中每个服务都有一个 RESTful API 而不是 WSDL 契约,每个服务都是一个 Erlang/OTP 应用程序。
这是我的问题:
- 图2:我想在这里重新发明轮子吗?我应该坚持使用纯 Erlang/OTP 架构吗?(“纯 Erlang”是指打包到一个版本中的 Erlang 应用程序,通过 gen_server:call 和 gen_server:cast 函数调用相互通信);
- 您能说出建议的方法中的任何缺点吗?(图二)
- 您认为维护和发展(R1 和 R2)这样的系统(图 2)比真正的 Erlang/OTP 系统更容易吗?
- 这样一个系统的安全性(图 2)可能是一个问题,因为有许多对 Web 开放的入口点(所有服务的 RESTful API)而不是只有一个入口点(图 1),不是吗?
- 在这样的系统中有几个“编排模块”是否可以,或者可能存在一些更好的做法?(“接单”、“CRM”和“派单”服务如图2);
- 就消息传递和协议的限制而言,纯 Erlang/OTP(图 1)是否比这种方法(图 2)有任何优势?(在我之前的类似问题gen_server:call VS HTTP RESTful 调用中进行了部分讨论)