README.md

June 17, 2026 · View on GitHub

cc-bot logo

CC-BOT

Develop project from group chat — by Claude Code
接 AI 进群里开发项目 — 飞书(Lark)/ Slack

IM group  →  Monitor  →  Intent  →  Claude acts  →  Chat reply
one plugin, any project, zero backend.

version   install   im   node   platform   MIT


Why CC-BOT? · 为什么做 CC-BOT?

Problem — Team members want to query and trigger project actions from the group chat ("what's the progress?" / "run tests" / "deploy staging" / "why did build fail?") without switching to terminals, dashboards, or ticket systems. Existing chat bots need bespoke backends per project and rarely integrate with an AI coding agent.

Solution — CC-BOT is a Claude Code plugin that listens to IM group messages, routes natural-language intents to per-project actions (you define them), runs them through Claude, and replies back. One plugin, any number of projects — each project's own profile.intents dict (intent → action description).


问题 —— 团队希望在群里就能查询和触发项目操作(「进度怎么样?」「跑测试」「部署灰度」「构建为什么失败?」),而不用切到终端 / 仪表盘 / 工单系统。现有聊天机器人通常需要为每个项目定制后端,且很少与 AI 编程助手打通。

方案 —— CC-BOT 是 Claude Code 插件:监听 IM 群消息,把自然语言意图路由到项目特定动作(由你定义),通过 Claude 执行,结果回到群里。一份插件、任意项目 —— 每个项目自己的 profile.intents 字典(意图 → 动作描述)。

Tip

Windows users: Use npm i -g @anthropic-ai/claude-code instead of the native installer to avoid Bun memory crashes (oven-sh/bun#25082). cc-bot's Monitor runs long-lived, amplifying Bun's memory pressure.

Windows 用户: 建议用 npm i -g @anthropic-ai/claude-code 代替原生安装器,规避 Bun 内存崩溃;cc-bot 的 Monitor 是长驻进程,会放大 Bun 的内存问题。


Features

Streaming Cards
Lark CardKit v2 typewriter
三态 header(蓝→绿/红)
实时打字 + 耗时收尾

Interactive Setup
guided wizard · auto-detect IDs
profile schema 自动 backfill

IM-agnostic
Lark · Slack
capability-based adapter

Per-project Intents
JSON 自定义动作
含 permission 分级

Auto Redact
token / 真名 / 飞书 ID /
邮箱 / 手机号 发群前强制 scrub

Crash-resistant
3-layer defense
PID lock · EPIPE · state heal

Code-driven
permission / intent / dispatch /
redact 全代码化,prose 不膨胀

█▌

HUD-aware
statusline shim
tees cc-hud if installed

Install

Inside Claude Code in your target project, run these in order:

/plugin marketplace add WaterTian/cc-bot
/plugin install cc-bot@cc-bot
/reload-plugins
/cc-bot:setup
  • Line 1 — register the plugin source (GitHub repo)

  • Line 2 — download to ~/.claude/plugins/cache/. CC will pop a scope selector; pick one:

    OptionWhen to useRecommendation
    Install for you (user scope)You plan to use cc-bot across many projects✅ Daily use
    Install for all collaborators (project scope)Team project, want teammates to auto-get cc-bot on clone✅ Team projects
    Install for you, in this repo only (local scope)First-time try, don't pollute other projects✅ Quick try
  • Line 3 — hot-reload plugin list without restarting CC (new since CC 2.1.x; faster than /exit + re-open)

  • Line 4 — enter the interactive setup wizard (lark-cli auto-install, OAuth login, chat picker via AskUserQuestion cards, config auto-fill)

Note

If /reload-plugins is unavailable or /cc-bot:* commands still don't appear, fall back to /exit and relaunch Claude Code.


Updating

v0.1.40+ 升级流程(推荐,逐条执行):

/cc-bot:stop                          # 若 bot 在跑
/plugin marketplace update cc-bot     # 刷新 marketplace 清单(CC 会打开面板,看到新版关闭即可)
/plugin update cc-bot@cc-bot          # 把新版下载到 cache(同样可能打开面板)
/reload-plugins                       # 热加载新版到当前会话
/cc-bot:start                         # 内含 self-heal:profile schema backfill + Bash 权限补齐,老用户无感升级

Important

CC 的 /plugin ...交互式命令(会打开 Plugin Marketplace 面板),不支持 shell && 串联,必须逐条等执行完再下一条。想真正 1 步省心 → 用下面 > [!TIP] 块里的 autoUpdate opt-in。

/cc-bot:start 启动前会自动跑 profile-migrate.js apply(v0.1.29+)+ Bash 权限完备度补齐(v0.1.38+ 同 setup §9 逻辑),都是幂等纯加法:无字段缺 / 无权限缺 = 静默;有补 = ℹ self-heal: 补全 N 个字段 + M 条权限 报告后正常启动。失败不阻塞 start。

完全省略了老的 /cc-bot:setup + /cc-bot:doctor 中间两步。

Tip

真正一键升级 — autoUpdate(可选 opt-in) (v0.1.41+)

首次运行 /cc-bot:setup 时 wizard 会用 AskUserQuestion 卡问 "Enable autoUpdate?",默认 No 保守;选 Yes 自动把以下片段 merge 进 ~/.claude/settings.json

{
  "extraKnownMarketplaces": {
    "cc-bot": {
      "source": { "source": "github", "repo": "WaterTian/cc-bot" },
      "autoUpdate": true
    }
  }
}

配上 /cc-bot:start 的 self-heal,完整升级流程降到 2 步且无交互面板

  1. /exit 退出 CC,shell 里 claude 重启 → CC 启动时 autoUpdate 自动拉最新版
  2. 进新会话 /cc-bot:start → self-heal + 启动

后悔了想关 / 没装时想开 → 手工把 autoUpdatetrue/false 即可,无需重跑 setup。

进阶:手工排查(旧流程,self-heal 失败时回退)

/cc-bot:setup     # 显式跑 profile-migrate + Bash 权限注册 + hooks 注册
/cc-bot:doctor    # 只读健康检查 — 版本漂移 / profile / 权限完备度 / lark-cli scope / agents.json schema
  • lark-cli scope 漂移(v0.1.22+ 流式卡片要求 cardkit:card:write + cardkit:card:read)—— 升级 lark-cli 后必须 lark-cli auth login --scope "cardkit:card:write cardkit:card:read" 重新拿 token,否则 streaming card 调不动。/cc-bot:doctor 会显式检查这两个 scope。
  • Switching a project to Slack (v0.1.12+) — install the SDK (npm i -g @slack/socket-mode @slack/web-api), then re-run /cc-bot:setup; the wizard starts with an IM picker. One project = one IM.

From source (development / contributors)
git clone https://github.com/WaterTian/cc-bot.git

In your target project, launch Claude Code with the local plugin dir:

cd /your/project
claude --plugin-dir /absolute/path/to/cc-bot

Then /cc-bot:setup. Skips marketplace install — loads straight from the local repo. Ideal for iterating on cc-bot itself.


Quick Start — what /cc-bot:setup does · 快速开始

Setup prints a version banner (cc-bot v<X.Y.Z> setup — <project>), then runs through these steps — guided by AskUserQuestion cards, with IDs auto-detected wherever possible:

  1. Pick IM · 选 IMlark or slack. One project = one IM (switching needs profile rewrite).
  2. Detect tooling · 检测工具 — lark: auto-install lark-cli via npm i -g @larksuite/cli. slack: verify @slack/socket-mode + @slack/web-api (npm i -g @slack/socket-mode @slack/web-api if missing).
  3. Authenticate · 认证 — lark: OAuth Device Flow login (with app-creation checklist). slack: paste templates/slack-manifest.yaml into App's "From a manifest" form, then paste xoxb- Bot + xapp- App-Level tokens (scope connections:write).
  4. Pick target chat · 选目标群 — lark: list bot's chats via AskUserQuestion card or one-click create. slack: paste channel ID C0xxx; wizard probes + reminds /invite @cc-bot.
  5. Auto-detect IDs · 自动探测 — lark: bot_app_id / admin_open_id from lark-cli auth list. slack: bot_user_id from auth.test. Zero manual entry.
  6. Write config · 写配置.cc-bot/profiles/active.json (IM-branched fields) + state.json + .gitignore. Locale defaults: zh-CN (lark) / en-US (slack); override via im.locale.
  7. Register statusline shim · 注册 shim — tees stdin JSON to hud-stdin.json (for bot's HUD intent) + cc-hud rendering if installed.
  8. Register Bash permission set · 注册 Bash 权限集 (v0.1.38+) — append IM-specific wildcards (runtime/*.js · lark-cli * · npm install -g @larksuite/cli* / @slack/* · curl api.github.com) to <project>/.claude/settings.local.json. Strictly additive + idempotent — never overwrites existing rules.

Every step is idempotent — rerun safely. Then /cc-bot:start — bot online in ≤ 5s.


How It Works

Main session ── Monitor(persistent) ── node poll.js ── lark: every 10s IMAdapter.listRecentMessages()
                                                       slack: Socket Mode WebSocket push (event-driven)
                                                    ├─ dedupe via state.last_processed_time + poll.emitted
                                                    └─ stdout: NEW_MSG|msg_id|sender|text|ts
                                                               ↓ Monitor → notification
                                                         main session → permission.js check → intent.js resolve
                                                                      → dispatch.js register(slot/tags/serial)
                                                                      → spawn worker subagent

                                                worker → streaming-card.js report(lark)
                                                       → slack-send.js send-text(slack)
                                                       → redact.js 自动脱敏(两路径强制)
HTTP polling (lark)
10s default interval · VPN-proxy safe
Socket Mode push (slack)
WebSocket event-driven
mainBusy still emits
3-layer defense
PID lockfile · EPIPE self-kill
state future-value heal
Per-project isolation
.cc-bot/ per project
zero cross-contamination

Code-driven decisions(v0.1.22+ runtime/)

工具用途
runtime/streaming-card.jsLark CardKit v2 流式卡片 driver — 单一 report 入口,CLI 内部按 profile + 内容形态自动选 卡片 / 文本 / 降级 reply,自动脱敏。v0.1.36+ state.lastContentHash sha1 dedup 跳过同 content 重复 patch
runtime/streaming-card-policy.jsv0.1.35+ canUseStreamingCard(profile) 单一事实源,被 streaming-card / dispatch / todo-bridge 共用,去重 3 处 inline im.type + enabled 判断漂移
runtime/atomic-write.jsv0.1.36+ 原子写 helper(tmp + fsync + rename + cleanup)— 全 runtime 状态文件(agents.json / stream-*.json / poll.busy-held / profile / 等 8 处)crash-safe
runtime/permission.js角色判定 + intent level 映射(public / admin / admin-confirm / group-rejected),含高危名字防御启发式
runtime/intent.jsintent 解析:占位符替换(<project.root> / <paths.bot_temp_abs> 等)+ 动态可用清单(doc_progress 文件存在校验)
runtime/redact.js文本脱敏(slack token / Bearer / JWT / app_secret=* / 飞书 cli_/ou_/om_ ID / 邮箱 / 手机号 / blocklist 真名)—— lark + slack 发群入口强制调
runtime/slack-send.jsv0.1.12+ Slack Web API 跨平台 helper,规避 Win curl GBK 乱码 + token 暴露;自动 redact
runtime/ack-detect.js短消息 ACK 语义判定(yes / continue / ok / thanks + 停止词否决)+ 推荐回复
runtime/dispatch.jsagents.json 调度生命周期(evaluate / register / complete / sweep)— tags 冲突 + slot + 同 user 串行全代码化。v0.1.33+ register 同步预热流式卡片(首帧 6-10s → 1-2s);v0.1.35+ register 响应带 preheated:bool 让 SKILL.md 一行判要不要回群占位;v0.1.37+ sweep 子命令按 profile.dispatch.max_turn_time_mins(默认 0=不启用)回收超时 running + 释放 slot + agents.json version 字段 CAS 防 lost update
runtime/profile-migrate.js版本化 profile schema migration — 升级时自动 backfill 历史新增字段,不覆盖用户已设值
runtime/todo-bridge.jsv0.1.32+ CC PreToolUse hook bridge — 主会话调 TodoWrite / TaskCreate / TaskUpdate 时自动 diff todos 变化 → spawn streaming-card.js 把进度(▸ 进行中 / ✓ 完成)推到当前 running 任务的卡片,worker 端零负担(hook 异步 detached 不阻塞主会话)

设计原则:决策、转换、状态管理代码化,prose(SKILL.md / worker.md)只描述"调哪个命令、按返回 action 走",LLM 推理负担和文档膨胀双降


Commands

CommandWhat it does
/cc-bot:setupFirst-run interactive wizard (idempotent, safe to re-run)
/cc-bot:start · 开bot / start botStart Monitor + send online notification to chat
/cc-bot:stop · 关bot / stop botStop Monitor + send offline notification
/cc-bot:new-profile <name>Create new profile from template
/cc-bot:switch <name>Switch active profile (auto-stops running bot first)
/cc-bot:doctorRead-only health check — version drift, profile validity, runtime state, zombie permissions, shim registration

Main session also accepts natural-language triggers (开bot / 关bot / switch to xxx).


Profile Intents — Per-project Customization

Each project has its own .cc-bot/profiles/active.json. The intents dict maps natural-language intents to action descriptions Claude executes when the group triggers them. Typical examples (you pick the keys and describe the actions freely):

{
  "intents": {
    "deploy": "Run `bash scripts/deploy.sh production`, report stdout tail",
    "run_tests": "Run `npm test`, report pass/fail counts + first failure trace",
    "query_logs": "Use mcp__cloudbase__logs to fetch last 20 error logs, summarize",
    "build_preview": "Run `npm run build:preview`, upload artifact to <paths.bot_temp_abs>, reply with link"
  },
  "intent_permissions": {
    "deploy": "admin",
    "drop_data": "admin-confirm"
  }
}

intent_permissions(v0.1.23+,可选)声明每个 intent 的权限级别:

  • public — 任何群成员可触发(默认)
  • admin — 仅 members.admin_open_ids 白名单可执行
  • admin-confirm — 即使 admin 也需口头确认一次(破坏性操作)
  • group-rejected — 群里发一律拒(bot 开关类)

未声明的项目 intent,名字含 deploy / publish / release / drop_* / delete_* / reset_* / restart_* / prod* 等高危词时自动默认 admin(防 legacy profile 把生产操作意外公开),其他默认 public

Works for any project type — Web / mini-program / Node service / Python data pipeline / mobile app. If you can script it, you can intent-route it.


Prerequisites

  • Claude Code — uses Skill / Monitor / TaskStop / AskUserQuestion tools
  • For lark: npm i -g @larksuite/cli + lark-cli auth login (setup wizard will guide this)
  • For slack: npm i -g @slack/socket-mode @slack/web-api + create an App at api.slack.com/apps via the templates/slack-manifest.yaml (setup wizard will guide token paste-in)
  • ShellWindows: Git Bash required (cmd.exe / PowerShell mangle special characters in argv); macOS / Linux: system bash works out of the box
  • Optional: cc-hud — install for prettier status bar (/plugin install cc-hud@WaterTian-cc-hud); cc-bot shim tees it automatically

Per-project Layout

ComponentLocationDistribution
SKILL · adapter · poll.js · commands · templates${CLAUDE_PLUGIN_ROOT}/plugin version
Chat IDs · project root · members · intents<project>/.cc-bot/profiles/active.jsonper-project (gitignored)
state · cache · pid · dedupe · bot_temp<project>/.cc-bot/runtime/ + .cc-bot/bot_temp/per-project (gitignored)

One plugin, many projects in parallel — zero cross-contamination.


Extend to a New IM

cc-bot ships with Lark + Slack. Adding WeCom / DingTalk / Discord / Telegram / etc:

  1. Add adapters/<im>.js extending IMAdapter (see adapters/base.js) — implement listRecentMessages / sendText / sendImage / downloadResource / getUser; for push-based IMs also implement startListening / stopListening (see adapters/slack.js for Socket Mode reference)
  2. Add factory branch in runtime/poll.js: if (im.type === '<im>') { ... }; set IM_MODE = 'polling' (HTTP fetch loop) or 'push' (WebSocket / callback) — push-mode messages must emit even during mainBusy (errors are permanent, no retry tick)
  3. Set im.type in profile.active.json to the new IM name; optionally extend DEFAULT_LOCALE_BY_IM for system-message i18n
  4. Add skills/<im>-bot/SKILL.md or extend existing one

Privacy Protection

两层防御

① Runtime auto-redact(v0.1.24+)runtime/redact.js 在所有发群路径(streaming-card.js report / slack-send.js send-text)入口自动过一遍 scrub:

敏感串类型替换为
Slack token (xoxb-* / xapp-*)<redacted:slack_xoxb> / <redacted:slack_xapp>
Bearer / JWT / app_secret=* / api_key=*<redacted:bearer> / <redacted:jwt> / <redacted:secret_kv>
飞书 ID (cli_* / ou_* / om_*)<redacted:lark_app_id> / <redacted:lark_open_id> / <redacted:lark_msg_id>
邮箱 / 中国手机号<redacted:email> / <redacted:phone_cn>
profile.privacy.blocklist 自定义真名<同事>(可改 blocklist_replace

worker 不需要手动调;CLI 强制脱敏,无遗漏路径。

② Pre-commit hook(开发本仓库时装) — 阻塞真实 IM ID / 黑名单真名 / api-secret 进 git commit。一次性 setup 见 CLAUDE.md §Git 提交隐私防护.


Star History

Star History Chart

MIT License © Water