Files
dotfiles/.agents/skills/add-mcp-server/SKILL.md
T
noconnorandClaude Opus 4.8 485e267565 .agents/: add skills for working on this repo
Five skills covering this repo's own conventions: adding a bootstrap
module, adding a CLI to bin/, bumping a pinned version, adding an MCP
server, and verifying a module change.

Lives in .agents/skills/ because opencode discovers that path natively
alongside .opencode/skills/ and .claude/skills/, making it the most
tool-neutral of the three. Distinct from the repo's skills/ tree, which
ships to every covert-gpt user via sync.sh; these stay in the checkout.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-13 13:10:18 -04:00

2.9 KiB

name, description
name description
add-mcp-server Use when adding or changing an MCP server in mcp-config/opencode.gateway.json (gitea, proxmox, …). Covers the {env:VAR} secret rule, the npx/node dependency, the shared-vs-personal boundary, and how to tell a dead server apart from a model that just can't call tools.

Adding an MCP server

mcp-config/opencode.gateway.json is the shared opencode config, synced to every covert-gpt user by mcp-config/sync.sh. Read mcp-config/README.md before changing it.

Secrets: {env:VAR}, never a literal

"environment": {
  "GITEA_HOST": "https://git.nic-oconnor.com",
  "GITEA_ACCESS_TOKEN": "{env:GITEA_KEY}"   // <- resolved from the user's shell
}

This file is shared and committed. A literal token here leaks it to every user and into git history. The {env:VAR} indirection is what lets one shared config give each person tools that act as them — opencode resolves the var from the invoking user's environment and passes it to the server it spawns.

When you add a server that needs a credential:

  1. Reference it as {env:NEW_VAR} in the config.
  2. Add NEW_VAR to zsh/zshrc.local.example.
  3. Document it in the root README.md variable list and in mcp-config/README.md.

Users keep the value in ~/.zshrc.local (mode 0600), which bootstrap never overwrites. It is never written into any config file.

Shared vs personal

This tree is identical for every user. A server that only makes sense for one person's cluster, kubeconfig, or local paths belongs in that user's own ~/.config/opencode/, which sync never touches. Same rule as skills/.

It needs npx

Servers are spawned as npx -y <pkg>@<version>, so node/install.sh must have run. Pin the version — npx -y otherwise runs whatever the registry serves, and this process receives the user's tokens. See the bump-pinned-version skill.

Debugging: dead server vs. bad model

The failure modes look alike from the chat window, so distinguish them first:

  • Server dead — the tool isn't in the model's tool list at all. Usual cause: npx missing from PATH, a bad package name, or an unset env var. opencode reports this only as absent tools, which reads like a config problem.
  • Server fine, model weak — the tool is called and the server answers, including with errors like user 'x' does not exist. That round trip proves MCP works. A model that invents required arguments (owner, repo) rather than discovering them, or retries the same wrong call verbatim, is a tool-use capability limit, not a config bug. Smaller / non-agentic models (e.g. VL or low-active-param MoE variants) do this; coder-tuned models generally don't.

Check the tool list before touching the config:

opencode debug skill      # skills opencode can see
npx -y <pkg>@<ver>        # does the server even start standalone?

Fix argument-guessing in AGENTS.md (give the model the default owner/host), not in opencode.gateway.json.