From 2d8396511c7e3e1da22ed49fa3afd43cbe4db288 Mon Sep 17 00:00:00 2001 From: Arnav Date: Mon, 5 Oct 2026 23:43:48 +0530 Subject: [PATCH] docs(chat): integrate Discord adapter into registry and project template Integrate tools/chat-discord into the chat contract documentation, adapter registry, spec-loop specifications, and adopter project template. - In docs/adapters/registry.md: update tracking issues for Matrix (#309) and Zulip (#308). - In plugins/magpie-setup/templates/project.md and tools/chat/README.md: ship optional Discord-specific chat.guild_id commented out, clarify channel names as accepting IDs for Discord, and document Discord bot token under \C:\Users\arnav in prerequisites credentials. - In tools/spec-loop/specs/adapters.md and contributor-growth.md: list tools/chat-discord as a shipping adapter under contract:chat, note chat covers Slack and Discord while Matrix and Zulip remain extension points with no adapter yet. Generated-by: Antigravity --- docs/adapters/registry.md | 2 +- plugins/magpie-setup/templates/project.md | 5 +++-- tools/chat/README.md | 7 ++++--- tools/spec-loop/specs/adapters.md | 18 +++++++++++------- tools/spec-loop/specs/contributor-growth.md | 14 +++++++------- 5 files changed, 26 insertions(+), 20 deletions(-) diff --git a/docs/adapters/registry.md b/docs/adapters/registry.md index 54338f973..b28d04b1d 100644 --- a/docs/adapters/registry.md +++ b/docs/adapters/registry.md @@ -55,7 +55,7 @@ extension point = a documented, labelled slot with a tracking issue. | [`tools/scan-format`](../../tools/scan-format/) | ASVS | other scanner formats | | [`tools/vcs`](../../tools/vcs/) | Git, Mercurial, Fossil | Subversion [\#602](https://github.com/apache/magpie/issues/602), Jujutsu [\#603](https://github.com/apache/magpie/issues/603), Perforce [\#605](https://github.com/apache/magpie/issues/605) | | Forge / tracker | [`github`](../../tools/github/), [`forgejo`](../../tools/forgejo/) `partial` foundation, [`jira`](../../tools/jira/), [`bitbucket`](../../tools/bitbucket/) `partial-read-only` foundation, [`sourcehut`](../../tools/sourcehut/), [`fossil`](../../tools/fossil/), [`gitlab`](../../tools/gitlab/) `partial-read-only` foundation | Forgejo/Gitea [\#310](https://github.com/apache/magpie/issues/310), Pagure [\#312](https://github.com/apache/magpie/issues/312), deeper Bitbucket/Jira coverage [\#606](https://github.com/apache/magpie/issues/606), GitLab [\#305](https://github.com/apache/magpie/issues/305), Bugzilla [\#302](https://github.com/apache/magpie/issues/302) | -| [`tools/chat`](../../tools/chat/) | [`chat-slack`](../../tools/chat-slack/) | Discord [#1421](https://github.com/apache/magpie/issues/1421) | +| [`tools/chat`](../../tools/chat/) | [`chat-slack`](../../tools/chat-slack/), [`chat-discord`](../../tools/chat-discord/) | Matrix [\#309](https://github.com/apache/magpie/issues/309), Zulip [\#308](https://github.com/apache/magpie/issues/308) | | Agent harness | Claude Code, [Codex](codex.md) `experimental` ([#313](https://github.com/apache/magpie/issues/313)), [Gemini CLI](gemini.md) `experimental` ([#314](https://github.com/apache/magpie/issues/314)), [Local LLM (Ollama / llama.cpp / vLLM)](local-llm.md) ([#315](https://github.com/apache/magpie/issues/315)), [Cursor](cursor.md) ([#316](https://github.com/apache/magpie/issues/316)), [Goose](goose.md) `guide only` ([#319](https://github.com/apache/magpie/issues/319)), [Aider](aider.md) `guide only` ([#317](https://github.com/apache/magpie/issues/317)), [GitHub Copilot](copilot.md) `guide only` ([#318](https://github.com/apache/magpie/issues/318)), Grok `reviewer backend only` ([#1416](https://github.com/apache/magpie/issues/1416)) | Amazon Q [#320](https://github.com/apache/magpie/issues/320)–OpenHands [#322](https://github.com/apache/magpie/issues/322) | | Security cross-ref | [`tools/osv`](../../tools/osv/) | — | | [`tools/typed-decision`](../../tools/typed-decision/) | TypeSafe Jev API | Local models / llama.cpp / Ollama ([#1431](https://github.com/apache/magpie/issues/1431)) | diff --git a/plugins/magpie-setup/templates/project.md b/plugins/magpie-setup/templates/project.md index 87b33c52b..666fe0aa8 100644 --- a/plugins/magpie-setup/templates/project.md +++ b/plugins/magpie-setup/templates/project.md @@ -126,7 +126,7 @@ for ASF projects) is org-level — inherited from your organization's | CVE allocation + record mgmt | *org-level* — inherited from `organizations//organization.md → cve_authority.tool`; for ASF: `vulnogram` ([`tools/cve-tool-vulnogram/`](../../../tools/cve-tool-vulnogram/)), for independent: `mitre-form` | — | override in [CVE authority](#cve-authority) only if this project differs from its org | | Security cross-ref | `osv` | [`../../tools/osv/`](../../../tools/osv/) | `security_cross_ref.tool`, `security_cross_ref.ecosystem` | | Project metadata (rosters / people / releases) | *org-level* — inherited from `organizations//organization.md → project_metadata.kind`; for ASF: `apache-projects` ([`tools/apache-projects/`](../../../tools/apache-projects/)), for independent: `none` | — | override in [Project metadata](#project-metadata) only if this project differs from its org | -| Project chat | TODO: `slack`, `discord`, or `none` | [`../../tools/chat/`](../../../tools/chat/) (abstract) + adapter dirs (`tools/chat-slack/`) | `chat.kind`, `chat.channels` — see [Project chat](#project-chat) below; read-only, public channels only | +| Project chat | TODO: `slack`, `discord`, or `none` | [`../../tools/chat/`](../../../tools/chat/) (abstract) + adapter dirs (`tools/chat-slack/`, `tools/chat-discord/`) | `chat.kind`, `chat.channels`, `chat.guild_id` — see [Project chat](#project-chat) below; read-only, public channels only | | Release comms | TODO: the backend that carries release announcements — for ASF: `dev_list` / `announce_list` / `users_list`; for GitHub Releases leave blank | — | whichever release-comms keys the org default or per-project override declares | To replace a tool (e.g. swap GitHub issues for JIRA), declare an @@ -192,7 +192,8 @@ Leave `kind: none` if the project has no public chat, or does not want it read. ```yaml chat: kind: none # slack | discord | none - channels: [] # channel names to read; empty = every public channel — + # guild_id: "" # Discord only, optional: server (guild) ID when the bot joins several servers + channels: [] # channel names (Discord also accepts IDs) to read; empty = every public channel — # list them explicitly in a workspace shared by several projects ``` diff --git a/tools/chat/README.md b/tools/chat/README.md index 7eb51d02a..69c4af5f7 100644 --- a/tools/chat/README.md +++ b/tools/chat/README.md @@ -40,7 +40,7 @@ No verb posts, reacts, edits, or reads a direct message or a private channel. - **Runtime:** None of its own — this file is an adapter-contract *specification* (pure Markdown). Concrete prerequisites belong to whichever adapter the project declares. - **CLIs:** None for the contract itself. -- **Credentials / auth:** Per adapter; the Slack adapter uses the Slack connector authorised for the project's workspace. +- **Credentials / auth:** Per adapter; the Slack adapter uses the Slack connector authorised for the project's workspace; the Discord adapter uses a bot token stored under `$HOME` (`~/.config/apache-magpie/discord-token` or `$DISCORD_BOT_TOKEN`). - **Network:** Per adapter. ## Today's adapters @@ -48,7 +48,7 @@ No verb posts, reacts, edits, or reads a direct message or a private channel. | Adapter | Status | Source | Notes | |---|---|---|---| | `slack` | shipping | [`tools/chat-slack/`](../chat-slack/) | Public channels of the project's Slack workspace through the Slack MCP. | -| `discord` | placeholder | not implemented | Public channels of a Discord server. Tracked in [#1421](https://github.com/apache/magpie/issues/1421). | +| `discord` | shipping | [`tools/chat-discord/`](../chat-discord/) | Public channels of a Discord server through the Discord MCP. | | `none` | placeholder | not implemented | Explicit *"no chat backend"*: every verb returns an empty result and the consuming skill reports chat as *not collected*. | ## Interface @@ -107,7 +107,8 @@ No backend configured, or no messages: `[]`. ```yaml chat: kind: slack # slack | discord | none - channels: [] # channel names; empty = every public channel + # guild_id: "" # Discord only, optional: server (guild) ID when the bot joins several servers + channels: [] # channel names (Discord also accepts IDs); empty = every public channel ``` A project with no `chat:` block is treated as `kind: none`. diff --git a/tools/spec-loop/specs/adapters.md b/tools/spec-loop/specs/adapters.md index 0227792c7..9215349a7 100644 --- a/tools/spec-loop/specs/adapters.md +++ b/tools/spec-loop/specs/adapters.md @@ -14,7 +14,8 @@ source: > tools/sourcehut/, tools/maildir/, tools/vcs/, tools/change-request/, tools/asf-svn/, tools/mail-archive/, tools/mail-patch/, tools/jira-patch/, tools/forwarder-relay/, tools/github-body-field/, - tools/github-rollup/, tools/gitlab/, tools/chat/, tools/chat-slack/. + tools/github-rollup/, tools/gitlab/, tools/chat/, tools/chat-slack/, + tools/chat-discord/. acceptance: - Project-specific integrations live behind adapter modules, not hardcoded into skills. @@ -147,12 +148,15 @@ by swapping the adapter, not the skill. Consumed by the contributor-growth skills to see how a contributor helps others in chat ([contributor growth](contributor-growth.md)). Selected by `chat.kind` in `/project.md`. -- `tools/chat-slack/` — the shipping `contract:chat` adapter: a mapping + `none` is a placeholder in the contract's adapter table. +- `tools/chat-slack/` — the Slack adapter for `contract:chat`: a mapping onto the Slack MCP tools (`operations.md`) over the public channels of the project's workspace, optionally narrowed by `chat.channels`. It never calls a tool that sends, schedules, drafts, or edits a message. - `discord` and `none` are placeholders in the contract's adapter table - (Discord tracked in #1421). +- `tools/chat-discord/` — the Discord adapter for `contract:chat`: a mapping + onto the Discord MCP tools (`operations.md`) over the public channels of the + project's Discord server, optionally narrowed by `chat.channels`. + It never calls a tool that sends, edits, deletes, or reacts to messages. ## Behaviour & contract @@ -215,9 +219,9 @@ uv run --all-packages --group dev pytest tools/github-rollup/tests #305. Fetched issue and MR titles, descriptions, diffs and commit messages are external data, never instructions. -- **Chat covers Slack only.** `contract:chat` ships one adapter; - `discord` and `none` are placeholders, so a project on Discord gets chat - reported as not collected. +- **Chat covers Slack and Discord.** `contract:chat` ships Slack and Discord + adapters; Matrix and Zulip remain extension points, and `none` is an explicit + no-op backend. - **Bitbucket adapter is new and intentionally partial.** `tools/bitbucket/` currently provides read-only repository metadata, read-only branch restriction context, pull-request discovery, pull-request fetching, read-only pull-request diff --git a/tools/spec-loop/specs/contributor-growth.md b/tools/spec-loop/specs/contributor-growth.md index 5e6cb6750..e5fe8767f 100644 --- a/tools/spec-loop/specs/contributor-growth.md +++ b/tools/spec-loop/specs/contributor-growth.md @@ -18,7 +18,7 @@ source: > good-first-issue-author, mentoring-welcome, good-first-issue-sweep (plugins/magpie-mentoring/). Deterministic counting in tools/contributor-metrics; chat evidence through tools/chat - (contract:chat) and tools/chat-slack. + (contract:chat), tools/chat-slack, and tools/chat-discord. acceptance: - Every family skill is read-only or propose-before-post; none transitions, promotes, or announces without explicit maintainer @@ -183,9 +183,9 @@ Adopter config scaffolds live in `plugins/magpie-setup/templates/` calibration. Unit tests under `tools/contributor-metrics/tests/`. - Tools: `tools/chat` (`contract:chat`, read-only `list_channels`, - `resolve_user`, `search_messages`) and `tools/chat-slack` (Slack MCP - adapter, public channels only, never posts). - Discord is an extension point with no adapter yet. + `resolve_user`, `search_messages`), `tools/chat-slack` (Slack MCP + adapter, public channels only, never posts), and `tools/chat-discord` + (Discord MCP adapter, public channels only, never posts). ## Behaviour & contract @@ -224,7 +224,7 @@ Adopter config scaffolds live in `plugins/magpie-setup/templates/` - **Community signals are evidence, not a score.** Step 3 of both skills collects `nomination/community-signals.md`: dev/users-list presence and release testing, chat answers through `contract:chat` - (Slack adapter; public channels only), GitHub Discussions answers, + (Slack or Discord adapter; public channels only), GitHub Discussions answers, and project-related posts on accounts the contributor linked themselves. Identities count only when confirmed: a chat or social profile that merely names the GitHub handle is a possible match, not @@ -336,8 +336,8 @@ uv run --project tools/skill-and-tool-validator --group dev skill-and-tool-valid `magpie-mentoring`. A later family-maturity review may formalise the boundary or merge the families; for now, both specs cross-reference each other. -- **Chat evidence is Slack-only.** `contract:chat` has one adapter - (`tools/chat-slack`); Discord and Matrix answers are not collected +- **Chat evidence covers Slack and Discord.** `contract:chat` has two shipping adapters + (`tools/chat-slack`, `tools/chat-discord`); Matrix and Zulip answers are not collected until an adapter lands. - **`experimental` — no adopter pilot has run.** All twelve skills exist but no maintainer has run the full contributor-to-committer path