# 预约命令 **本文引用的文件** - [src/command/index.ts](file://src/command/index.ts) - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts) - [src/command/handlers/events.ts](file://src/command/handlers/events.ts) - [src/command/handlers/eventDetails.ts](file://src/command/handlers/eventDetails.ts) - [src/command/handlers/history.ts](file://src/command/handlers/history.ts) - [src/command/handlers/login.ts](file://src/command/handlers/login.ts) - [src/command/handlers/logout.ts](file://src/command/handlers/logout.ts) - [src/command/handlers/start.ts](file://src/command/handlers/start.ts) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts) - [package.json](file://package.json) ## 目录 1. [简介](#简介) 2. [项目结构](#项目结构) 3. [核心组件](#核心组件) 4. [架构总览](#架构总览) 5. [详细组件分析](#详细组件分析) 6. [依赖关系分析](#依赖关系分析) 7. [性能考虑](#性能考虑) 8. [故障排查指南](#故障排查指南) 9. [结论](#结论) 10. [附录](#附录) ## 简介 本文件面向“预约命令”的实现与使用,围绕以下命令展开: - 预约创建:/book_{event_id}_{slot_id} - 预约取消:/cancel_{booking_id} - 活动浏览:/events、/event_{id} - 历史查询:/history - 登录/登出:/login、/logout、/start 文档将深入解释命令解析、用户认证、活动与时间槽选择、优惠券应用、取消确认流程、状态管理与并发控制策略,并提供错误处理与数据一致性保障方案,以及扩展开发指导。 ## 项目结构 该机器人采用模块化命令分发与客户端封装: - 命令入口与路由:在命令入口中注册所有命令与回调查询,绑定环境变量(KV 存储)。 - 命令处理器:每个命令对应一个处理器文件,负责解析输入、调用客户端 API、构建交互式键盘与消息。 - 客户端封装:统一的 CosmoeClient 封装 API 请求、认证状态与数据模型。 ```mermaid graph TB subgraph "命令层" CMD_INDEX["命令入口
src/command/index.ts"] H_BOOK["预约处理器
src/command/handlers/bookEvent.ts"] H_CANCEL["取消处理器
src/command/handlers/cancel.ts"] H_EVENTS["活动列表处理器
src/command/handlers/events.ts"] H_EVENTD["活动详情处理器
src/command/handlers/eventDetails.ts"] H_HISTORY["历史处理器
src/command/handlers/history.ts"] H_LOGIN["登录处理器
src/command/handlers/login.ts"] H_LOGOUT["登出处理器
src/command/handlers/logout.ts"] H_START["开始处理器
src/command/handlers/start.ts"] end subgraph "客户端层" C_CLIENT["CosmoeClient
src/client/cosmoe.ts"] end CMD_INDEX --> H_BOOK CMD_INDEX --> H_CANCEL CMD_INDEX --> H_EVENTS CMD_INDEX --> H_EVENTD CMD_INDEX --> H_HISTORY CMD_INDEX --> H_LOGIN CMD_INDEX --> H_LOGOUT CMD_INDEX --> H_START H_BOOK --> C_CLIENT H_CANCEL --> C_CLIENT H_EVENTS --> C_CLIENT H_EVENTD --> C_CLIENT H_HISTORY --> C_CLIENT H_LOGIN --> C_CLIENT H_LOGOUT --> C_CLIENT H_START --> C_CLIENT ``` 图表来源 - [src/command/index.ts](file://src/command/index.ts#L20-L110) - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts#L1-L226) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L1-L132) - [src/command/handlers/events.ts](file://src/command/handlers/events.ts#L1-L27) - [src/command/handlers/eventDetails.ts](file://src/command/handlers/eventDetails.ts#L1-L61) - [src/command/handlers/history.ts](file://src/command/handlers/history.ts#L1-L107) - [src/command/handlers/login.ts](file://src/command/handlers/login.ts#L1-L75) - [src/command/handlers/logout.ts](file://src/command/handlers/logout.ts#L1-L34) - [src/command/handlers/start.ts](file://src/command/handlers/start.ts#L1-L6) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L113-L503) 章节来源 - [src/command/index.ts](file://src/command/index.ts#L20-L110) ## 核心组件 - 命令入口与路由:集中注册命令与回调查询,绑定 KV 存储用于会话与凭证持久化。 - 预约处理器:解析 /book_{event_id}_{slot_id},校验用户登录状态,拉取活动详情与时间槽,支持优惠券选择与自动下单。 - 取消处理器:解析 /cancel_{booking_id},展示确认键盘,二次确认后调用取消接口。 - 客户端封装:统一的 CosmoeClient 提供认证、事件查询、预约、取消等能力,并维护认证状态。 - 会话与存储:通过 KV 适配器为会话与对话状态提供持久化。 章节来源 - [src/command/index.ts](file://src/command/index.ts#L20-L110) - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts#L11-L118) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L11-L84) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L113-L503) ## 架构总览 命令到 API 的整体调用链如下: ```mermaid sequenceDiagram participant U as "用户" participant B as "命令入口
src/command/index.ts" participant HB as "预约处理器
src/command/handlers/bookEvent.ts" participant HC as "取消处理器
src/command/handlers/cancel.ts" participant CC as "CosmoeClient
src/client/cosmoe.ts" participant KV as "KV 存储" U->>B : 发送命令 /book_{event_id}_{slot_id} B->>HB : 路由到预约处理器 HB->>KV : 读取用户凭证 KV-->>HB : 返回凭证 HB->>CC : 获取活动详情与时间槽 CC-->>HB : 返回活动数据 HB->>U : 展示优惠券选择键盘如适用 U->>B : 回调选择优惠券 B->>HB : 调用优惠券选择处理器 HB->>CC : 下单含可选优惠券 CC-->>HB : 返回下单结果 HB-->>U : 成功/失败消息 U->>B : 发送命令 /cancel_{booking_id} B->>HC : 路由到取消处理器 HC->>CC : 查询我的预约 CC-->>HC : 返回预约列表 HC->>U : 展示取消确认键盘 U->>B : 回调确认取消 B->>HC : 调用取消确认处理器 HC->>CC : 执行取消 CC-->>HC : 返回取消结果 HC-->>U : 成功/失败消息 ``` 图表来源 - [src/command/index.ts](file://src/command/index.ts#L77-L105) - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts#L11-L118) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L11-L84) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L191-L270) ## 详细组件分析 ### 预约命令 /book_{event_id}_{slot_id} - 命令解析:使用正则匹配 /book_{event_id}_{slot_index},提取活动 ID 与时间槽索引。 - 认证检查:从 KV 中读取用户凭证,若无则提示先登录。 - 活动与时间槽:调用客户端获取活动详情,按 range 排序,校验索引有效性与剩余容量。 - 优惠券应用: - 若存在多个可用优惠券,生成内联键盘让用户选择;支持“不使用优惠券”选项。 - 若仅有一个优惠券,自动应用;若无优惠券,则直接下单。 - 下单流程:构造下单请求(event_id、time_slot、可选 coupon_code),调用客户端下单接口,返回最终价格、预约编号等信息并反馈给用户。 ```mermaid flowchart TD Start(["进入 /book_{event_id}_{slot_id}"]) --> Parse["解析命令参数
提取 event_id, slot_index"] Parse --> CheckAuth["从 KV 读取用户凭证"] CheckAuth --> HasAuth{"有凭证?"} HasAuth --> |否| PromptLogin["提示先登录"] --> End HasAuth --> |是| FetchEvent["获取活动详情与时间槽"] FetchEvent --> ValidateIndex{"索引有效且有余量?"} ValidateIndex --> |否| ShowError["提示错误并结束"] --> End ValidateIndex --> |是| CheckCoupons{"是否有可用优惠券?"} CheckCoupons --> |多张| ShowKeyboard["展示优惠券选择键盘"] --> End CheckCoupons --> |一张| AutoApply["自动应用唯一优惠券"] CheckCoupons --> |无| NoCoupon["不使用优惠券"] AutoApply --> PlaceOrder["调用下单接口"] NoCoupon --> PlaceOrder PlaceOrder --> OrderOK{"下单成功?"} OrderOK --> |是| ReplySuccess["回复成功消息含最终价格/编号/优惠码"] --> End OrderOK --> |否| ReplyFail["回复失败消息"] --> End ``` 图表来源 - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts#L17-L117) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L191-L270) 章节来源 - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts#L11-L118) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L191-L270) ### 取消命令 /cancel_{booking_id} - 命令解析:使用正则匹配 /cancel_{booking_id},提取预约 ID。 - 认证检查:从 KV 读取凭证,确保已登录。 - 预约确认:调用客户端获取我的预约,查找目标预约,不存在则提示。 - 确认流程:生成“确认/取消”内联键盘,展示预约详情与风险提示。 - 取消执行:用户确认后调用取消接口,返回结果并更新消息。 ```mermaid sequenceDiagram participant U as "用户" participant B as "命令入口" participant HC as "取消处理器" participant CC as "CosmoeClient" participant KV as "KV 存储" U->>B : 发送 /cancel_{booking_id} B->>HC : 路由到取消处理器 HC->>KV : 读取用户凭证 KV-->>HC : 返回凭证 HC->>CC : 获取我的预约 CC-->>HC : 返回预约列表 HC->>U : 展示确认键盘 U->>B : 回调 confirm_cancel 或 cancel_action alt 确认取消 B->>HC : 调用取消确认处理器 HC->>CC : 执行取消 CC-->>HC : 返回取消结果 HC-->>U : 更新为成功/失败消息 else 取消 HC-->>U : 更新为已取消 end ``` 图表来源 - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L17-L84) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L87-L132) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L226-L239) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L405-L422) 章节来源 - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L11-L84) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L87-L132) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L226-L239) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L405-L422) ### 活动与时间槽展示 - /events:列出最近的摄影活动,每个活动附带跳转到详情页的命令链接。 - /event_{id}:获取活动详情,排序时间槽并显示剩余/容量;对可预约且当天或之前的时间槽,提供对应的 /book_{event_id}_{slot_index} 链接。 章节来源 - [src/command/handlers/events.ts](file://src/command/handlers/events.ts#L4-L26) - [src/command/handlers/eventDetails.ts](file://src/command/handlers/eventDetails.ts#L10-L60) ### 历史与登录/登出 - /history:获取用户预约历史,按时间倒序取最新若干条,对可取消的预约显示 /cancel_{booking_id} 链接。 - /login:交互式登录,向 Cosmoe API 获取 token 并存入 KV。 - /logout:删除 KV 中的用户凭证。 - /start:欢迎信息与可用命令提示。 章节来源 - [src/command/handlers/history.ts](file://src/command/handlers/history.ts#L4-L106) - [src/command/handlers/login.ts](file://src/command/handlers/login.ts#L13-L74) - [src/command/handlers/logout.ts](file://src/command/handlers/logout.ts#L10-L33) - [src/command/handlers/start.ts](file://src/command/handlers/start.ts#L4-L5) ## 依赖关系分析 - 命令入口依赖各处理器与 KV 存储,负责命令与回调查询的路由。 - 处理器依赖 CosmoeClient 进行 API 调用,并依赖 KV 存储进行凭证与会话持久化。 - 客户端封装统一的 API 行为,包括认证状态检查与错误处理。 ```mermaid graph LR CMD_INDEX["src/command/index.ts"] --> H_BOOK["src/command/handlers/bookEvent.ts"] CMD_INDEX --> H_CANCEL["src/command/handlers/cancel.ts"] CMD_INDEX --> H_EVENTS["src/command/handlers/events.ts"] CMD_INDEX --> H_EVENTD["src/command/handlers/eventDetails.ts"] CMD_INDEX --> H_HISTORY["src/command/handlers/history.ts"] CMD_INDEX --> H_LOGIN["src/command/handlers/login.ts"] CMD_INDEX --> H_LOGOUT["src/command/handlers/logout.ts"] CMD_INDEX --> H_START["src/command/handlers/start.ts"] H_BOOK --> C_CLIENT["src/client/cosmoe.ts"] H_CANCEL --> C_CLIENT H_EVENTS --> C_CLIENT H_EVENTD --> C_CLIENT H_HISTORY --> C_CLIENT H_LOGIN --> C_CLIENT H_LOGOUT --> C_CLIENT H_START --> C_CLIENT ``` 图表来源 - [src/command/index.ts](file://src/command/index.ts#L20-L110) - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts#L1-L226) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L1-L132) - [src/command/handlers/events.ts](file://src/command/handlers/events.ts#L1-L27) - [src/command/handlers/eventDetails.ts](file://src/command/handlers/eventDetails.ts#L1-L61) - [src/command/handlers/history.ts](file://src/command/handlers/history.ts#L1-L107) - [src/command/handlers/login.ts](file://src/command/handlers/login.ts#L1-L75) - [src/command/handlers/logout.ts](file://src/command/handlers/logout.ts#L1-L34) - [src/command/handlers/start.ts](file://src/command/handlers/start.ts#L1-L6) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L113-L503) 章节来源 - [src/command/index.ts](file://src/command/index.ts#L20-L110) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L113-L503) ## 性能考虑 - API 调用频率:活动列表、详情、预约历史、下单与取消均涉及网络请求,建议在处理器中避免重复请求,必要时缓存短期结果。 - 消息长度限制:历史消息可能较长,已做截断处理,避免超出 Telegram API 限制。 - KV 存储:凭证与会话存储在 KV 中,注意键空间命名与过期策略,避免无限增长。 - 时间计算:活动日与当前时间比较使用北京时间偏移,确保本地化正确性。 章节来源 - [src/command/handlers/history.ts](file://src/command/handlers/history.ts#L94-L97) - [src/command/handlers/eventDetails.ts](file://src/command/handlers/eventDetails.ts#L23-L35) ## 故障排查指南 - 命令未响应 - 检查命令是否被正确注册与路由(命令入口)。 - 确认回调查询正则匹配是否正确。 - 无法登录 - 确认 /login 是否成功写入 KV,检查凭证格式与有效期。 - 预约失败 - 检查时间槽剩余容量与索引合法性。 - 确认优惠券是否仍有效且适用于该活动。 - 取消失败 - 确认预约是否存在且状态允许取消。 - 检查回调数据格式与解析逻辑。 - 错误处理策略 - 所有处理器均包含 try/catch,出现异常时回复通用错误消息并记录日志。 - 客户端方法在未认证时抛出错误,需在调用前确保已设置凭证。 章节来源 - [src/command/index.ts](file://src/command/index.ts#L77-L105) - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts#L114-L117) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L80-L83) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L207-L209) ## 结论 该预约系统通过清晰的命令分发与处理器职责划分,结合 KV 存储与客户端封装,实现了从活动浏览、时间槽选择、优惠券应用到预约与取消的完整闭环。系统具备良好的可扩展性与错误处理能力,适合在此基础上进一步增强并发控制、状态机与审计日志。 ## 附录 ### 命令一览与行为 - /start:欢迎信息与可用命令提示。 - /events:列出最近活动,附带 /event_{id} 链接。 - /event_{id}:展示活动详情与时间槽,提供 /book_{event_id}_{slot_index} 链接。 - /book_{event_id}_{slot_index}:预约创建,支持优惠券选择与自动下单。 - /history:展示预约历史,对可取消项提供 /cancel_{booking_id} 链接。 - /cancel_{booking_id}:取消预约,二次确认后执行。 - /login:交互式登录,保存凭证至 KV。 - /logout:删除 KV 中的用户凭证。 章节来源 - [src/command/handlers/start.ts](file://src/command/handlers/start.ts#L4-L5) - [src/command/handlers/events.ts](file://src/command/handlers/events.ts#L4-L26) - [src/command/handlers/eventDetails.ts](file://src/command/handlers/eventDetails.ts#L10-L60) - [src/command/handlers/bookEvent.ts](file://src/command/handlers/bookEvent.ts#L17-L117) - [src/command/handlers/history.ts](file://src/command/handlers/history.ts#L4-L106) - [src/command/handlers/cancel.ts](file://src/command/handlers/cancel.ts#L17-L84) - [src/command/handlers/login.ts](file://src/command/handlers/login.ts#L13-L74) - [src/command/handlers/logout.ts](file://src/command/handlers/logout.ts#L10-L33) ### 数据模型与 API 关键点 - CosmoeClient 提供认证、事件、预约、取消等方法,内部维护 userId 与 token。 - 预约请求包含 event_id、time_slot、可选 coupon_code。 - 预约响应包含最终价格、预约编号等字段,便于回执展示。 章节来源 - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L113-L503) ### 并发控制与状态管理 - 当前实现未显式引入分布式锁或队列,建议在关键路径(如下单)增加幂等键与重试策略,避免重复提交。 - 使用 KV 存储会话与凭证,注意键冲突与并发读写的一致性问题。 - 对于高并发场景,可在客户端层引入重试与退避策略,并在处理器中对同一用户的连续请求进行限流。 章节来源 - [src/command/index.ts](file://src/command/index.ts#L21-L52) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L247-L269) ### 扩展开发指导 - 新增命令:在命令入口注册新命令与回调查询,编写处理器文件并在入口中导入。 - 新增 API:在 CosmoeClient 中新增方法,遵循现有认证与错误处理模式。 - 优化体验:引入会话状态机管理多步流程,减少 KV 读写次数;对长消息进行分片发送。 - 安全加固:对命令输入进行更严格的校验与白名单过滤;对敏感操作增加二次确认与审计日志。 章节来源 - [src/command/index.ts](file://src/command/index.ts#L20-L110) - [src/client/cosmoe.ts](file://src/client/cosmoe.ts#L113-L503) - [package.json](file://package.json#L18-L22)