# 分布式最终一致性

#### CAP定理

###

### 分布式最终一致性

状态机、恢复日志、异步校验

### 重试

重试机制可以使分布式不一致数据自动恢复，前提是重试接口要提供幂等保证。重试机制是达成分布式最终一致性的重要手段。例如，超时重传是TCP协议保证数据可靠性的一个重要机制，核心思想其实就是重试。

### 幂等

幂等的数学定义为

```
f(f(x)) = f(x)
```

用通俗的话来说就是 : 相同的操作执行多次 和 执行一次产生的效果是一样的。有的操作是天然幂等的，如查询、删除操作。

#### 状态机

状态机是表示实体的状态根据条件转移的数学模型。通过状态机模型，系统可以判断当前不一致状态，以及如何校正不一致状态到一致状态。这样说可能比较抽象，我们拿发微信群红包的例子来说明。当你点开发红包按钮，输入总金额、红包个数、标题，点击支付成功后。其实根据时间先后红包系统后台至少经历过这样一个状态机 ![图片](https://uploader.shimo.im/f/63GykYcoQFwKZZwb.png!thumbnail):

#### 恢复日志

恢复日志是程序现场的记录，也是业务数据恢复的重要依据。恢复日志log要求全局唯一的requestId来标示请求(实际的业务场景可采用不会重复有含义的业务id)，出现异常，可以根据requestId维度redo和undo业务操作，恢复日志具体可分为三部分 :

* requestId请求开始时，记录REQUEST START requestId
* 本地修改时，记录全部的（requestId，x，originalValue, destValue）四元组，x代表操作对象，修改前x的值为originalValue，本次修改的目的操作值为destValue
* requestId结束时，记录REQUEST End requestId

#### 异步校验

彻底解决分布式一致性问题，有著名的Paxos算法，通过该算法分布式系统自发达成一致性。而在具体的业务场景，完全不需要系统自发的达成共识，我们只要在业务系统外部加上严格的业务约束，用来仲裁业务系统的状态。通过异步校验，可以发现分布式系统中的异常状态，并通过恢复日志进行脚本批量恢复或者人工处理恢复，根据校验的粒度有 :

* 根据业务实体id校验，使用消息队列，将需要校验业务id投递给校验系统，进行异步校验。
* 根据时间维度批量校验，使用异步调度框架，根据时间粒度批量获取进行异步校验。

此外，并不是所有系统都有可靠消息队列和调度服务支撑，业务系统可以增加一个本地业务id校验回执字段，校验系统根据校验步骤回调设置校验回执字段，并对校验未通过的数据进行重校验或者订正。
