Slack MCP Server

Slack MCP Server

Enables AI assistants to interact with Slack workspaces through secure OAuth 2.0 authentication. Supports posting messages, reading channel history, and listing channels across multiple workspaces with production-ready security features.

Category
Visit Server

README

Slack MCP Server

A production-ready Model Context Protocol (MCP) server for Slack integration. This server enables AI assistants to interact with Slack workspaces through a secure, multi-tenant OAuth flow.

Features

  • šŸ” Secure OAuth 2.0 Flow - Full Slack OAuth v2 implementation with state validation
  • šŸ¢ Multi-Tenant Support - Handle multiple Slack workspaces simultaneously
  • šŸ”„ Token Rotation - Automatic token refresh for long-lived installations
  • šŸ›”ļø Production Security - CORS, API key protection, Helmet.js, request timeouts
  • šŸ“Š Structured Logging - Pino logger with configurable log levels
  • 🐳 Docker Ready - Multi-stage Dockerfile with non-root user
  • ⚔ MCP Tools - Post messages, read channel history, list channels

Architecture

This server uses the Streamable HTTP transport for MCP, making it suitable for web-based AI assistants. It manages:

  • OAuth Flow: /slack/install and /slack/oauth/callback endpoints
  • MCP Endpoint: /mcp for all MCP protocol communication
  • Session Management: Automatic session pruning with configurable TTL
  • Installation Storage: Pluggable storage interface (in-memory by default)

Prerequisites

  1. Slack App - Create a Slack app at api.slack.com/apps
  2. Node.js - Version 18+ required
  3. pnpm - Package manager (or npm/yarn)

Quick Start

1. Install Dependencies

pnpm install

2. Configure Environment

Copy the example environment file and fill in your values:

cp .env.example .env

Required variables:

  • SLACK_CLIENT_ID - From your Slack app's OAuth settings
  • SLACK_CLIENT_SECRET - From your Slack app's OAuth settings
  • SLACK_REDIRECT_URI - Your callback URL (e.g., https://yourdomain.com/slack/oauth/callback)
  • SLACK_SCOPES - Comma-separated bot scopes (e.g., chat:write,channels:history,channels:read)
  • AFFINITYBOTS_MCP_API_KEY - Secret key to protect your MCP endpoint

3. Run Development Server

pnpm dev

The server will start on http://localhost:8080 by default.

4. Install Slack App

  1. Navigate to http://localhost:8080/slack/install
  2. Authorize the app for your workspace
  3. You'll be redirected back with a success message

5. Use MCP Tools

Connect your MCP client to http://localhost:8080/mcp with:

  • Authorization header: Bearer YOUR_AFFINITYBOTS_MCP_API_KEY
  • Origin header: Must match ALLOWED_ORIGINS if configured

Available MCP Tools

slack_post_message

Post a message to a Slack channel.

Parameters:

  • team_id (string) - Slack workspace/team ID (T...)
  • channel_id (string) - Channel/DM ID (C... or D...)
  • text (string) - Message text (1-4000 characters)
  • thread_ts (string, optional) - Thread timestamp to reply to

slack_get_channel_history

Read messages from a Slack channel.

Parameters:

  • team_id (string) - Slack workspace/team ID
  • channel_id (string) - Channel/DM ID
  • limit (number, optional) - Number of messages (1-200, default: 50)

slack_list_channels

List all channels in the workspace.

Parameters:

  • team_id (string) - Slack workspace/team ID
  • types (string, optional) - Channel types: public_channel,private_channel,mpim,im (default: public_channel)
  • limit (number, optional) - Number of channels (1-1000, default: 200)

Configuration

Environment Variables

Variable Required Default Description
PORT No 8080 Server port
HOST No 0.0.0.0 Server host
PUBLIC_BASE_URL No http://localhost:8080 Public URL for OAuth redirects
SLACK_CLIENT_ID Yes - Slack app client ID
SLACK_CLIENT_SECRET Yes - Slack app client secret
SLACK_REDIRECT_URI Yes - OAuth callback URL
SLACK_SCOPES Yes - Comma-separated bot scopes
AFFINITYBOTS_MCP_API_KEY Recommended - API key for MCP endpoint
ALLOWED_ORIGINS No - Comma-separated allowed origins for CORS
SESSION_TTL_MS No 900000 MCP session timeout (15 min)
LOG_LEVEL No info Log level: trace, debug, info, warn, error, fatal

Required Slack Scopes

At minimum, your Slack app needs these bot token scopes:

  • chat:write - Post messages
  • channels:history - Read public channel messages
  • channels:read - List public channels

Additional recommended scopes:

  • groups:history - Read private channel messages
  • groups:read - List private channels
  • im:history - Read direct messages
  • im:read - List direct messages
  • mpim:history - Read group DM messages
  • mpim:read - List group DMs

Production Deployment

Using Docker

Build the image:

docker build -t slack-mcp-server .

Run the container:

docker run -d \
  -p 8080:8080 \
  -e SLACK_CLIENT_ID=your_client_id \
  -e SLACK_CLIENT_SECRET=your_client_secret \
  -e SLACK_REDIRECT_URI=https://yourdomain.com/slack/oauth/callback \
  -e SLACK_SCOPES=chat:write,channels:history,channels:read \
  -e AFFINITYBOTS_MCP_API_KEY=your_secret_key \
  -e ALLOWED_ORIGINS=https://yourdomain.com \
  slack-mcp-server

Production Checklist

  • [ ] Set AFFINITYBOTS_MCP_API_KEY to a strong random value
  • [ ] Configure ALLOWED_ORIGINS with your frontend domains
  • [ ] Use HTTPS for all endpoints (required by Slack)
  • [ ] Set PUBLIC_BASE_URL to your public HTTPS URL
  • [ ] Replace InMemoryInstallStore with persistent storage (Redis/PostgreSQL)
  • [ ] Set up monitoring and alerting
  • [ ] Configure log aggregation
  • [ ] Set appropriate SESSION_TTL_MS for your use case
  • [ ] Enable Slack token rotation in your app settings (recommended)
  • [ ] Set up rate limiting at the reverse proxy level
  • [ ] Configure health check monitoring on /health

Storage

The default InMemoryInstallStore is suitable for development but not for production. For production, implement the InstallStore interface with a persistent backend:

export interface InstallStore {
  upsert(install: SlackInstallation): Promise<void>;
  getByTeamId(teamId: string): Promise<SlackInstallation | null>;
}

Recommended storage options:

  • PostgreSQL - Best for relational data and complex queries
  • Redis - Fast, simple key-value storage
  • MongoDB - Document-based storage
  • DynamoDB - Serverless AWS option

Security Features

Implemented

  • āœ… CSRF protection via OAuth state parameter
  • āœ… API key authentication for MCP endpoint
  • āœ… CORS with origin allowlist
  • āœ… Helmet.js security headers
  • āœ… Request timeouts (30s)
  • āœ… Session expiration and pruning
  • āœ… Automatic token refresh
  • āœ… Secure error messages (no info leakage)
  • āœ… Non-root Docker user

Recommended Additional Security

  • Add rate limiting (e.g., express-rate-limit)
  • Use a reverse proxy (nginx, Caddy) with TLS
  • Implement request size limits
  • Add request ID tracking
  • Set up WAF rules
  • Enable Slack signing secret verification for webhooks (if added)

Monitoring

Health Check

curl http://localhost:8080/health

Returns ok if the server is running.

Logs

The server uses structured JSON logging via Pino. Key log events:

  • OAuth flow initiation and completion
  • MCP session creation and expiration
  • Token refresh operations
  • API errors and warnings
  • Security events (unauthorized access, invalid origins)

Set LOG_LEVEL=debug for detailed debugging.

Troubleshooting

OAuth Errors

"Invalid or expired state"

  • The OAuth state token expired (10 min TTL)
  • Try the installation flow again

"Slack OAuth failed: invalid_code"

  • The authorization code was already used or expired
  • Restart the installation flow

"Origin not allowed"

  • Your frontend origin is not in ALLOWED_ORIGINS
  • Add your origin to the environment variable

MCP Errors

"Unauthorized"

  • Missing or invalid Authorization header
  • Ensure you're sending Bearer YOUR_API_KEY

"Unknown or expired session"

  • MCP session expired (default 15 min)
  • Reinitialize the MCP connection

"No Slack installation found"

  • The workspace hasn't installed the app
  • Complete the OAuth flow first

Token Errors

"Token refresh failed"

  • The refresh token is invalid or revoked
  • User needs to reinstall the app
  • Check if token rotation is enabled in Slack app settings

Development

Project Structure

slack-mcp-server/
ā”œā”€ā”€ src/
│   ā”œā”€ā”€ index.ts          # Main server and routing
│   ā”œā”€ā”€ mcp.ts            # MCP tool definitions
│   ā”œā”€ā”€ slackOauth.ts     # OAuth flow handlers
│   ā”œā”€ā”€ slackClient.ts    # Slack API client with token refresh
│   ā”œā”€ā”€ installStore.ts   # Installation storage interface
│   └── security.ts       # Security utilities
ā”œā”€ā”€ Dockerfile
ā”œā”€ā”€ package.json
ā”œā”€ā”€ tsconfig.json
└── README.md

Adding New Tools

Register new tools in src/mcp.ts:

server.tool(
  "tool_name",
  "Tool description",
  {
    team_id: z.string(),
    // ... other parameters
  },
  async ({ team_id, ...params }) => {
    const slack = await getSlackClientForTeam(store, team_id);
    // ... implement tool logic
    return { content: [{ type: "text", text: "result" }] };
  }
);

Testing

# Run development server with debug logging
LOG_LEVEL=debug pnpm dev

# Build for production
pnpm build

# Run production build
pnpm start

License

MIT

Support

For issues and questions:

  1. Check the IMPLEMENTATION.md guide
  2. Review Slack API documentation at api.slack.com
  3. Check MCP documentation at modelcontextprotocol.io

Contributing

Contributions welcome! Please:

  1. Follow the existing code style
  2. Add tests for new features
  3. Update documentation
  4. Ensure all lints pass

Recommended Servers

playwright-mcp

playwright-mcp

A Model Context Protocol server that enables LLMs to interact with web pages through structured accessibility snapshots without requiring vision models or screenshots.

Official
Featured
TypeScript
Magic Component Platform (MCP)

Magic Component Platform (MCP)

An AI-powered tool that generates modern UI components from natural language descriptions, integrating with popular IDEs to streamline UI development workflow.

Official
Featured
Local
TypeScript
Audiense Insights MCP Server

Audiense Insights MCP Server

Enables interaction with Audiense Insights accounts via the Model Context Protocol, facilitating the extraction and analysis of marketing insights and audience data including demographics, behavior, and influencer engagement.

Official
Featured
Local
TypeScript
VeyraX MCP

VeyraX MCP

Single MCP tool to connect all your favorite tools: Gmail, Calendar and 40 more.

Official
Featured
Local
graphlit-mcp-server

graphlit-mcp-server

The Model Context Protocol (MCP) Server enables integration between MCP clients and the Graphlit service. Ingest anything from Slack to Gmail to podcast feeds, in addition to web crawling, into a Graphlit project - and then retrieve relevant contents from the MCP client.

Official
Featured
TypeScript
Kagi MCP Server

Kagi MCP Server

An MCP server that integrates Kagi search capabilities with Claude AI, enabling Claude to perform real-time web searches when answering questions that require up-to-date information.

Official
Featured
Python
E2B

E2B

Using MCP to run code via e2b.

Official
Featured
Neon Database

Neon Database

MCP server for interacting with Neon Management API and databases

Official
Featured
Exa Search

Exa Search

A Model Context Protocol (MCP) server lets AI assistants like Claude use the Exa AI Search API for web searches. This setup allows AI models to get real-time web information in a safe and controlled way.

Official
Featured
Qdrant Server

Qdrant Server

This repository is an example of how to create a MCP server for Qdrant, a vector search engine.

Official
Featured