fail-fast&fail-safe
1. fail-fast¶
简言之,快速失败。我们在设计一个模块(可以是一个函数,一个类甚至是一个服务)时,如果有某种条件会导致模块无法正常运行下去,就应该让模块立刻终止(可以是return,也可以抛一个runtimeexception)。这样做有两种好处:
- 及早终止,防止错误一直被带到下游,导致下游服务崩溃或者产生脏数据;
- 便于排查,fail-fast一般都会有类似断言的机制来判定某种条件,在断言处终止可以很方便的定位问题,而如果错误被带到下游,就很难定位问题的根源了;
经典例子:集合的ConcurrentModificationException:在对 collection 进行迭代时,某个线程对该 collection 在结构上对其做了修改,这时迭代器就会抛出 ConcurrentModificationException 异常信息。
2. fail-safe¶
与fail-fast相反,如果模块遇到某种错误,不应该让程序失败,而是采取某种降级策略,尽量往下走。这个原则主要适用于主模块内的分支流程。
举个例子,我有一个接口,主要是返回feed流的,但是有一个分支逻辑是调用广告服务插入广告类型的feed的,如果广告服务不可用了,我的整体逻辑是不能挂的,因为不插入广告也没关系,但是正常的feed流还是需要返回。所以对广告服务的调用是要能降级的。简单来说,可以try-catch住,如果调用有异常了就不插入广告。不能因为一个分支逻辑而把主要逻辑整挂了。