mcp-agent-server
An MCP server that provides agent-powered tools, each using an LLM agent loop to iteratively call FlowMCP schema tools to solve complex problems. It can be mounted as Express middleware and supports A2A protocol for agent-to-agent communication.
README
mcp-agent-server
Version: 2.0.0
MCP Server with agent-powered tools, mountable as Express middleware. Each tool starts an LLM Agent Loop that iteratively calls FlowMCP schema tools to solve problems.
Architecture
flowchart LR
MC[MCP Client] -->|MCP Protocol| B[AgentToolsServer]
A2A[A2A Client] -->|message/send| AD[A2A Adapter]
AD -->|tools/call| B
B --> C[ToolRegistry]
C --> D[AgentLoop]
D -->|OpenRouter| E[LLM]
D -->|callTool| F[ToolClient]
D -->|discover| G[A2A Discovery]
F --> H[FlowMCP Schemas]
H --> I[External APIs]
Quickstart
git clone https://github.com/FlowMCP/mcp-agent-server.git
cd mcp-agent-server
npm i
import express from 'express'
import { AgentToolsServer } from 'mcp-agent-server'
const app = express()
app.use( express.json() )
const { mcp } = await AgentToolsServer.create( {
name: 'My Agent Server',
version: '1.0.0',
routePath: '/mcp',
llm: {
baseURL: 'https://openrouter.ai/api',
apiKey: process.env.OPENROUTER_API_KEY
},
tools: [
{
name: 'defi-research',
description: 'Research DeFi protocols',
inputSchema: {
type: 'object',
properties: {
query: { type: 'string' }
},
required: [ 'query' ]
},
agent: {
systemPrompt: 'You are a DeFi research agent.',
model: 'anthropic/claude-sonnet-4-6',
maxRounds: 10,
maxTokens: 4096
},
toolSources: [
{
type: 'flowmcp',
schemas: [ defilamaSchema, coingeckoSchema ],
serverParams: { DEFILAMA_KEY: process.env.DEFILAMA_KEY }
}
],
execution: {
taskSupport: 'optional'
}
}
]
} )
app.use( mcp.middleware() )
app.listen( 4100 )
Features
- MCP Server with StreamableHTTP transport (session-based)
- LLM Agent Loop with iterative tool calling via Anthropic SDK
- FlowMCP schemas as tool sources (in-process, no external server needed)
- A2A Adapter — optional Agent-to-Agent protocol support (
@a2a-js/sdk) - A2A Discovery — built-in tool to discover other A2A agents
- Agent Card — auto-generated from manifest at
/.well-known/agent.json - Configurable answer schema per tool
- MCP Tasks API for async tool execution
- Composable with
x402-mcp-middlewarefor payment gating - Multiple tool sources per tool via CompositeToolClient
Table of Contents
Methods
AgentToolsServer.create()
Creates a new MCP server instance from configuration.
Method
AgentToolsServer.create( { name, version, routePath, llm, tools, tasks } )
| Key | Type | Description | Required |
|---|---|---|---|
| name | string | Server name for MCP handshake | Yes |
| version | string | Server version | Yes |
| routePath | string | Express route path. Default '/mcp' |
No |
| llm | object | LLM config { baseURL, apiKey } |
Yes |
| tools | array | Array of tool configurations | Yes |
| tasks | object | Task store config { store }. Default InMemoryTaskStore |
No |
Returns
// AgentToolsServer instance
const { mcp } = await AgentToolsServer.create( { /* config */ } )
AgentToolsServer.fromManifest()
Creates a server from a FlowMCP v3.0.0 agent manifest.
Method
AgentToolsServer.fromManifest( { manifest, llm, schemas, serverParams, routePath } )
| Key | Type | Description | Required |
|---|---|---|---|
| manifest | object | Agent manifest (export const agent from agent.mjs) |
Yes |
| llm | object | LLM config { baseURL, apiKey } |
Yes |
| schemas | array | FlowMCP schema objects for the agent's tools | No |
| serverParams | object | API keys for schemas | No |
| routePath | string | Express route path. Default '/mcp' |
No |
Example
import { agent } from './agent.mjs'
const { mcp } = await AgentToolsServer.fromManifest( {
manifest: agent,
llm: {
baseURL: 'https://openrouter.ai/api',
apiKey: process.env.OPENROUTER_API_KEY
},
schemas: [ etherscanSchema, defilamaSchema ],
serverParams: { ETHERSCAN_API_KEY: process.env.ETHERSCAN_API_KEY }
} )
.middleware()
Returns an Express middleware function that handles MCP protocol requests (POST/GET/DELETE) on the configured route path.
Method
mcp.middleware()
Returns
// Express middleware function (req, res, next) => Promise<void>
app.use( mcp.middleware() )
.listToolDefinitions()
Returns all registered tools in MCP ListTools format.
Method
mcp.listToolDefinitions()
Returns
const { tools } = mcp.listToolDefinitions()
// tools: [ { name, description, inputSchema, execution? } ]
| Key | Type | Description |
|---|---|---|
| tools | array | Array of tool definitions in MCP format |
Tool Configuration
Each tool in the tools array has the following structure:
| Key | Type | Description | Required |
|---|---|---|---|
| name | string | Tool name (used in MCP protocol) | Yes |
| description | string | Tool description | Yes |
| inputSchema | object | JSON Schema for tool input | Yes |
| agent | object | Agent configuration (see below) | Yes |
| toolSources | array | Array of tool source configs (see below) | Yes |
| execution | object | { taskSupport: 'optional' | 'required' } |
No |
Agent Configuration
| Key | Type | Description | Required |
|---|---|---|---|
| systemPrompt | string | System prompt for the LLM | Yes |
| model | string | LLM model ID (e.g. 'anthropic/claude-sonnet-4-6') |
Yes |
| maxRounds | number | Maximum agent iterations. Default 10 |
No |
| maxTokens | number | Max completion tokens. Default 4096 |
No |
| answerSchema | object | Custom JSON Schema for submit_answer tool |
No |
Tool Sources
Each entry in toolSources defines where the agent gets its tools from:
| Key | Type | Description | Required |
|---|---|---|---|
| type | string | Source type. Currently 'flowmcp' |
Yes |
| schemas | array | FlowMCP schema objects | Yes |
| serverParams | object | Environment variables / API keys for schemas | No |
A2A Adapter
Optional Agent-to-Agent protocol support. Import separately:
import { AgentToolsServer } from 'mcp-agent-server'
import { A2AAdapter } from 'mcp-agent-server/a2a'
const { mcp } = await AgentToolsServer.fromManifest( { manifest, llm: { ... } } )
app.use( mcp.middleware() )
// A2A (optional)
const a2a = A2AAdapter.from( { mcp, manifest, serverUrl: 'https://my-agent.com' } )
app.use( '/.well-known/agent.json', a2a.agentCardMiddleware() )
app.use( '/a2a/v1', a2a.handler() )
This exposes three endpoints:
| Endpoint | Protocol | Purpose |
|---|---|---|
POST /mcp |
MCP | Tool calls from MCP clients (Claude Desktop, Cursor) |
GET /.well-known/agent.json |
A2A | Agent discovery (Agent Card) |
POST /a2a/v1 |
A2A | Agent-to-agent communication (message/send) |
The A2A adapter translates message/send into MCP tools/call — no separate agent loop.
A2A Discovery
The agent loop includes an optional discover_agent tool that fetches Agent Cards from other A2A agents:
const { mcp } = await AgentToolsServer.fromManifest( {
manifest,
llm: { ... },
discovery: true // Enables discover_agent tool
} )
Composition with x402
No code coupling. Pure Express middleware ordering:
import express from 'express'
import { X402Middleware } from 'x402-mcp-middleware/v2'
import { AgentToolsServer } from 'mcp-agent-server'
const app = express()
app.use( express.json() )
// 1. Payment gate (optional)
const x402 = await X402Middleware.create( { /* config */ } )
app.use( x402.mcp() )
// 2. Agent MCP Server
const { mcp } = await AgentToolsServer.create( { /* config */ } )
app.use( mcp.middleware() )
app.listen( 4100 )
Documentation
Full FlowMCP documentation at flowmcp.github.io. See the Agent Server page for integration guides.
License
MIT
Contributing
PRs are welcome. Please open an issue first to discuss proposed changes.
Recommended Servers
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.
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.
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.
VeyraX MCP
Single MCP tool to connect all your favorite tools: Gmail, Calendar and 40 more.
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.
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.
E2B
Using MCP to run code via e2b.
Neon Database
MCP server for interacting with Neon Management API and databases
Qdrant Server
This repository is an example of how to create a MCP server for Qdrant, a vector search engine.
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.