Skip to content

How to Set Up and Configure MCP Servers for Claude Code

How to Set Up and Configure MCP Servers for Claude Code

I wanted to extend Claude Code with MCP servers. I found the official docs but got confused by one question: Do I need to install Python packages locally on my dev machine, or is there some sort of hosted gateway I can run on a VM or in the cloud?

Turns out the answer is: it depends on the MCP server. Let me walk you through what I learned.

What Are MCP Servers Anyway?

MCP (Model Context Protocol) servers are plugins that extend Claude Code’s capabilities. They give Claude access to external systems like databases, APIs, file systems, and more.

Think of them like npm packages for your AI assistant. Each server provides specific tools and resources that Claude can use.

┌─────────────┐ ┌─────────────┐ ┌─────────────┐
│ Claude Code │ ──stdio─→│ MCP Server │ ───────→│ External │
│ (Client) │ or │ (Plugin) │ │ System │
│ │ HTTP │ │ │ │
└─────────────┘ └─────────────┘ └─────────────┘

There are two main types:

  1. stdio servers - Run as local child processes on your machine
  2. HTTP servers - Remote servers accessed over the network

This distinction matters a lot for setup.

Local vs Hosted: The Core Confusion

When I first looked at MCP servers, the documentation was scattered. Some repos said “npm install”, others said “pip install”, and a few mentioned HTTP URLs.

Here’s what I figured out:

Local Installation (stdio servers)

Most MCP servers run locally on your development machine. They spawn as child processes that Claude Code communicates with via standard input/output.

Examples: Filesystem MCP, PostgreSQL MCP, Docker MCP

Best for: Personal development, sensitive data, low latency

Hosted Installation (HTTP servers)

Some MCP servers can run remotely on VMs or cloud instances. You connect to them via HTTP.

Examples: Context7 MCP, GitHub MCP (enterprise deployments)

Best for: Team sharing, centralized management, enterprise deployments

Decision Matrix

ScenarioRecommended Approach
Personal developmentLocal stdio
Team collaborationHosted HTTP
Sensitive dataLocal stdio
Enterprise deploymentHosted with policies
Quick testingLocal stdio

For most developers starting out, local stdio servers are the way to go. That’s what I use for daily development.

Prerequisites

Before setting up MCP servers, I made sure I had the basics:

Check prerequisites
# Check Claude Code
claude --version
# Check Node.js (for Node.js-based MCPs)
node --version # Need 18+
# Check Python (for Python-based MCPs)
python --version # Need 3.8+

For Node.js MCPs, npx comes bundled with Node.js. For Python MCPs, I needed pip installed.

Setting Up Node.js MCP Servers

Let me start with the Filesystem MCP - probably the most commonly used one.

The npx Approach

The cool thing about Node.js MCPs is that npx handles everything. No manual installation needed.

I tried adding this to my configuration:

~/.claude.json
{
"mcpServers": {
"filesystem": {
"command": "npx",
"args": ["-y", "@modelcontextprotocol/server-filesystem", "/Users/cowrie/projects"],
"env": {
"LOG_LEVEL": "debug"
}
}
}
}

The -y flag tells npx to automatically download and run the package without prompting. I specify the allowed directory for security - Claude can only access files in that path.

What I Got Wrong at First

I initially forgot to specify the allowed directory and got an error:

Error without directory path
Error: Filesystem server requires at least one allowed directory path

Then I tried using a path that didn’t exist:

Error with non-existent path
Error: Directory /nonexistent/path does not exist

MCP servers validate their configuration at startup. This caught me off guard but makes sense for security.

Setting Up Python MCP Servers

Python MCPs typically require a bit more setup. Let me walk through the PostgreSQL MCP as an example.

Cloning and Installing

First, I cloned the repository:

Clone PostgreSQL MCP
git clone https://github.com/crystaldba/postgres-mcp.git
cd postgres-mcp
pip install -e .

The -e flag installs in development mode, which is useful for debugging.

Configuration

Then I added it to my configuration:

~/.claude.json
{
"mcpServers": {
"postgres": {
"command": "python",
"args": ["-m", "postgres_mcp"],
"env": {
"DATABASE_URL": "postgresql://user:pass@localhost:5432/mydb"
}
}
}
}

The Environment Variable Trap

I hardcoded the database URL at first. Bad idea. When I committed my config to dotfiles, I almost exposed my credentials.

Now I use environment variables:

Using environment variables
{
"mcpServers": {
"postgres": {
"command": "python",
"args": ["-m", "postgres_mcp"],
"env": {
"DATABASE_URL": "${DATABASE_URL}"
}
}
}
}

Then I set the actual value in my shell:

Set environment variable
export DATABASE_URL="postgresql://user:pass@localhost:5432/mydb"

Using the Claude Code CLI

Claude Code has a CLI for managing MCP servers. I found this easier than editing JSON files manually.

Adding a Server

Add MCP server via CLI
# Basic syntax
claude mcp add-json <name> '<json-config>'
# Example: Add a local stdio server
claude mcp add-json my-filesystem '{
"command": "npx",
"args": ["-y", "@modelcontextprotocol/server-filesystem", "/home/user/projects"]
}'
# Example: Add an HTTP server
claude mcp add-json remote-api '{
"url": "https://mcp.example.com/mcp",
"headers": {
"Authorization": "Bearer your-token"
}
}'

Listing Servers

List configured MCP servers
claude mcp list

This shows all configured servers and their status.

Configuration File Locations

I got confused about where to put configuration files. Turns out there are multiple options:

Global Configuration

Location: ~/.claude.json or ~/.claude/mcp.json

This applies to all your projects. I use this for servers I always want available, like the filesystem MCP.

Project-Level Configuration

Location: .mcp.json in project root

This is project-specific and can be committed to git for team sharing. I use this for project-specific database connections.

.mcp.json (project level)
{
"database-tools": {
"command": "python",
"args": ["-m", "project_db_mcp"],
"env": {
"DB_URL": "${PROJECT_DB_URL}"
}
}
}

Configuration Hierarchy

┌─────────────────────────────────────────┐
│ ~/.claude.json (Global) │
│ - Always available servers │
│ - Personal tools │
└─────────────────────────────────────────┘
┌─────────────────────────────────────────┐
│ .mcp.json (Project Level) │
│ - Project-specific servers │
│ - Team shared configuration │
└─────────────────────────────────────────┘
┌─────────────────────────────────────────┐
│ Merged Configuration │
│ - Both global and project servers │
│ - Project can override global │
└─────────────────────────────────────────┘

Here are the MCP servers I actually use day-to-day.

GitHub CLI MCP

For interacting with GitHub repositories, issues, and PRs:

Install GitHub CLI
# macOS
brew install gh
# Ubuntu
sudo apt install gh
# Authenticate
gh auth login
GitHub MCP configuration
{
"mcpServers": {
"github": {
"command": "gh",
"args": ["mcp"]
}
}
}

Context7 MCP

For fetching up-to-date documentation for any library:

Context7 MCP configuration
{
"mcpServers": {
"context7": {
"command": "npx",
"args": ["-y", "@upstash/context7-mcp"]
}
}
}

This is super useful when I need current docs for a library that changed recently.

Docker MCP

For managing Docker containers and images:

Docker MCP configuration
{
"mcpServers": {
"docker": {
"command": "docker",
"args": ["mcp", "serve"]
}
}
}

Requires Docker to be installed and running.

Troubleshooting Common Issues

Server Not Starting

Symptoms: MCP server doesn’t appear in Claude Code, “command not found” errors.

What I check:

Debug server startup
# Verify command exists
which npx
which python
# Test server manually
npx -y @modelcontextprotocol/server-filesystem /tmp
# Check logs
claude mcp list

Most of the time, the issue is a missing dependency or wrong path.

Permission Denied

Symptoms: “Permission denied” errors, cannot access files.

What I check:

Fix permission issues
# Make script executable
chmod +x /path/to/server
# Check file permissions
ls -la /path/to/server

Environment Variables Not Loading

Symptoms: API keys not recognized, configuration values missing.

What I check:

Debug environment variables
# Verify environment variable is set
echo $GITHUB_TOKEN
# Set in shell profile if missing
echo 'export GITHUB_TOKEN="your-token"' >> ~/.bashrc
source ~/.bashrc

Connection Refused (HTTP Servers)

Symptoms: “Connection refused” or timeout errors for HTTP servers.

What I check:

Debug HTTP connection
# Verify server is running
curl http://localhost:8080/health
# Check firewall
sudo ufw status
# Verify URL in configuration

Enterprise Deployment

For teams, there are enterprise features worth knowing about.

Allowlists and Denylists

Control which MCP servers users can configure:

Enterprise allowlist
{
"allowedMcpServers": [
{ "serverName": "github" },
{ "serverName": "sentry" },
{ "serverCommand": ["npx", "-y", "@modelcontextprotocol/server-filesystem"] },
{ "serverUrl": "https://mcp.company.com/*" }
],
"deniedMcpServers": [
{ "serverName": "dangerous-server" },
{ "serverUrl": "https://*.untrusted.com/*" }
]
}

Managed Configuration

For complete control, use a managed configuration file that users cannot modify:

/etc/claude/managed-mcp.json
{
"mcpServers": {
"github": {
"url": "https://api.githubcopilot.com/mcp/"
},
"sentry": {
"url": "https://mcp.sentry.dev/mcp"
}
}
}

Best Practices I Follow

Security:

  • Never hardcode secrets in configuration files
  • Use environment variables: "API_KEY": "${API_KEY}"
  • Restrict file system access to specific directories

Organization:

  • Use descriptive server names
  • Use project-level .mcp.json for team sharing
  • Document each server’s purpose in comments

Maintenance:

  • Keep MCP servers updated
  • Review and rotate API keys regularly
  • Audit server access logs in enterprise settings

Summary

In this post, I walked through how to set up and configure MCP servers for Claude Code. The key points:

  1. Most MCPs run locally via stdio - use npx for Node.js, pip for Python
  2. Configuration uses simple JSON in ~/.claude.json or .mcp.json
  3. Environment variables keep secrets secure - never hardcode credentials
  4. HTTP servers exist for teams - use them for centralized management

Start with the Filesystem MCP to get comfortable, then explore other servers based on your needs. The MCP ecosystem is growing fast, and the setup process becomes second nature after a few tries.

Final Words + More Resources

My intention with this article was to help others share my knowledge and experience. If you want to contact me, you can contact by email: Email me

Here are also the most important links from this article along with some further resources that will help you in this scope:

Oh, and if you found these resources useful, don’t forget to support me by starring the repo on GitHub!

Comments