-
-
Notifications
You must be signed in to change notification settings - Fork 3.9k
feat(services): 新增 QQ OneBot 适配器 (services/qq-bot) #1668
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Draft
PhoenixForrestLin
wants to merge
31
commits into
moeru-ai:main
Choose a base branch
from
PhoenixForrestLin:feat/qq-bot
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Draft
Changes from 26 commits
Commits
Show all changes
31 commits
Select commit
Hold shift + click to select a range
87975ca
feat(qq-bot): add qq bot service
PhoenixForrestLin 9efb7e5
fix(deps): 修复缺失的依赖
PhoenixForrestLin 13a5fb3
[autofix.ci] apply automated fixes
autofix-ci[bot] ce8f220
fix(qq-bot): 修复 DecorateStage 长文本拆分失效
PhoenixForrestLin d23c8a7
fix(qq-bot): ProcessStage 并发安全 (correlationId)
PhoenixForrestLin 1a760bf
fix(qq-bot): 清理 airi-client 重复注册与私有属性访问
PhoenixForrestLin d2e613e
fix(qq-bot): FilterStage 空消息过滤逻辑
PhoenixForrestLin e8759af
fix(qq-bot): RateLimitStage interval 泄漏
PhoenixForrestLin 77f675c
refactor(qq-bot): PipelineExtensions 显式声明 proc_clearSession
PhoenixForrestLin d8e2a3d
refactor(qq-bot): AgentLoop 消除 any 类型
PhoenixForrestLin fbc6d69
build(qq-bot): Dockerfile 多阶段构建 + monorepo 支持
PhoenixForrestLin ef06dcc
chore(qq-bot): 固定 naplink 版本 + 更新文档
PhoenixForrestLin 29f10bd
docs(qq-bot): 更新 README,明确 airi 链接需要 token
PhoenixForrestLin 20bc27d
Merge branch 'feat/qq-bot' of github.com:PhoenixForrestLin/airi into …
PhoenixForrestLin 896352b
fix(qq-bot): 订阅 poke 事件到生产入口
PhoenixForrestLin 23348d0
fix(qq-bot): normalize AIRI structured content before trim && WakeSta…
PhoenixForrestLin e9b1586
fix(qq-bot): restrict reply wakeups to replies targeting the bot
PhoenixForrestLin 5e723f5
fix(qq-bot): parse commands before enforcing wake-up gating
PhoenixForrestLin f11713c
fix(qq-bot): normalize summary output content before trimming
PhoenixForrestLin a497ba5
fix(qq-bot): prevent lost updates when persisting conversation history
PhoenixForrestLin a65646c
fix(qq-bot): advance checkpoint when proactive decision is wait
PhoenixForrestLin 7a7d799
Merge branch 'moeru-ai:main' into feat/qq-bot
PhoenixForrestLin 60e53a2
fix(qq-bot): always release conversation mutex in runner exit paths
PhoenixForrestLin 5038ccf
fix(qq-bot): align NodeNext ESM runtime behavior
PhoenixForrestLin cdc2608
fix(qq-bot): add id tie-breaker to message-history ordering
PhoenixForrestLin 5559a80
Merge branch 'moeru-ai:main' into feat/qq-bot
PhoenixForrestLin a684c5f
fix: 防止会话锁双重释放 & 补全 Dockerfile 拓扑构建
PhoenixForrestLin 51d54ce
Merge branch 'main' into feat/qq-bot
PhoenixForrestLin f814f54
fix(qq-bot): 显式配置 botQQ 以修复 @bot 唤醒失效
PhoenixForrestLin b45651f
Merge branch 'moeru-ai:main' into feat/qq-bot
PhoenixForrestLin 32628ff
[autofix.ci] apply automated fixes
autofix-ci[bot] File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
Large diffs are not rendered by default.
Oops, something went wrong.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Empty file.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,65 @@ | ||
| # Copilot instructions for `services/qq-bot` | ||
|
|
||
| ## Build, test, and lint commands | ||
|
|
||
| Run commands from repo root (`airi`) unless noted. | ||
|
|
||
| - Install workspace deps: `pnpm install` | ||
| - Run this service once: `pnpm -F @proj-airi/qq-bot start` | ||
| - Run this service in watch mode: `pnpm -F @proj-airi/qq-bot dev` | ||
| - Typecheck this service: `pnpm -F @proj-airi/qq-bot typecheck` | ||
|
|
||
| Repository-level commands (used when validating broader impact): | ||
|
|
||
| - Lint all workspaces: `pnpm lint` | ||
| - Auto-fix lint/format: `pnpm lint:fix` | ||
| - Run all tests: `pnpm test:run` | ||
|
|
||
| Single test command pattern: | ||
|
|
||
| - `pnpm exec vitest run <path/to/test-file>` | ||
| - Example: `pnpm exec vitest run services/qq-bot/src/some-feature.test.ts` | ||
|
|
||
| ## High-level architecture | ||
|
|
||
| This package is a QQ OneBot adapter scaffold built around NapLink and a staged message pipeline. | ||
|
|
||
| - `src/config.ts` is the configuration center: | ||
| - defines `BotConfigSchema` with Valibot, | ||
| - exports all config types via `v.InferOutput`, | ||
| - loads YAML and applies env fallback for LLM fields (`LLM_API_BASE_URL`, `LLM_API_KEY`, `LLM_MODEL`). | ||
| - `src/client.ts` is the runtime composition root: | ||
| - builds `NapLink` client, | ||
| - wires `Dispatcher -> PipelineRunner`, | ||
| - normalizes incoming `message.group` / `message.private` events, | ||
| - runs graceful shutdown (`SIGINT` / `SIGTERM`). | ||
| - `src/types/*` defines protocol-safe internal contracts: | ||
| - `event.ts`: normalized `QQMessageEvent` and `sessionId` format (`qq:{type}:{id}`), | ||
| - `context.ts`: pipeline blackboard (`PipelineContext`) and `StageResult`, | ||
| - `message.ts`: typed message segments with input/output separation, | ||
| - `response.ts`: discriminated union payloads + fail-fast factory helpers. | ||
| - `src/pipeline/stage.ts` defines the stage base contract and timing/error wrapper. | ||
| - `src/pipeline/extensions.ts` reserves a strongly-typed cross-stage extension area. | ||
| - `src/utils/logger.ts` + `src/utils/naplink-logger-adapter.ts` provide unified logging and NapLink logger bridging. | ||
|
|
||
| Design reference for the intended 7-stage pipeline (`Filter -> Wake -> RateLimit -> Session -> Process -> Decorate -> Respond`) is in: | ||
|
|
||
| - `Project AIRI — QQ OneBot 适配器设计文档 ... .md` | ||
|
|
||
| Current repository status to keep in mind while coding: | ||
|
|
||
| - Treat the checked-in source tree as the source of truth. | ||
|
|
||
| ## Key conventions in this codebase | ||
|
|
||
| - Keep config as a single source of truth in Valibot schemas; derive TS types from schemas instead of parallel interfaces. | ||
| - Use explicit discriminated unions (`kind`, `action`, `type`) for pipeline flow and payloads; avoid loosely typed records. | ||
| - Preserve the input/output message segment split: | ||
| - input may contain `reply` segments, | ||
| - output payloads must not contain `reply`; use `replyTo` and let dispatch layer inject reply segments. | ||
| - Use `PipelineContext` as the shared stage blackboard; cross-stage extra data belongs in `context.extensions` with typed fields, not ad-hoc metadata. | ||
| - Follow fail-fast helpers in `src/types/response.ts` (throw on invalid empty payloads) instead of silent fallbacks. | ||
| - Keep session identity format consistent: `qq:{sourceType}:{groupId|userId}`. | ||
| - Prefer factory-based assembly for runtime wiring (`createBot`, `createDispatcher`, normalizers, runner) and keep orchestration in composition roots. | ||
| - Route all logs through `createLogger(...)`/`initLoggers(...)`; do not introduce standalone logging patterns. | ||
| - Use `pnpm` workspace filters (`pnpm -F ...`) for service-scoped runs in this monorepo. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,3 @@ | ||
| # Ignore the config file and data directory | ||
| config.yaml | ||
| data/* |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,34 @@ | ||
| FROM node:22-alpine AS builder | ||
|
|
||
| WORKDIR /app | ||
|
|
||
| RUN corepack enable | ||
|
|
||
| COPY pnpm-lock.yaml pnpm-workspace.yaml package.json tsconfig.json ./ | ||
| COPY services/qq-bot/package.json services/qq-bot/tsconfig.json ./services/qq-bot/ | ||
| COPY services/qq-bot/src ./services/qq-bot/src | ||
| COPY packages/server-sdk/package.json packages/server-sdk/tsconfig.json ./packages/server-sdk/ | ||
| COPY packages/server-sdk/src ./packages/server-sdk/src | ||
| COPY packages/server-shared/package.json packages/server-shared/tsconfig.json ./packages/server-shared/ | ||
| COPY packages/server-shared/src ./packages/server-shared/src | ||
|
|
||
| RUN pnpm install --frozen-lockfile | ||
| RUN pnpm --filter @proj-airi/qq-bot build | ||
|
|
||
| FROM node:22-alpine AS production | ||
|
|
||
| WORKDIR /app | ||
|
|
||
| RUN corepack enable | ||
|
|
||
| COPY pnpm-lock.yaml pnpm-workspace.yaml package.json ./ | ||
| COPY services/qq-bot/package.json ./services/qq-bot/package.json | ||
| COPY packages/server-sdk/package.json ./packages/server-sdk/package.json | ||
| COPY packages/server-sdk/src ./packages/server-sdk/src | ||
| COPY packages/server-shared/package.json ./packages/server-shared/package.json | ||
| COPY packages/server-shared/src ./packages/server-shared/src | ||
| COPY --from=builder /app/services/qq-bot/dist ./services/qq-bot/dist | ||
|
|
||
| RUN pnpm install --frozen-lockfile --prod | ||
|
|
||
| CMD ["node", "services/qq-bot/dist/index.js"] | ||
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.