Skip to main content
Guide6 min read

How to share MCP server configs across a team (Git-based workflow)

Stop pasting configs in Slack. A repeatable pattern for team-wide MCP setup: Git-versioned server definitions, one-command bootstrap for new hires, secret isolation.

As soon as your team hits three MCP-curious developers, "paste this config into Claude Desktop" in Slack breaks down. Here is the workflow we use — Git-versioned, secret-safe, one command for new hires.

The goal

A new hire runs one command on day one and ends up with the team’s full MCP loadout: GitHub, Postgres (dev DB), Slack, internal tools. Per-user secrets never touch the repo.

Repo layout

your-repo/
  mcp/
    servers.d/
      00-github.json
      10-postgres-dev.json
      20-slack.json
      30-internal-tools.json
    secrets.example.env
    install.sh
  .gitignore   # contains secrets.env

One file per server

Each JSON is a fragment — just mcpServers with one key. Example servers.d/00-github.json:

{
  "mcpServers": {
    "github": {
      "command": "docker",
      "args": [
        "run", "--rm", "-i",
        "-e", "GITHUB_PERSONAL_ACCESS_TOKEN",
        "ghcr.io/github/github-mcp-server:v1.4.2"
      ]
    }
  }
}

Notice — no token in the file. Secrets come from the local secrets.env.

secrets.example.env

Committed, has no actual secrets:

# Each dev copies this to secrets.env and fills their own values
GITHUB_PERSONAL_ACCESS_TOKEN=
POSTGRES_DEV_URL=
SLACK_BOT_TOKEN=

Add secrets.env to .gitignore.

install.sh — the bootstrap

#!/bin/sh
set -e

# 1. Detect Claude config path
case "$(uname)" in
  Darwin)   CFG="$HOME/Library/Application Support/Claude/claude_desktop_config.json" ;;
  Linux)    CFG="$HOME/.config/Claude/claude_desktop_config.json" ;;
  *)        CFG="$APPDATA/Claude/claude_desktop_config.json" ;;
esac

# 2. Load secrets into env
set -a; . ./mcp/secrets.env; set +a

# 3. Merge all servers.d/*.json into one config
mkdir -p "$(dirname "$CFG")"
jq -s '{ mcpServers: ([.[].mcpServers] | add) }' \
   mcp/servers.d/*.json > "$CFG"

# 4. Substitute env vars (optional — only for templated values)
envsubst < "$CFG" > "$CFG.tmp" && mv "$CFG.tmp" "$CFG"

echo "✔ MCP config written to $CFG"
echo "  Restart Claude Desktop to pick up changes."

A new hire runs:

cp mcp/secrets.example.env mcp/secrets.env
# fill in tokens
./mcp/install.sh

CI check: don’t commit broken JSON

Add a workflow that runs jq '.' servers.d/*.json — fails the PR on invalid JSON. Saves a weekly "why does the config break for half the team" meeting.

Secrets via 1Password / Vault

For mature teams, don’t even let devs copy tokens into files. Use 1Password CLI or Vault:

# in install.sh
export GITHUB_PERSONAL_ACCESS_TOKEN=$(op read "op://Eng/GitHub-MCP/token")
export POSTGRES_DEV_URL=$(op read "op://Eng/Postgres-Dev/url")

Tokens never hit disk. Rotation is just a 1Password update.

Per-env configs

If you have dev / staging / prod databases, split into subfolders:

mcp/
  servers.d/
    common/       # GitHub, Slack — same everywhere
    dev/          # dev Postgres, dev Sentry
    staging/      # staging Postgres

Accept ENV=dev|staging env var in install.sh, merge common/ + $ENV/.

Read me before you ship to devs

  • Never share the same MCP token across devs — per-user PATs only. Rotating one user’s token should not break others.
  • Scope tokens hard: GitHub PATs with minimum-needed permissions; Postgres role read-only.
  • Document what each server does in a top-level mcp/README.md. Especially call out any server that can write.
Loadout

Build your AI agent loadout

The directory of MCP servers and AI agents that actually work. Pick the right loadout for Slack, Postgres, GitHub, Figma and 20+ integrations — with install commands ready to paste into Claude Desktop, Cursor or your own stack.

© 2026 Loadout. Built on Angular 21 SSR.