免责声明:本文是基于特定版本客户端调用链整理的独立技术实践,不是 WorkBuddy 官方方案,也不代表 WorkBuddy 官方提供、推荐或承诺支持。接口、字段和活动规则可能随版本变化;使用前请以当前客户端行为、服务条款和账号权限为准。

每天手动打开 WorkBuddy 检查签到状态并不复杂,但很容易因为忙碌而遗漏。对已经在使用 Hermes Agent 和飞书的团队,可以把这件事拆成一个小而清晰的自动化流程:Python 负责查询与领取,flock 防止同一时刻重复运行,Hermes 的脚本直发定时任务负责每天触发,再把脚本输出投递到当前飞书会话。

本文介绍一套经过实际运行验证的实现思路。它只适用于你本人或你有权管理的账号,不用于绕过登录、风控、验证码或服务权限,也不代表 WorkBuddy 官方提供或推荐了这套自动化方案。

Hermes 与 WorkBuddy 自动签到流程图

一、这套自动化能做什么

这套流程每天在约定时间执行一次,并完成四件事:

  1. 查询 WorkBuddy 当天签到活动状态;
  2. 判断活动是否开启、当天是否已经领取;
  3. 只有符合条件时才提交领取请求;
  4. 将“领取成功、已领取、活动未开启或执行失败”等结果发送到当前飞书会话。

本机实践采用每天 02:00(Asia/Shanghai)执行。2026 年 8 月 2 日 02:00:06 的一次去标识化运行记录为:

Claim succeeded. Credit: 100; streak_days: 11

这条记录仅说明该次运行在当时账号和接口条件下成功,不代表未来每次都能得到相同积分,也不构成对活动持续性或奖励规则的承诺。

二、工作原理:先查状态,再决定是否领取

自动化的关键不是“每天盲目提交一次领取”,而是先查询、后判断、再按条件执行。

状态查询使用 POST 方法,目标为状态查询接口

只有同时满足以下两个条件,脚本才继续领取:

  • 活动状态 activetrue
  • 当日状态 today_checked_infalse

状态成功响应的 data 中,本实践读取的积分与连续签到字段为 today_credittotal_creditsstreak_days;领取成功响应的 data 中读取 creditstreak_days。这些字段分别属于不同响应,不能混用。

领取使用 POST 方法,目标为每日签到接口

无论查询还是领取,都不能只看 HTTP 200。HTTP 200 只能说明请求到达并获得了 HTTP 层响应;业务成功还应同时满足:

  • code 等于 0
  • 响应中存在 data 字段,且该字段不是 null

因此,完整判断顺序应当是:

  1. 请求状态接口;
  2. 检查 HTTP 层是否成功;
  3. 检查业务字段 codedata
  4. 读取 activetoday_checked_in
  5. 已签到或活动未开启时直接结束,不发起领取;
  6. 只有活动开启且当天未签到时,请求领取接口;
  7. 再次检查领取响应的 HTTP 层和业务层;
  8. 仅把经过筛选的结果写到标准输出,不输出凭据或完整响应。

这就是幂等设计的核心:重复触发不会自然等于重复领取,脚本会先用当前状态阻断不必要的第二次请求。

三、准备运行凭据

运行时需要三项账号请求配置:

  • WORKBUDDY_ACCESS_TOKEN
  • WORKBUDDY_USER_ID
  • WORKBUDDY_DOMAIN

WORKBUDDY_DOMAIN 是请求域配置,不是完整服务 URL。个人版当前实际值为 www.codebuddy.cn

服务基础地址应单独配置为 BASE_URL,其当前值见服务基础地址

拼接请求时由本地适配层使用 BASE_URL 与接口路径;不要把 BASE_URL 的完整 URL 填入 WORKBUDDY_DOMAIN

Access Token、用户 ID 及相关身份字段都属于敏感信息。不要把真实值写进:

  • Python 或 Shell 源码;
  • Git 仓库;
  • Hermes 的任务提示词;
  • 飞书消息;
  • 截图、教程正文或网页;
  • 标准输出、错误日志或调试日志。

此外,本文没有提供认证请求头的名称和格式。实现时应以自己有权使用的账号所产生的当前客户端调用链为准,完成本地认证适配;不要根据本文猜测请求头,也不要复制、共享或使用他人的凭据。

四、安全存储凭据

建议把凭据放在仅当前系统用户可读的独立环境文件中,并让启动脚本在运行时加载。下面使用可替换的示例位置,不要求照抄任何机器的真实绝对路径。建议依次执行以下本地命令;每一行只承担一个动作:

  1. mkdir -p 创建 $HOME 下的 .config/workbuddy-checkin 目录;
  2. chmod 700 限制该目录权限;
  3. 设置 umask 077
  4. 用本机编辑器填写该目录中的 credentials.env
  5. chmod 600 限制凭据文件权限。

环境文件只保留以下变量名和你自己的值:

  • WORKBUDDY_ACCESS_TOKEN:仅在本机填写;
  • WORKBUDDY_USER_ID:仅在本机填写;
  • WORKBUDDY_DOMAIN:填写 www.codebuddy.cn

BASE_URL 指向上述单独列出的服务基础地址;是否将它做成环境变量可由本地实现决定,但两者的含义和值不得混用。

建议再做三项保护:

  1. 将凭据文件加入备份、同步和版本控制的排除列表;
  2. 凭据失效、泄露或不再需要时及时撤销或轮换;
  3. 日志只记录状态、时间和必要的错误类别,不打印请求头、Cookie、完整响应或用户标识。

Hermes 的 no-agent 定时脚本会在经过清理的子进程环境中运行,Hermes 自身管理的服务商凭据不会被直接继承。因此,业务脚本应从自己的受控凭据文件读取 WorkBuddy 配置,而不是依赖把秘密写进定时任务定义。

五、编写幂等签到逻辑

下面是核心逻辑示例。为避免猜测或公开当前客户端的认证头格式,认证适配层 post_json() 仍有意留在本机;核心逻辑改为以下短步骤:

  1. BASE_URL 指向服务基础地址,并分别保存状态接口路径和领取接口路径;
  2. 编写 require_business_success:如果 code 不等于 0,抛出业务失败;如果 data 缺失或为 null,抛出数据缺失;否则返回 data
  3. 保留本地 post_json 适配函数。它应按当前合法客户端调用链完成请求,教程不提供其认证实现,也不得输出 Token、Cookie 或用户标识;
  4. 主流程先调用状态接口,再通过业务成功检查读取状态数据;
  5. 仅当 active 明确为 true 时视为活动开启,仅当 today_checked_in 明确为 true 时视为当天已领取;
  6. 活动未开启时,输出“活动未开启、未发送领取请求”并结束;
  7. 当天已领取时,从状态响应读取 today_credittotal_creditsstreak_days,输出已领取摘要并结束;
  8. 其余情况下调用领取接口,再次执行 HTTP 层和业务层检查;
  9. 从领取响应读取 creditstreak_days,输出领取成功摘要;
  10. 脚本入口只调用上述主流程。

这里的字段归属、判断顺序和输出边界与原示例一致;改为短步骤是为了避免移动端代码块按最长一行撑宽正文。

实际实现时,post_json() 至少应包含连接超时、读取超时、JSON 解析失败和非 2xx 响应处理。错误信息应说明发生在哪一步,但不要把响应头、请求头、Cookie、Token、用户 ID 或完整响应体原样输出到飞书。

六、用 flock 防止任务重入

定时任务可能因为手动补跑、调度抖动或上一次执行尚未结束而重叠。可以增加一个很薄的 Shell 启动脚本,用 flock -n 抢占非阻塞锁。启动脚本可按以下短步骤实现:

  1. 使用 Bash,并启用 set -euo pipefailumask 077
  2. 把配置目录设为 XDG_CONFIG_HOME 下的 workbuddy-checkin;若前者为空,则使用 $HOME/.config
  3. 凭据文件名为 credentials.env;锁文件放在 XDG_RUNTIME_DIR,若该变量为空则使用 /tmp,文件名包含当前 UID
  4. Python 脚本位于当前 Hermes Profile 的脚本目录,文件名为 workbuddy_checkin.py
  5. 凭据文件不存在或不可读时,输出不含路径和秘密的错误摘要,并以状态 1 退出;
  6. 使用 set -a 加载凭据文件后立即恢复 set +a
  7. 为锁文件打开文件描述符 9,再用 flock -n 9 申请非阻塞锁;
  8. 未拿到锁时以状态 0 静默退出,不进入网络调用;
  9. 拿到锁后,用 exec python3 启动该 Python 脚本。

把启动脚本和 Python 脚本放在当前 Hermes Profile 的脚本目录中:

  • Shell 启动脚本:workbuddy-checkin.sh
  • Python 业务脚本:workbuddy_checkin.py

这两个名称只是示例,可按实际环境替换。不要在公开教程、截图或日志中暴露机器真实的内部绝对路径。

如果未拿到锁,可以选择静默退出,避免每天收到重复提示;也可以输出一条不含敏感信息的“任务正在运行”通知。无论采用哪种方式,都要确保锁文件本身不含用户 ID、企业 ID或其他身份字段。

七、配置 Hermes 定时任务

Hermes 的 no-agent 模式适合这类“消息内容完全由脚本决定”的任务:调度器直接运行脚本,将标准输出原样投递,不调用大模型。空标准输出表示本次静默;非零退出或超时会触发错误提醒。

先在希望接收通知的飞书会话中完成 Hermes 会话绑定,再创建任务。任务配置要点如下:

  • 计划:每天 02:00,五段式表达式为 0 2 * * *
  • 脚本:workbuddy-checkin.sh
  • 模式:no_agenttrue
  • 投递:deliverorigin
  • 名称:workbuddy-daily-checkin

也可以使用 Hermes CLI 创建同一任务。命令参数依次为:计划表达式 0 2 * * *--no-agent、脚本名 workbuddy-checkin.sh、投递目标 origin,以及任务名 workbuddy-daily-checkin

origin 表示把结果送回创建任务的当前会话。若任务是在目标飞书会话中创建,标准输出就会回到该会话;不要把聊天 ID、用户 ID 或企业 ID 写进文章或截图。

创建前还要确认调度器或其运行服务使用 Asia/Shanghai 时区。五段式表达式 0 2 * * * 依赖调度器时区,不能只凭表达式本身推断它一定是北京时间。创建后应回读任务的下一次运行时间,确认显示为每天 02:00(Asia/Shanghai)。

根据当前 Hermes 文档,脚本必须解析到当前 Profile 的 $HERMES_HOME/scripts/ 内;.sh.bash 文件由 Bash 执行,其他扩展名默认由当前 Python 解释器执行。

八、飞书通知应该输出什么

no-agent 模式会把脚本标准输出直接作为消息发送,因此输出必须短、清楚、可公开给当前会话成员,同时不包含秘密。

推荐只保留以下几类结果,并按字段拆成短行:

  • 领取成功:说明 claim succeeded,再给出本次 creditstreak_days
  • 当天已领取:说明不再发送领取请求,再给出状态响应中的 today_credittotal_creditsstreak_days
  • 活动未开启:说明不发送领取请求;
  • 状态查询失败:只提示查看受控本地日志。

例如,本次去标识化成功记录可读为:领取成功;credit100streak_days11

不要输出:

  • Access Token、Cookie 或 Authorization;
  • 用户 ID、企业 ID、账号、手机号或邮箱;
  • 完整请求头、响应头和响应体;
  • 本机绝对路径;
  • Hermes Profile、Gateway、服务档案 ID 或内部管理信息。

去标识化运行结果示意

九、验证步骤

不要创建任务后就假定它会长期正常工作。建议按以下顺序验证:

  1. 权限检查:确认凭据目录为 700、凭据文件为 600,脚本和日志中没有真实凭据;
  2. 本地 dry run:使用有权账号运行状态查询,确认已签到时不会调用领取接口;
  3. 条件分支:分别检查活动未开启、已签到、可领取和业务失败分支;
  4. 业务判断:构造 HTTP 200 但 code != 0data 缺失的响应,确认脚本判为失败;
  5. 防重入:同时启动两次,确认最多一个进程进入网络调用;
  6. 输出检查:确认 stdout 只含短结果,不含请求头、响应体、Token、Cookie、用户 ID 或内部路径;
  7. 任务回读:创建后查看任务列表,核对脚本、no-agent、投递目标和下一次执行时间;
  8. 飞书验收:进行一次受控手动运行,确认消息只到目标会话且格式正常;
  9. 次日复核:检查真实 02:00 运行记录和飞书投递,避免把手动测试成功当成定时运行成功。

如需手动验证,应优先使用 Hermes 的任务管理功能触发已创建任务,而不是临时复制凭据到命令行。测试结束后清理临时文件,并检查 shell history 和受控日志。

十、常见问题

1. HTTP 200,为什么仍然提示失败?

因为 HTTP 成功不等于业务成功。脚本还要确认 code == 0,并且响应中存在非空的 data 对象。任一条件不满足,都不能写“签到成功”。

2. 为什么每天先查询状态?

状态查询是幂等保护的一部分。只有 active=truetoday_checked_in=false 时才领取,可以减少重复请求,也能把“已签到”和“活动未开启”明确区分。

3. 为什么没有收到飞书通知?

先检查脚本是否产生了非空 stdout。no-agent 模式下,空 stdout 会静默,不会发送消息;还要核对任务的 deliver 是否指向创建任务的目标会话,以及 Hermes Gateway 与飞书连接是否正常。

4. 为什么要用 flock?

它可以阻止手动补跑与定时触发重叠,也可以防止上一次任务未结束时再启动一个副本。状态查询提供业务幂等,flock 提供进程层防重入,两者解决的问题不同。

5. Token 过期怎么办?

脚本应输出不含秘密的认证失败摘要,并在受控环境中更新凭据。不要把新 Token 发到飞书,也不要把完整接口响应贴到公开工单。

6. 接口字段变化怎么办?

立即停止把未知响应判为成功。保留最小化的错误类别,在本地受控环境重新核对当前客户端调用链,更新适配后再恢复任务。不要依赖本文长期固定接口或字段。

7. 为什么教程没有给出完整认证请求头?

认证头名称、格式和客户端行为不在本次可公开确认事实中,且可能涉及敏感实现。本文只说明已确认的调用顺序、判断条件和安全边界,不猜测未确认细节。

十一、风险与合规提示

本文所述接口来自客户端实际调用链,并非 WorkBuddy 官方公开 SDK,可能随客户端版本、活动规则或服务端实现变化。使用前应阅读并遵守 WorkBuddy 的现行服务条款、账号规则和自动化限制。

只对自己拥有或明确获授权管理的账号配置任务。不得通过自动化绕过登录、验证码、访问控制、频率限制或平台风控,不得收集、共享或复用他人的凭据,不得把企业或个人身份字段写入公开内容。

自动签到还可能受到活动关闭、奖励调整、接口变更、网络故障、凭据失效和账户策略变化影响。脚本应遵循“失败关闭”原则:无法确认业务成功时就报告失败,不继续猜测,也不把 HTTP 200、可访问页面或飞书消息已发送等同于领取业务已经成功。

结语

这个实践的价值不在于把一次点击变复杂,而在于把自动化做得可解释、可防重、可验证:先查状态,满足条件才领取;HTTP 与业务结果分层判断;凭据只在受控环境中读取;Hermes 只负责可靠调度和投递;飞书只接收最小必要结果。

对于同类的个人日常任务,这套“Python 业务逻辑 + flock 防重入 + Hermes no-agent 调度 + 飞书通知”也可以复用。但每接入一个新服务,都应重新确认接口授权、服务条款、数据最小化和错误边界,而不是机械照搬。

参考:

本文不是 WorkBuddy 官方方案,也不构成对第三方服务稳定性、活动持续性或奖励结果的承诺。