How to Use MCP (Model Context Protocol)
Connect AI apps to your files, GitHub, and databases with MCP: two copy-ready server configs (Filesystem + GitHub), verify-it-worked checks, and real error fixes.
Note
Before you start
- Node.js 18+ (the Filesystem and many other reference servers run through npx)
- An MCP-capable client: Claude Desktop, Claude Code, VS Code (Copilot), Cursor, or ChatGPT
- A folder or two you are willing to let an AI tool read and write (start small)
- For the GitHub server: a GitHub account, optionally Docker
Jump to section
- 1
Understand the two roles
Every MCP setup has a client (your AI tool) and a server (a small program exposing tools). You only configure the client - the server brings the tools the model can call.
- 2
Pick your client and scope
Claude Desktop edits claude_desktop_config.json; Claude Code uses `claude mcp add`; VS Code uses .vscode/mcp.json. Scope decides where the config lives and who shares it.
- 3
Connect the Filesystem server
Copy the exact mcpServers JSON below into your client config, replacing the paths with folders you trust. This is the 'hello world' of MCP.
- 4
Verify the Filesystem server
Restart the client, open the MCP/connectors panel, and confirm the server shows connected with its tools. Then confirm the log grows.
- 5
Connect the official GitHub server
Two supported routes: remote HTTP at api.githubcopilot.com/mcp/ (easiest, OAuth or PAT) or the local Docker server with OAuth on first use.
- 6
Verify GitHub and go safe
Run `claude mcp list` and look for a checked status, or test tools with `github-mcp-server tool-search`. Keep PATs in environment variables, not JSON.
MCP (Model Context Protocol) lets an AI tool call your files, GitHub, and databases through one standard interface - and in this guide you’ll connect two real servers, verify they work, and fix the errors that actually happen. If you set up Claude Code or built your first agent, MCP is the socket those tools plug into - no more copy-pasting data into chat.
What MCP is, in one breath
From the official docs: MCP is “an open-source standard for connecting AI applications to external systems.” The docs’ own analogy is the cleanest: “Think of MCP like a USB-C port for AI applications.” One standard connector, and any compatible device plugs in.
Every setup has two roles:
- MCP server - a small program that exposes capabilities (tools, resources, prompts). Examples: a filesystem server, GitHub’s server, a memory server.
- MCP client - your AI application (Claude Desktop, Claude Code, ChatGPT, VS Code/Copilot, Cursor, Codex, n8n). It discovers the server’s tools and calls them on your behalf, with your approval.
Clients supported (officially)
The official MCP docs list Claude, ChatGPT, VS Code (Copilot), Cursor and more as MCP-capable clients in 2026 - build a server once and it works across all of them. That cross-client support is the entire reason companies like GitHub ship an official MCP server.
Before you start
- Node.js 18+ - the Filesystem and most reference servers run via
npx. Check withnode --version. - An MCP-capable client. This guide uses Claude Desktop (config-file client) and Claude Code (command-line client) because they cover both configuration styles. The concepts carry to every other client.
- A client-version warning: MCP config schemas change between product versions. Every JSON block below was verified against the current official docs (MCP spec 2026-07-28) on 13 August 2026. If a screen doesn’t match, check your client’s version first.
Step 1: Connect the official Filesystem server
The Filesystem server is the protocol’s “hello world”: read, create, move, and search files - every action awaits your approval. Start it via the official package @modelcontextprotocol/server-filesystem.
Where you configure it depends on your client:
Claude Desktop - from the Claude menu, open Settings → Developer → Edit Config. Replace the contents of claude_desktop_config.json with this (macOS shown; on Windows the file is %APPDATA%\Claude\claude_desktop_config.json and paths use backslashes):
{
"mcpServers": {
"filesystem": {
"command": "npx",
"args": [
"-y",
"@modelcontextprotocol/server-filesystem",
"/Users/YOUR_USERNAME/Desktop",
"/Users/YOUR_USERNAME/Downloads"
]
}
}
}
The args array’s trailing entries are the ONLY directories the server can touch. The official docs are blunt: “Only grant access to directories you’re comfortable with Claude reading and modifying.”
Claude Code - the same server, added as a local stdio (subprocess) server. Note the -- that separates Claude’s flags from the server’s command:
claude mcp add --transport stdio filesystem -- \
npx -y @modelcontextprotocol/server-filesystem \
/Users/YOUR_USERNAME/Desktop /Users/YOUR_USERNAME/Downloads
Other clients - VS Code uses .vscode/mcp.json with the same mcpServers block. The shape is shared; only the file location differs.
Step 2: Verify it worked
- Restart the client completely - it only loads MCP config at startup.
- Claude Desktop: click the paperclip/indicator in the input box, open Connectors → Manage connectors, and confirm filesystem is listed with its tools. Claude Code: run
/mcpand look for a checked (✔) status. - Prove it, don’t trust it: ask Claude “list the files on my Desktop” or “create a file called test.md on my Desktop” - and notice it asks permission before acting. If you approve, the file appears.
- Tools you see will be namespaced with the server prefix, e.g.
mcp__filesystem__...(the exact tool list is visible in the connectors panel).
Every server action is logged. On macOS the logs live in ~/Library/Logs/Claude (mcp.log for connections, mcp-server-filesystem.log for the server’s own output); on Windows, %APPDATA%\Claude\logs. Follow them live:
tail -n 20 -f ~/Library/Logs/Claude/mcp*.log # macOS / Linux
The server has your user permissions
The Filesystem server runs under your account, so it can do anything you can do - that is why the official docs insist you scope it to specific directories. Never grant / or your home root. Start with Desktop/Downloads; expand later only if you must.
Step 3: Connect the official GitHub MCP server
GitHub ships its own MCP server (github/github-mcp-server). Two supported routes:
Which route?
Use the remote HTTP server if your client supports remote servers (VS Code 1.101+, Claude Desktop, Cursor) - it’s a URL, nothing to run. Use the local Docker server if you want a subprocess on your machine or you’re on a client that only supports stdio.
Route A - remote HTTP server (no install): GitHub hosts it at https://api.githubcopilot.com/mcp/. In Claude Code, add it with a personal access token as a header:
claude mcp add --transport http github https://api.githubcopilot.com/mcp/ \
--header "Authorization: Bearer YOUR_GITHUB_PAT"
Create the token at github.com/settings/personal-access-tokens with fine-grained access to the repositories you want - the official README lists minimum scopes as repo, read:packages, read:org for the local server’s needs.
Route B - local Docker server (OAuth on first use): the official image is ghcr.io/github/github-mcp-server. It runs the browser OAuth login itself on first use, keeping the token in memory; the container needs a fixed callback port published to loopback. The official config (host JSON):
{
"mcpServers": {
"github": {
"command": "docker",
"args": [
"run", "-i", "--rm",
"-p", "127.0.0.1:8085:8085",
"-e", "GITHUB_OAUTH_CALLBACK_PORT",
"ghcr.io/github/github-mcp-server"
],
"env": {
"GITHUB_OAUTH_CALLBACK_PORT": "8085"
}
}
}
}
Prefer a token over OAuth? Set GITHUB_PERSONAL_ACCESS_TOKEN - the README states it takes precedence over OAuth.
Step 4: Verify GitHub connected
In Claude Code: run claude mcp list. Official statuses are ✔ Connected, ! Needs authentication, or ✘ Failed to connect - a failure means the client couldn’t reach or authenticate the server, not that the list command broke. claude mcp get github shows details. Then ask it to do something real: “list the open issues in MY_ORG/MY_REPO”.
In Docker: the binary ships a search/debug command. List the tools available to the model:
docker run -it --rm ghcr.io/github/github-mcp-server tool-search "issue" --max-results 5
Default tool groups (toolsets) are context, repos, issues, pull_requests, users - you can shrink the surface with GITHUB_TOOLSETS (e.g. read-only triage) or GITHUB_TOOLS for individual tools.
Troubleshooting
Server shows up but no hammer/connector icon (it never connected)
- Restart the client completely - MCP config loads at startup only.
- Check the JSON syntax - a single missing comma makes the whole block invalid.
- The docs list a classic cause: paths must be absolute, not relative.
/Users/you/Desktopworks;~/DesktoporDesktopoften fails. - Read the server log (
mcp-server-filesystem.log) for the real error. - Run the server directly in a terminal - if it errors there, your client isn’t the problem:
npx -y @modelcontextprotocol/server-filesystem /Users/YOUR_USERNAME/Desktop /Users/YOUR_USERNAME/DownloadsClaude Code: server exists but never connects (no type field)
A remote server config copied from docs often has a url but no type. Claude Code reads a type-less entry as a stdio server, skips it, and reports (on current versions): MCP server "NAME" has a "url" but no "type"; add "type": "http" (or "sse" / "ws") to this entry. Fix: add "type": "http" to the server object. When working in .mcp.json, type accepts streamable-http as an alias for http.
Claude Code: “MCP server NAME already exists in local config”
You re-added a server that’s already configured. This is expected - claude mcp add fails cleanly on duplicates. Check what’s there with claude mcp list, or overwrite deliberately by removing first (claude mcp remove NAME) then re-adding.
Authentication fails (401/403 or “needs authentication”)
- Your client marks a remote server
! Needs authenticationwhen the server returns 401/403. For OAuth servers, run/mcp(orclaude mcp login NAME) and complete the browser flow - tokens are stored securely and refresh automatically. - Trap:
claude mcp addsaves the config without validating credentials, so a placeholder token is accepted at add-time and only fails later. A bad token typically showsfailedwith the HTTP status (e.g. 401) in the failure detail. - For GitHub route A, make sure the fine-grained PAT actually has access to the repo you’re querying.
Filesystem server: ENOENT / ${APPDATA} errors on Windows
The docs’ fix for the ${APPDATA}-in-path failure: add the expanded value to the server’s env block (and confirm npm is installed globally):
{
"filesystem": {
"command": "npx",
"args": ["-y", "@modelcontextprotocol/server-filesystem", "C:\\Users\\YOUR_USERNAME\\Desktop"],
"env": {
"APPDATA": "C:\\Users\\YOUR_USERNAME\\AppData\\Roaming"
}
}
}The npx line can also fail if npm isn’t global - npm install -g npm fixes that (per the official docs).
GitHub Docker server: callback port conflict
The OAuth flow pins the callback to 127.0.0.1:8085. If 8085 is taken, the login callback fails. Change the port consistently in both the -p 127.0.0.1:PORT:PORT mapping and the GITHUB_OAUTH_CALLBACK_PORT env value. If the image pull fails with an auth error, try docker logout ghcr.io (the README calls out stale tokens).
You did it
- You can explain MCP and both roles in one sentence each
- Your client shows the Filesystem server connected, with tools listed
- Claude created/read a file in an allowed directory - after your approval
- You followed a real
mcp-server-filesystem.logline during a tool call - Your GitHub server authenticates (OAuth or PAT) and exposes issues/PRs tools
- No token sits hardcoded in a config file that could be committed
Official sources
- MCP overview (with the USB-C analogy): modelcontextprotocol.io/introduction
- Connect local servers + Filesystem config + troubleshooting: connect-local-servers (2026-07-28)
- Reference servers list (Filesystem, Memory, Git): MCP example servers
- GitHub MCP server (routes, configs, toolsets, scopes): github/github-mcp-server README
- Claude Code MCP reference (
claude mcp add, scopes, statuses, errors): docs.claude.com/en/docs/claude-code/mcp
All fetched 13 August 2026; MCP docs pinned at spec version 2026-07-28.
Next: MCP servers are how your own agent gets real tools, and n8n ships a built-in MCP server so an AI tool can build your AI workflows for you. For the benchmark context on why agent tool-calling quality matters so much in 2026, our Terminal-Bench 2.1 explainer is the reference.
Questions, answered first
What is MCP in plain language?
MCP (Model Context Protocol) is an open standard for connecting AI applications to external systems. Think of it as a USB-C port for AI: one standard interface, and any compatible server plugs in - files, GitHub, databases, search - instead of each tool building its own integration.
Is MCP the same as an API?
No. An API is one provider's interface, built for one consumer. MCP is a shared protocol that any compliant server and any compliant client can use, so a server written once works in Claude, ChatGPT, VS Code, and dozens of other hosts. That standardization is the point.
Do I need to build a server to use MCP?
No. You connect an existing server. Reference servers like Filesystem and Memory run from one npx command; companies like GitHub and Sentry host their own servers. Building one is a second project - our custom-agent guide covers the agent side, and the official MCP build-server tutorial covers the server side.
Is MCP safe to use?
MCP's design is that every action needs your approval. The real risks are two: a server with file access runs with your user permissions (so grant it only folders you trust), and servers that fetch external content can open prompt-injection channels - treat anything a server returns as untrusted input, exactly as you already do with web pages.
Why did n8n and GitHub build their own MCP servers?
Because one server plugs into every client. GitHub's server works in VS Code, Claude Desktop, Cursor, and Codex with the same config. n8n's built-in MCP server lets any AI tool draft and run workflows on your instance. Both are on the official modelcontextprotocol examples/registry - and any agent you build with our [LangGraph guide](/guides/build-your-first-ai-agent/) can call the same servers.
You did it
- You can name what MCP is and the client/server roles in one sentence each
- Your client's MCP panel lists at least one server as connected
- Claude successfully wrote a file to one of your allowed directories - after your approval
- You watched the mcp.log line for the server during a tool call
- Your GitHub server authenticates (OAuth or PAT) and lists issues/PRs tools
- No API token is hardcoded in a config file that gets committed to git