6

如何拆分离散型流程

 3 years ago
source link: https://zhuanlan.zhihu.com/p/347341314
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

如何拆分离散型流程

problem solver

例如在订单成交之后,给中介分佣这一类的业务。它们有三个特点

  • 不需要返回值。也就是只需要在时间顺序上,安排在之后发生。
  • 不精确要求立即执行。稍微晚个几秒是可以忍受的。
  • 不影响事务结果。不因为分佣服务挂了,导致订单无法成交。
v2-8b4799bff190f74cba7a4b25cf09d1bd_720w.jpg

订单的 Git 仓库提供 OrderCreated 事件。 分佣的 Git 仓库依赖订单 Git 仓库,订阅 OrderCreated 事件,在收到事件之后分佣金。

订单不能感知到分佣是否成功,也不能在下单成功的界面上立即展示出分佣的数据。 分佣也无法保证一定是在订单创建之后被立即触发执行的,消息队列仅保证最终会把消息投递出去。

可降级为事件驱动

很多流程需求夹杂了UI的需求,无法变成纯事件驱动的。

例如在结束订单的时候,要立即终止计费进程,并显示出账单。如果纯事件驱动的话,界面上的账单数据是拿不到的。 但是有可能计费进程这个时候异常,可以先在订单上标记好结束时间。 然后界面上显示“出账中,请耐心等待”。等计费进程恢复之后,再异步结账扣费。

这种类型的业务是订单的Git仓库依赖计费的Git仓库,而不是像上面的分佣业务那样,依赖是倒置的。

这种实现的伪代码是:

try {
    const newUI = finishBilling();
    renderUI(newUI);
} catch(e) {
    enqueueFinishBilling();
    renderUI('出账中,请耐心等待')
}

界面重刷新

上一种实现方式里,finishBilling 同时完成了两件事情

  • 告诉订单结束,我这里搞完了,没问题
  • 同时返回了账单

渲染账单的逻辑可能是经常易变的,导致 finishBilling 的接口稳定不下来。 可以把这两个操作分为两步:

try {
    finishBilling();
    refreshUI();
} catch(e) {
    enqueueFinishBilling();
    renderUI('出账中,请耐心等待')
}

这样,finishBilling 就可以仅仅专注于流程,而不用管 UI 需求。UI 逻辑可以使用离散型 UI 里的各种模式集成进来。

在可能的情况下,纯事件驱动当然是 Autonomy 最佳的方案。奈何产品经理不喜欢异步。 最好不要在流程代码的接口里包含 UI,这样会使得接口更易变,也就更易于产生额外的沟通成本。 最好把 UI 需求按照离散型 UI 里描述的集成方式,用更 Autonomy 的方案集成进来。

《业务逻辑拆分模式》

全文撰写中taowen/modularization-examples


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK