6.7 KiB
6.7 KiB
06 门锁授权与异步操作状态机设计 (Authorization State Machine)
语义铁律:DMS HTTP 200
success: true仅代表“请求已保存/已受理 (REQUEST_ACCEPTED)”,绝不代表“门锁设备执行成功 (DEVICE_SUCCESS)”! 门锁生效滞后性:门锁作为电池供电的无线物联网终端,下发指令需要经过网关转发与微功耗空中唤醒,官方明确要求调用成功 10 秒后再行查询操作状态。 设计目标:建立双层解耦状态机(业务授权状态 vs 设备操作状态),消除状态混淆。
1. 双层状态体系解耦定义
必须区分两个不同生命周期的状态机:
- 门禁授权业务状态 (
DoorAuthorizationStatus):站在学员与住宿业务视角,表达该住宿事实当前是否具备开门权限。 - 外部硬件操作状态 (
ExternalOperationStatus):站在异步任务与设备网络视角,表达向 DMS 派发的具体单次指令的执行进展。
2. 状态映射与状态定义字典
2.1 门禁授权业务状态 (DoorAuthorizationStatus)
| 本地业务状态枚举 | 业务含义 | 允许的操作 |
|---|---|---|
UNISSUED (待下发) |
住宿已确认,尚未向门锁发起授权下发请求 | 下发授权 (grant) |
ISSUING (下发中) |
已向 DMS 发送创建钥匙请求,已获得 operationId,正在等待 10 秒后对账确认 |
刷新状态、等待轮询 |
ACTIVE (已生效/成功) |
轮询确认设备返回 operationStatus = success,学员可正常刷卡/输密码开门 |
查看凭据、撤销授权 (revoke) |
ISSUE_FAILED (下发失败) |
DMS 或设备明确返回失败,或超时重试达到上限 | 重新下发 (retry)、人工改派房间 |
REVOKING (撤销中) |
学员退宿/调房,已向 DMS 提交删除钥匙请求,正在等待对账确认 | 刷新状态、等待轮询 |
REVOKED (已注销) |
轮询确认钥匙已被设备成功删除,权限已彻底关闭 | 归档留存、不可逆 |
EXPIRED (已到达有效期) |
超过 DMS 凭据设定的 validUntil 有效期边界(离线过期机制需供应商确认) |
自动归档、主动撤权兜底 |
2.2 外部硬件异步操作状态 (ExternalOperationStatus) 与 DMS 映射
| 本地操作状态枚举 | 对应 DMS API 原始字段 | 状态说明与处理策略 |
|---|---|---|
CREATED |
内部构建指令,尚未发送 | 准备调用 HTTP 客户端 |
REQUESTED |
HTTP 请求发出,等待响应 | 网络传输中 |
ACCEPTED |
DMS 返回 success: true,携带 operationId |
记录 operationId,调度器挂起 10 秒轮询任务 |
PENDING_DEVICE |
轮询返回 operationStatus: "undone" |
设备尚未完成执行,计算下次退避轮询时间 |
SUCCESS |
轮询返回 operationStatus: "success" |
终态:设备已成功落锁/删除,触发推进业务状态 |
FAILED |
轮询返回 operationStatus: "failed" |
终态:设备返回明确失败,记录 resultDetails 与错误原因 |
TIMEOUT |
轮询返回 operationStatus: "timeout" |
终态:DMS 判定设备通信超时(10秒未响应),触发重试或报警 |
RETRY_WAIT |
遭遇可恢复异常(如网络抖动),等待下一次重试 | 依据退避算法重新放入调度队列 |
3. 门锁授权端到端生命周期状态流转图 (Mermaid)
stateDiagram-v2
[*] --> UNISSUED : 住宿安排确认 (Accommodation Confirmed)
state "授权下发阶段 (Grant Flow)" as GrantFlow {
UNISSUED --> ISSUING : 触发下发 (报到或临近入住)
state ISSUING {
[*] --> Op_Requested : 调用 POST /online-password-key/create
Op_Requested --> Op_Accepted : DMS 返回 200 (获得 operationId)
Op_Accepted --> Op_Polling : 延迟等待 10 秒
Op_Polling --> Op_Undone : 查询状态返回 undone
Op_Undone --> Op_Polling : 间隔 5 秒重试 (最大3次)
}
ISSUING --> ACTIVE : 查询状态返回 success
ISSUING --> ISSUE_FAILED : 状态返回 failed 或多次 timeout
ISSUE_FAILED --> ISSUING : 管理员手动重试 / 定时补偿重试
}
state "正常使用阶段 (Active Use)" as ActiveUse {
ACTIVE --> ACTIVE : 门锁正常开门 / 查询电量信号
ACTIVE --> EXPIRED : 超过 validUntil 有效期边界
}
state "权限注销阶段 (Revoke Flow)" as RevokeFlow {
ACTIVE --> REVOKING : 学员退宿 / 提前退训 / 换房
ISSUE_FAILED --> REVOKING : 换房或作废
state REVOKING {
[*] --> Revoke_Requested : 调用 POST /online-password/delete
Revoke_Requested --> Revoke_Accepted : DMS 返回 200 (获得 operationId)
Revoke_Accepted --> Revoke_Polling : 延迟等待 10 秒
Revoke_Polling --> Revoke_Polling : undone (重试轮询)
}
REVOKING --> REVOKED : 查询状态返回 success
REVOKING --> REVOKE_FAILED : 状态返回 failed 或 timeout
REVOKE_FAILED --> REVOKING : 紧急人工重试撤销
}
REVOKED --> [*]
EXPIRED --> [*]
4. 关键流转分支与语义判定细节
4.1 成功下发分支 (Happy Path)
- 触发下发:适配器调用
/rest/doorlock/online-password-key/create。 - DMS 同步响应:
本地动作:持久化
{ "success": true, "data": { "id": 4945, "placeId": 1320, "lockId": 372, "operationId": "0872887e-464b-4f44-a0cc-057871ba0f65" } }external_key_id = 4945,创建外部操作记录(operationId = 0872887e...,status = ACCEPTED),授权主表推进为ISSUING。 - 轮询调度器等待 10 秒:调用
/rest/doorlock/query-operation-status(入参requestType = 1,operationId = ...)。 - 轮询响应:
本地动作:更新操作记录为
{ "success": true, "data": { "operationStatus": "success" } }SUCCESS,授权主表推进为ACTIVE(生效可用)。
4.2 设备超时分支 (Timeout Handling)
- 若 10 秒后轮询返回:
{ "success": true, "data": { "operationStatus": "timeout", "message": "Device response timeout" } } - 判定规则:门锁可能休眠过深、网关信号不佳或网关离线。
- 系统动作:
- 不得无限循环调用。
- 若配置了自动补偿,可追加 1 次重试查询;若依然超时,将操作置为
TIMEOUT,授权主表置为ISSUE_FAILED。 - 页面以警告色徽标展示“设备下发超时”,提供【重新下发】按钮供管理员现场排障。