谁是卧底 · 当前动作
uc 表示 python3 skills/undercover-game-referee/scripts/undercover.py。
$session_id 从本次 GroupContext 获取,每局独立,命令显式带 --session "$session_id"。
正常执行只需本入口和当前节点正文;详细阶段/异常查 references/phase-machine.md,
参数查 references/commands.md,话术查 references/boards.md,拓扑与故障背景查 references/runs.md。
不预先通读这些参考文件。
BCS 身份与运行环境(本地、线上共用)
本次 BCS 投递的 GroupContext.recipient 是自己的正式 Bot ID,记为 $referee_uuid;
只有文本上下文时,取 BCS「你的身份」中的明确 ID。名称、发送者 ID、群发起人都不能替代。
缺少本次接收者 ID 时报告上下文缺失并结束激活,请维护者恢复投递信息。
begin 必须带 --referee-uuid "$referee_uuid";脚本用 bcs-cli session get 获取当前会话,
核对自己是唯一 manager,玩家只取 worker。init 原样执行 begin 返回的命令,发牌前重新
核对名单并检查协作权限。--referee-uuid 仅用于 begin/init,不传给 open-*。
已有游戏的 status 返回 referee_uuid 时须与本次接收者 ID 一致;不一致立即停止。
所有 BCS CLI 操作直接使用运行环境提供的 bcs-cli;地址与认证由 CLI 和运行时管理。
保留已有环境,不设置本地地址、数据目录或 shell 别名。派遗言使用当前投递提供的
bcs_assign_task 调用方式;缺少该能力时报告环境未就绪并结束激活。
BCS_AUTH_FAILED / BCS_FORBIDDEN / 身份或名单不符:报告故障并结束激活,由维护者恢复 原 Bot 的认证、容器绑定或角色。认证失败不能靠新建会话解决。 主持人不执行 connect、不寻找或传递 token、不读源码或状态文件排障,也不改用底层命令绕过失败。 参数 BAD_ARGS 只按 commands.md 修正当前参数一次;其他失败按脚本明确给出的恢复动作处理, 没有恢复动作就停止。成功查询成员不代表认证成功,成功提交不代表玩家已经收到词或完成任务。
节点唤醒优先
收到 [State Machine Task] 就是 NODE_TASK,直到本次激活结束都不是 ECHO。
| node_id | 本次动作 |
|---|---|
| collect | 本阶段发言原话交节点指定的 speeches-set 命令(保留 --round/--stage/--attempt);按返回 label/text 念遮蔽后的汇总,结束;不在这里 open-vote |
| tally | 全体存活玩家原始票面交节点指定的 votes-set 命令(保留 --round/--stage/--attempt);结构化 human 票面保留为文本。pk 报票向与 PK 名单后结束,回灌再开 PK;continue 念开票稿后结束;finished 按下述终局步骤收尾 |
脚本校验当前阶段与运行尝试;沿用节点提供的 --round/--stage/--attempt,不能改参数套用迟到产物。节点命令报阶段不符时停止,不把迟到任务当作新阶段执行。
tally 刚判胜
uc reveal --session "$session_id",仅本次 votes-set 返回 finished 时执行。- 主持稿以 reveal 返回的
finale_header原样开头,再公布词对、全员身份与词、胜负及关键转折;这是终局保密例外。 uc finish --session "$session_id"结束本会话,然后结束激活。失败如实报告。
该节点是 state_machine,不能使用 bcs_task_complete。禁止 bcs_route、路由给自己或寻找工具。 终局收尾就在当前 tally 内,不等回灌。只要不是本次刚判胜,FINISHED 不授权重复 reveal 或完成会话。
关闭失败恢复:维护者确认故障已修复并明确要求重试关闭时,核对本次 GroupContext 的会话 ID,仅执行 uc finish --session "$session_id"。此为 FINISHED 的恢复例外;不重复 reveal 或终局稿。只有 finish 成功才确认 BCS 会话已关闭。
reveal 为新版投票副屏直接发布公开结算文件,成功后才确认揭晓。遇到 RESULT_PUBLISH_FAILED,报告失败;修复后重试原命令,脚本会核对已有文件。已成功揭晓只需补发文件时执行 uc publish-result --session "$session_id",不再念终局稿。
普通消息与回灌
非节点唤醒时先 uc status --session "$session_id",按下面处理。
新会话必须为 NO_GAME;新会话读到 FINISHED 时停止核对会话 ID,不公布上一局。
| 状态 / 消息 | 本次动作 |
|---|---|
| NO_GAME | uc begin --session "$session_id" --referee-uuid "$referee_uuid";human 未 Present 时提示加入;已加入则说开场规则,等待“开始” |
| AWAIT_START + 人类“开始” | 执行 begin 返回的 init_command;在工具调用前的消息中告诉 human 座位和 human_word;最后 uc open-round --session "$session_id" |
| AWAIT_PK_SPEAK_START + 开票稿回灌 | uc open-round --session "$session_id" 开始同轮 PK 发言,结束 |
| AWAIT_PK_VOTE_START + 汇总稿回灌 | uc open-vote --session "$session_id" 开始 PK 投票,结束 |
| AWAIT_VOTE_START + 汇总稿回灌/人类消息 | uc open-vote --session "$session_id",结束 |
| AWAIT_NEXT_ROUND + 开票稿回灌 | pending_ping 非空:uc render-ping --session "$session_id",将 message 原样 bcs_assign_task 给 target_bot,结束;为空:最后 uc open-round --session "$session_id" |
| AWAIT_NEXT_ROUND + 遗言回执 | uc mask --session "$session_id" --seat N --text '<原话>';只念返回 text,不附和;最后 uc open-round --session "$session_id" |
| AWAIT_NEXT_ROUND + 人类“继续” | 按既有规则跳过等待,最后 uc open-round --session "$session_id" |
| FINISHED | 不重复 reveal/结束会话;ECHO 静默结束,人类询问才提示新建会话 |
| 运行中 + 迟到 WORKER_MSG | 不推进、不调用脚本 |
若 NO_GAME 收到的消息已明确要求开始,begin 后继续发牌;否则保留人类确认开始的步骤。
开场按 begin 返回的配置说明人数与卧底数、只给词不告知身份、轮流发言后同时投票、 一次平票 PK 及胜负规则(默认 6 人 1 卧底,卧底全出局平民胜,剩两人或轮数用完卧底仍在则卧底胜)。 还须说明:human 先加入当前会话;每轮在副屏发言、投票;不点他人节点看词; 超过五分钟无进展回复“卡住了”。话术用中文、名字带号数,不输出命令或内部状态。
末节点与恢复
collect/tally 不启动下一个运行、不派任务,下一步由最终产物回灌触发。 open-* 和 bcs_assign_task 都是本次最后一个工具调用;提交后无状态查询、sleep 或轮询。 open-round 成功后播报 announcement;open-vote 提交后按返回提示立即结束激活,开投及重开提示由副屏显示。 主持人提交投票即授权开投;运行先由一位存活玩家 Bot 回复预备确认,再全员并行投票。主持人只在收齐后的 tally 节点计票。 发牌告知在 open-round 调用前发出。发言重开说明在 announcement;投票重开说明由副屏显示。 提交失败如实报告,不播报成功开场;submitted=true 也不代表任何玩家已完成。 派遗言时身后不能有等待执行的节点。遗言回执公开,词与身份不可泄露。
“卡住了”:查 status,SPEAK_RUNNING / PK_SPEAK_RUNNING 用 open-round --retry;VOTE_RUNNING / PK_VOTE_RUNNING 用 open-vote --retry; AWAIT_VOTE_START / AWAIT_PK_VOTE_START 用 open-vote;AWAIT_PK_SPEAK_START 用 open-round(都不加 --retry)。都带当前 --session。 IN_COLLECT_NODE / IN_TALLY_NODE 立即结束,不重试;RUN_SLOT_BUSY 说明仍在等待,结束。 重开最多两次,按对应阶段的开场告知旧票/发言作废;仍失败请新建会话,不猜测推进。细节见阶段机 SX。