best-feishu-bot
v0.0.6
Published
Bridge Feishu/Lark messenger with local CLI coding agents
Maintainers
Readme
best-feishu-bot
把飞书 / Lark 消息和本地 Claude Code 或 Codex CLI 打通的轻量 bot。用一条命令启动,扫码绑定 PersonalAgent 应用,然后在飞书里和本机编程助手对话,让它读图、处理文件、改代码。
关于能实现的效果,详情可以阅读飞书文档
主要功能
- 在飞书私聊直接发消息,或在群里
@bot,把任务转给本机 Claude Code / Codex CLI。 - 流式卡片:文本回复和工具调用实时更新在同一张卡片上。
- 会话延续:每个聊天、话题或文档评论有自己的会话,不会互相串。
- 排队与消息合并:短时间连续发送的消息会合并处理;任务运行中收到的普通消息会排队到下一轮,
/new、/cd、/ws use、/stop这类命令可以中断当前任务。 - 多工作空间:用
/cd切换当前项目,用/ws保存和复用常用项目目录。 - 图片 / 文件:直接发给 bot,bridge 下载到本地后交给本机 agent 处理。
- 卡片按钮:
/help、/ws list、/status返回可点击的交互卡片。 - 多 bot 隔离:在不同终端用
--bot <name>启动多个 bot。每个 bot 都有自己独立的配置、Claude settings、skills、会话、日志和工作目录,默认都在~/.best-feishu-bot下。
前置条件
- Node.js >= 20.12.0
- 至少有一个可用 agent:
- Claude Code 通过
@anthropic-ai/claude-agent-sdk随 bridge 内置;模型和供应商配置从当前 bot 的 Claude Code 配置目录读取。 - Codex CLI 仍需要本机安装
codex,安装说明:https://developers.openai.com/codex/cli
- Claude Code 通过
- 一个飞书 / Lark PersonalAgent 应用。首次启动的扫码向导可以帮你创建并绑定。
安装
npm i -g best-feishu-bot
# 或
pnpm add -g best-feishu-bot快速开始
npm i -g best-feishu-bot
# 把公司管控的 Claude Code / DeepSeek 配置放到这里:
mkdir -p ~/.best-feishu-bot/bots/default/claude
$EDITOR ~/.best-feishu-bot/bots/default/claude/settings.json
best-feishu-bot裸命令 best-feishu-bot 等价于 best-feishu-bot run:前台启动 bridge,检查 Claude Code 运行时,没有 profile 时进入扫码向导。
- 终端渲染二维码。
- 用飞书 App 扫码。
- 选择或创建 PersonalAgent 应用。
- 成功后配置写入
~/.best-feishu-bot/bots/default/config.json。 - bot 连上后,就可以在飞书私聊或群里 @ 使用。
没有指定项目目录也可以启动。bridge 会创建 ~/.best-feishu-bot/bots/default/workspaces/default;启动后在飞书里发送 /cd <path> 切到同一个 bot 的 workspaces/ 根目录下的其他项目。
首次启动默认使用 Claude。bridge 会把 CLAUDE_CONFIG_DIR 强制设为当前 bot 的 claude/ 目录,并且不会把宿主 shell 里的模型供应商密钥透传给 Claude,例如 ANTHROPIC_API_KEY、ANTHROPIC_AUTH_TOKEN、CLAUDE_CODE_OAUTH_TOKEN、ANTHROPIC_MODEL、ANTHROPIC_BASE_URL,以及 Bedrock / Vertex / Foundry 相关变量。公司批准的 DeepSeek / Claude Code 配置放在 bot-local settings.json;bridge 不在自己的 profile 里新增 API key 字段。
要同时启动多个 bot,可以在不同终端使用不同 bot 名:
best-feishu-bot --bot sales
best-feishu-bot --bot support每个 bot 都位于 ~/.best-feishu-bot/bots/<bot>,可以拥有不同的应用凭据、Claude settings、skills、会话、日志和工作目录。
如果已经有 PersonalAgent app,可以在初始化时传 --app-id 跳过创建应用流程;命令会提示输入 App Secret。
best-feishu-bot run --app-id cli_xxx
# 或直接初始化并启动后台服务
best-feishu-bot start --allow-system-service-files --app-id cli_xxxLark 国际版应用可加 --tenant lark。
后台运行
run 适合首次配置、前台运行和多终端启动多个 bot。后台服务属于进阶用法,因为它会写 OS service manager 文件。start 默认会拒绝;明确接受时加 --allow-system-service-files:
best-feishu-bot start --bot sales --allow-system-service-files
best-feishu-bot status --bot sales
best-feishu-bot stop --bot sales服务层命令必须先全局安装,不能直接用 npx。daemon 的 launchd plist / systemd unit / Windows 任务会记录 bridge CLI 的路径;如果这个路径来自 npm 临时缓存,缓存清掉后 daemon 就起不来。run 用 npx 单次启动没问题。
服务层命令按 bot + profile 注册:
best-feishu-bot start --bot <name> [--profile <name>] --allow-system-service-files
best-feishu-bot stop --bot <name> [--profile <name>]
best-feishu-bot restart --bot <name> [--profile <name>]
best-feishu-bot status --bot <name> [--profile <name>]
best-feishu-bot unregister --bot <name> [--profile <name>]平台映射:
- macOS:launchd 用户代理
ai.best-feishu-bot.bot.<profile> - Linux:systemd 用户单元
best-feishu-bot.bot.<profile>.service - Windows:Task Scheduler 任务
LarkChannelBridge.Bot.<profile>,launcher 是.cmd
daemon 日志在 ~/.best-feishu-bot/bots/<bot>/profiles/<profile>/logs/daemon/。
多 bot 和多 profile
默认情况下,bridge 启动 default bot 以及该 bot 内的 active profile。需要独立配置目录时使用 --bot <name>。如果一个 bot 内还需要切换多套应用凭据或 agent 类型,再使用 profile use <name> --bot <name>。
best-feishu-bot --bot sales
best-feishu-bot --bot support
best-feishu-bot profile create codex --bot support --agent codex例如只重启 Codex bot:
best-feishu-bot restart --bot support --profile codex
best-feishu-bot status --bot support --profile codex命令速查
宿主 CLI
best-feishu-bot
best-feishu-bot --bot <name>
best-feishu-bot run [--bot <name>] [--profile <name>] [--agent claude|codex] [--workspace <path>] [-c <config>]
best-feishu-bot migrate [--bot <name>] [--profile <name>] [--agent claude|codex]
best-feishu-bot ps [--bot <name>]
best-feishu-bot kill <id|#> [--bot <name>]
best-feishu-bot skills list [--bot <name>]
best-feishu-bot skills add [--bot <name>] <path>
best-feishu-bot skills remove [--bot <name>] <skill-name>
best-feishu-bot --helpprofile use <name> --bot <name> 会切换该 bot 后续默认启动使用的 profile。一个 bot 内需要多 profile 时可以使用:
best-feishu-bot profile create claude --bot <name> --agent claude
best-feishu-bot profile create codex --bot <name> --agent codex
best-feishu-bot profile list --bot <name>
best-feishu-bot profile use <name> --bot <name>
best-feishu-bot profile remove <name> --bot <name>
best-feishu-bot profile remove <name> --bot <name> --purge --yes
best-feishu-bot profile export <name> --bot <name> [--output ./profile.json] [--force]
best-feishu-bot profile export <name> --bot <name> --include-secrets --yesprofile remove 默认归档本地状态,也可以删除当前激活的 profile。若还剩其他 profile,会自动切到下一个;若这是最后一个 profile,会清空 root config,之后可以用同名重新创建。只有加 --purge --yes 才会永久删除。profile export 默认脱敏 app secret;只有加 --include-secrets --yes 才会导出敏感配置。
如果某个 profile 被建成了错误的 agent 类型,先 stop 或 unregister --profile <name> 清理对应后台服务,再 profile remove <name>,然后用正确的 --agent 重新创建。
飞书内斜杠命令
| 命令 | 作用 |
|---|---|
| /new, /reset | 清空当前会话 |
| /cd <path> | 切换工作目录并重置会话 |
| /ws list | 列出命名工作空间 |
| /ws save <name> | 把当前工作目录保存为命名工作空间 |
| /ws use <name> | 切换到命名工作空间 |
| /ws remove <name> | 删除命名工作空间 |
| /resume | 恢复同 agent、工作目录、权限模式兼容的历史会话 |
| /status | 查看 profile、agent、工作目录、会话、lark-cli 身份和运行状态 |
| /config | 调整展示偏好、访问控制和 lark-cli 身份策略 |
| /invite user @某人 | 允许用户私聊使用 bot |
| /invite admin @某人 | 添加访问控制管理员 |
| /invite group | 允许当前群使用 bot |
| /invite all group | 允许 bot 所在的所有群使用 |
| /remove user @某人, /remove admin @某人, /remove group | 移除访问控制条目 |
| /stop | 停止当前 run,也可点卡片停止按钮 |
| /timeout [N\|off\|default] | 设置或清除当前会话的 idle watchdog |
| /ps | 列出本机 bridge 进程 |
| /exit <id\|#> | 停止指定 bridge 进程 |
| /reconnect | 强制 WebSocket 重连 |
| /doctor [描述] | 执行低敏诊断 |
| /help | 帮助卡片 |
私聊不需要 @。群和话题群默认必须 @bot;@all 会被忽略。支持的云文档评论里 @bot 就会触发回复。
lark-cli 身份策略
每个 profile 都使用 bot-local lark-cli 目录:~/.best-feishu-bot/bots/<bot>/profiles/<profile>/lark-cli。agent 子进程会收到指向这个目录的 LARKSUITE_CLI_CONFIG_DIR,所以不同 bot/profile 不共享 lark-cli 状态。
默认策略是 bot-only:lark-cli 使用应用 / bot 身份,不访问个人资源。bridge 不再从 bot home 之外导入普通本机 lark-cli 用户状态。owner/admin 可以在 /config 查看或切换这个策略;/status 会用 lark-cli: app 或 lark-cli: user-ready 展示当前摘要。
Claude Code 运行时
Claude profile 默认使用 SDK 运行时,由 @anthropic-ai/claude-agent-sdk 提供内置 Claude Code binary。如果 SDK 的可选平台包不可用,bridge 会在可能时回退到本机 claude 命令。
bridge 会为每次 Claude 运行设置 CLAUDE_CONFIG_DIR=~/.best-feishu-bot/bots/<bot>/claude。Claude Code 会从这个目录按自己的规则读取 settings.json。这样公司管控的 DeepSeek 或其他供应商配置会留在 bot home 内,不会误用开发者 shell 里的其他模型环境。
示例 ~/.best-feishu-bot/bots/default/claude/settings.json:
{
"env": {
"ANTHROPIC_BASE_URL": "https://api.deepseek.com/anthropic",
"ANTHROPIC_AUTH_TOKEN": "replace-with-company-managed-token",
"ANTHROPIC_MODEL": "deepseek-chat"
}
}首次启动会在旁边创建 settings.example.json。你可以复制成 settings.json,也可以让公司的配置下发流程直接写入 settings.json。profile 仍可选择 claude.runtime(sdk 或 cli)和 claude.binaryPath;claude.configDir 由当前 bot 的 claude/ 目录托管。
Bot skills
每个 bot 都有独立的 Claude Code skills 目录:~/.best-feishu-bot/bots/<bot>/claude/skills。skill 来源必须是包含 SKILL.md 的目录。
best-feishu-bot skills add --bot sales ./skills/customer-research
best-feishu-bot skills list --bot sales
best-feishu-bot skills remove --bot sales customer-research故障排查
SDK 内置 Claude Code binary 缺失
请重新安装并确保没有跳过 optional dependencies,例如 npm i -g best-feishu-bot。不要使用 --omit=optional / --no-optional。必要时也可以单独安装 Claude Code,并在 profile 的 claude.binaryPath 指向本机可执行文件。
Claude Code 认证失败
检查当前 bot 的 claude/settings.json,例如 ~/.best-feishu-bot/bots/default/claude/settings.json。bridge 不会把供应商密钥写入自己的 profile,也不会把宿主 shell 里的模型供应商密钥透传给 Claude。如果 Claude 返回认证或模型错误,/doctor 和飞书错误卡片会展示可读的 Claude/SDK 报错。
二维码过期
用 Ctrl-C 停掉前台进程后重新运行 best-feishu-bot,会生成新的二维码。
工作目录
每个 bot 有一个工作目录根:~/.best-feishu-bot/bots/<bot>/workspaces。新建 profile 时可以传 --workspace <path> 作为初始目录,但该路径必须已经位于这个根目录下;没传时 bridge 会创建 workspaces/default。
下面只是 profile 里的字段片段,不要整段覆盖 config.json;请改对应 profile 下的 workspaces 字段。
{
"workspaces": {
"default": "/Users/me/.best-feishu-bot/bots/default/workspaces/default"
}
}bridge 会检查 /cd、/ws use、--workspace 和 profile default 的 realpath 必须位于当前 bot 的 workspaces/ 根目录下。~/project、/tmp/project 或其他 bot 的 workspace 会被拒绝,并提示把项目放到当前 bot 的 workspaces/ 目录内。
agent 生成给用户查看的工作台文件时,应放在当前工作目录的 workbench/YYYYMMDD/ 下,文件名使用 kebab-title-YYYYMMDD-HHmm.html 或 .md。本次 run 新建或更新的 .html、.htm、.md 会在最终回复里自动追加“工作台文件”链接。本机使用默认 http://localhost:${FILE_SERVER_PORT:-9527};部署在服务器时可在当前 profile 配置 fileServer.publicBaseUrl,返回给飞书用户的就是 publicBaseUrl 加文件相对访问路径。
{
"fileServer": {
"publicBaseUrl": "https://bot.company.example"
}
}权限模式
推荐给用户配置的是 permissions.defaultAccess 和 permissions.maxAccess。新 profile 默认两项都是 full,以保持 bridge 的本地工具、授权流程、文件写入等能力完整可用。如需收紧权限,可以改成 workspace 或 read-only;收紧后本地工具执行、登录 / 授权流程、文件写入等能力可能受限。
下面只是 profile 里的字段片段,不要整段覆盖 config.json;请改对应 profile 下的 permissions 字段。
{
"permissions": {
"defaultAccess": "full",
"maxAccess": "full"
}
}模式映射:
| Bridge access | Claude permission mode | Codex mode |
|---|---|---|
| full | bypassPermissions | danger-full-access |
| workspace | acceptEdits | workspace-write |
| read-only | plan | read-only |
旧版 sandbox 字段仍可读取。bridge 保存 profile 后,会把该设置迁移为 canonical permissions。
数据目录
| 路径 | 内容 |
|---|---|
| ~/.best-feishu-bot/bots/<bot>/config.json | bot config,包含 profiles 和 active profile |
| ~/.best-feishu-bot/bots/<bot>/active-profile | 该 bot 最近选择的 profile |
| ~/.best-feishu-bot/bots/<bot>/claude/settings.json | 公司管控的 Claude Code / DeepSeek settings |
| ~/.best-feishu-bot/bots/<bot>/claude/skills/ | bot-local Claude Code skills |
| ~/.best-feishu-bot/bots/<bot>/profiles/<profile>/sessions.json | 会话状态 |
| ~/.best-feishu-bot/bots/<bot>/profiles/<profile>/sessions.json.catalog.json | agent-aware 会话索引 |
| ~/.best-feishu-bot/bots/<bot>/profiles/<profile>/workspaces.json | 当前和命名工作空间绑定 |
| ~/.best-feishu-bot/bots/<bot>/profiles/<profile>/secrets.enc | profile 本地加密 App Secret |
| ~/.best-feishu-bot/bots/<bot>/profiles/<profile>/lark-cli/ | bot/profile-local lark-cli 目录 |
| ~/.best-feishu-bot/bots/<bot>/profiles/<profile>/media/ | 附件缓存 |
| ~/.best-feishu-bot/bots/<bot>/profiles/<profile>/logs/ | 结构化运行日志 |
| ~/.best-feishu-bot/registry/processes.json | 本机进程注册表 |
| ~/.best-feishu-bot/registry/locks/ | bot/profile lock 和 app lock |
默认不会读取或迁移 ~/.lark-channel;旧数据迁移需要显式运行 best-feishu-bot migrate。LARK_CHANNEL_LOG_DAYS 可以调整日志保留天数。
访问控制
聊天访问默认是私有的:开箱即用时,只有"你"能在私聊和群聊里用这个 bot。 这里的"你" = 创建 / 拥有这个飞书应用的人(也就是扫码把 bot 建起来的那位)。bot 会自动从飞书查出谁是应用 owner,所以一个人用聊天入口完全不用配置——你私聊它、在任意群里 @它都正常工作,其他人的聊天消息会被静默忽略(bot 不会回"你没权限",免得暴露自己的存在)。云文档评论按文档权限生效,见下文。
想让别的同事或某些群也能用,就把他们加进下面三类名单:
| 名单 | 控制谁 | 加入 | 移除 |
|------|--------|------|------|
| 允许私聊的用户 | 谁可以私聊 bot | /invite user @某人 | /remove user @某人 |
| 响应的群 | bot 在哪些群里对群内所有人响应 | /invite group(当前群)/ /invite all group(bot 所在的全部群) | /remove group(当前群) |
| 管理员 | 谁能改设置、并能在任意群用 bot | /invite admin @某人 | /remove admin @某人 |
/invite、/remove这些命令只有你(创建者)和管理员能发。命令里 @ 的是对方(不是 @ bot),bot 会自动把 @ 解析成对应的人,你不用手动去找 ID。
两种"畅通无阻"的身份
- 你(创建者):不受任何名单限制——私聊、任意群、所有命令都能用,而且永远锁不死自己:哪怕名单配乱了,回到 bot 私聊发
/config总能进来。在飞书后台把应用 owner 转给别人后,bot 也会自动跟着切换。 - 管理员:能私聊、能用
/config等管理命令,而且不受"响应的群"名单限制——无论群在不在名单里,bot 都会回他们。适合给一起维护 bot 的同事。
几种常见配置
- 只给自己用 → 什么都不用做,默认就是。
- 让某个同事能私聊 bot →
/invite user @他 - 让某个工作群里所有人都能用 → 在那个群里发
/invite group - 第一次配,想把 bot 已经在的群一次性全开放 → 发
/invite all group一键拉取 bot 所在的全部群加入名单,之后再用/remove group删掉不想要的 - 再拉个人一起当管理员 →
/invite admin @他
还需要知道的
- 改完下一条消息就生效,不用重启。
- 群里默认要先 @bot 才会回(私聊不用 @)。这是另一个独立开关(
/config→"群里需要 @ bot"),和上面的名单是两回事。 - 陌生人发消息一律静默丢弃,不会有任何回复。唯一的例外:有人在一个还没开放的群里 @bot,bot 会回一句友好提示,告诉他可以让管理员发
/invite group开放这个群。 - 云文档评论按文档权限生效:能在支持的文档里评论并 @bot 的人可以触发回复。
高级:直接改配置文件
不想在飞书里点的话,/invite、/config 背后写的是 ~/.best-feishu-bot/bots/<bot>/config.json 中对应 profile 的 access 字段。空白名单表示这个名单没人,不表示所有人都能用。下面只是 profile 里的字段片段,不要整段覆盖 config.json:
{
"schemaVersion": 2,
"profiles": {
"claude": {
"agentKind": "claude",
"access": {
"allowedUsers": ["ou_xxxxxxxxxxxxx"],
"allowedChats": ["oc_xxxxxxxxxxxxx"],
"admins": ["ou_xxxxxxxxxxxxx"],
"requireMentionInGroup": true
}
}
}
}allowedUsers / admins 填用户 open_id,allowedChats 填群 chat_id。手动找 ID 最简单的办法:让对方给 bot 发条消息(群里就 @ 它一下),然后看当前 profile 的日志:
grep '"event":"enter"' ~/.best-feishu-bot/bots/default/profiles/<profile>/logs/bridge-$(date +%Y%m%d).jsonl | tail -5每行都带 chatId(群 / 私聊 ID)和 senderId(用户 open_id)。手改完后重启 bridge,或在允许的 admin 上下文里发 /reconnect 让它生效。日常调整还是 /invite / /config 更省事,直接改文件主要用于部署脚本预填。
云文档评论
云文档评论不再需要单独绑定工作目录或维护文档白名单。支持的文档评论里 @bot 后,bridge 会在同一个评论线程里回复。评论运行复用文档级 session key,并保持在当前 bot 配置的工作目录内。
常见问题
bot 没反应 / agent 不回复:通常是当前 bot 的 claude/settings.json 不可用、本机 codex CLI 没登录,或者当前会话指向了不存在的工作目录。发 /status 看当前状态;/new 重开会话往往就好。
agent 子进程假死(卡片停在最后一帧不动):支持 idle 探活。agent 一段时间没输出就会被 SIGTERM kill,卡片末尾会标出自动终止原因。默认关闭。开启方式:/config 设全局值(分钟),或 /timeout 10 只对当前会话生效;/timeout off 关掉当前会话的探活;/timeout default 清掉会话覆盖,回退到全局设置。
图片发过去 agent 说看不到:升级到最新版,0.1.0 之前的版本有文件名去重 bug。
发布安装包
需要给没有合适 Node.js 环境的用户发一键安装包时,可以生成自包含安装产物:
pnpm build:installer -- --base-url https://example.com/best-feishu-bot默认产物在 release/installer/,包含:
install.sh:macOS 一行安装入口。install.ps1:Windows PowerShell 一行安装入口。best-feishu-bot-<version>-darwin-arm64.tar.gzbest-feishu-bot-<version>-darwin-x64.tar.gzbest-feishu-bot-<version>-win32-x64.zipmanifest.json
把整个 release/installer/ 目录上传到 --base-url 对应的静态地址后,用户可以执行:
curl -fsSL https://example.com/best-feishu-bot/install.sh | bashWindows PowerShell:
iwr https://example.com/best-feishu-bot/install.ps1 -UseBasicParsing | iex构建命令默认会把当前构建机的 Node.js 版本打进各平台包里;安装器会优先使用用户机器上满足 package.json#engines.node 的 Node.js,不满足时回退到包内 Node。需要指定 Node 版本或目标平台时:
pnpm build:installer -- --node-version 22.22.0 --targets darwin-arm64,darwin-x64,win32-x64如果项目根目录存在 .env,构建命令默认会把它打进安装包,并安装到运行时目录下的 config/.env;启动 wrapper 会通过 BEST_FEISHU_BOT_ENV_FILE 自动加载它,后台服务也会保留这个路径。这个产物可能包含 App Secret、供应商 token 等敏感配置,请按密钥文件保管。不要打包 .env 时:
pnpm build:installer -- --no-env测试与 CI
本地检查:
pnpm test
pnpm typecheck
pnpm buildpnpm test 包含 unit、integration 和 process-level adapter 测试。CI 在 macOS、Ubuntu、Windows 上执行 pnpm install --frozen-lockfile、pnpm test、pnpm typecheck 和 pnpm build。
可选:遥测(Telemetry)
默认情况下 bridge 不上报任何数据:没有指标、没有日志离开你的机器,也不引入任何遥测依赖。下面这个钩子在你主动开启前完全是空操作。
想接自己的监控时,用环境变量指向一个 default export(或导出 createAdapter)AdapterFactory 的模块:
LARK_CHANNEL_TELEMETRY_MODULE=your-telemetry-package best-feishu-bot start该模块会收到每一条 log.* 事件,以及错误 / 指标钩子,转发到任何你想要的地方。接口从包根导出:
import type { AdapterFactory, TelemetryAdapter, TelemetryEvent } from 'best-feishu-bot';
const createAdapter: AdapterFactory = (meta) => ({
emit(event) {/* 上报事件 */},
recordError(err, ctx) {/* 上报异常 */},
recordMetric(name, value, tags) {/* 上报指标 */},
flush(timeoutMs) {/* 冲刷缓冲事件 */},
});
export default createAdapter;模块不存在、工厂函数不合法、或者 adapter 抛错,都会降级为空操作——遥测永远不会阻止 bridge 启动,也不会打断日志。
