0.0.3 • Published 5 months ago
@chainbound/payflow-sdk v0.0.3
Payflow SDK
The Payflow SDK is a Typescript library for building paid MCP servers using various micropayment protocols. It extends the Model Context Protocol SDK to provide a unified interface for building paid MCP servers.
Features
- Easy interface to register paid tools
- Support for x402 payment schema with USDC on Base
- Support for x402 with other assets and networks
- Extensible payment processing (like with Agent Commerce Kit, Stripe, etc.)
Installation
npm install @chainbound/payflow-sdk
# or
pnpm add @chainbound/payflow-sdk
# or
yarn add @chainbound/payflow-sdkQuick Start
1. Basic Setup
import { PayflowMcpServer } from '@chainbound/payflow-sdk';
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
import { z } from 'zod';
// Create a server
const server = new PayflowMcpServer({
name: 'my-paid-server',
version: '1.0.0',
}, {
x402: {
version: 1,
keyId: process.env.CDP_API_KEY_ID,
keySecret: process.env.CDP_API_KEY_SECRET,
}
});
// Connect transport
const transport = new StdioServerTransport();
await server.connect(transport);2. Register a Paid Tool
// Simple paid tool without parameters
server.paidTool(
'hello_world',
'Says hello to the world',
{
price: 0.01, // Price in USDC
recipient: '0x1234...' // Ethereum address to receive payment
},
async () => {
return {
content: [{
type: 'text',
text: 'Hello, World!'
}]
};
}
);3. Paid Tool with Parameters
server.paidTool(
'generate_text',
'Generates custom text based on input',
{
price: 0.05,
recipient: '0x1234...'
},
{
prompt: z.string().describe('The text prompt to generate from'),
length: z.number().max(1000).describe('Maximum length of generated text')
},
async ({ prompt, length }) => {
// Your tool logic here
const generatedText = await someAIService.generate(prompt, length);
return {
content: [{
type: 'text',
text: generatedText
}]
};
}
);API Reference
PayflowMcpServer
Extends the standard McpServer with paid tool capabilities.
const server = new PayflowMcpServer(serverInfo, options?);paidTool()
Register a tool that requires payment before execution.
Signatures:
// Basic paid tool
paidTool(name: string, options: PaymentOptions, callback: ToolCallback)
// With description
paidTool(name: string, description: string, options: PaymentOptions, callback: ToolCallback)
// With parameters schema
paidTool<Args>(name: string, options: PaymentOptions, paramsSchema: Args, callback: ToolCallback<Args>)
// With description and parameters
paidTool<Args>(name: string, description: string, options: PaymentOptions, paramsSchema: Args, callback: ToolCallback<Args>)
// With annotations
paidTool<Args>(name: string, description: string, options: PaymentOptions, paramsSchema: Args, annotations: ToolAnnotations, callback: ToolCallback<Args>)PaymentOptions
Configuration for payment requirements:
type PaymentOptions = {
price: number; // Price in USDC
recipient: string; // Ethereum address to receive payment
asset?: string; // Asset address (optional, defaults to USDC)
network?: number | string; // Network (optional, defaults to Base)
}How Payments Work
- Client Request: Client calls your paid tool with a
paymentparameter containing an x402 payment header - Payment Verification: SDK automatically verifies the payment against your specified requirements
- Tool Execution: If payment is valid, your tool callback is executed
- Payment Settlement: Payment is settled on-chain
- Response: Tool result is returned with payment transaction reference
sequenceDiagram
participant Client
participant PayflowServer as Payflow MCP Server
participant Facilitator as x402 Facilitator
participant Blockchain as Base Network
participant ToolLogic as Your Tool Logic
Client->>PayflowServer: Call paid tool with payment header
Note over PayflowServer: Step 1: Payment Verification
PayflowServer->>PayflowServer: Decode x402 payment
PayflowServer->>PayflowServer: Generate payment requirements
PayflowServer->>Facilitator: Verify payment against requirements
Facilitator-->>PayflowServer: Payment verification result
alt Payment Invalid
PayflowServer-->>Client: Error: Invalid payment
else Payment Valid
Note over PayflowServer: Step 2: Tool Execution
PayflowServer->>ToolLogic: Execute tool callback with params
ToolLogic-->>PayflowServer: Tool execution result
Note over PayflowServer: Step 3: Payment Settlement
PayflowServer->>Facilitator: Settle payment on-chain
Facilitator->>Blockchain: Submit payment transaction
Blockchain-->>Facilitator: Transaction hash
Facilitator-->>PayflowServer: Settlement response
Note over PayflowServer: Step 4: Response
PayflowServer->>PayflowServer: Add transaction reference to result
PayflowServer-->>Client: Tool result + payment transaction
endComplete Example
import { PayflowMcpServer } from '@chainbound/payflow-sdk';
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
import { z } from 'zod';
const server = new PayflowMcpServer({
name: 'weather-server',
version: '1.0.0',
});
// Free tool (standard MCP)
server.tool(
'get_weather_info',
'Get general weather information',
async () => ({
content: [{
type: 'text',
text: 'Weather service available. Use get_weather for specific locations.'
}]
})
);
// Paid tool for detailed weather
server.paidTool(
'get_weather',
'Get detailed weather for a specific location',
{
price: 0.02,
recipient: '0x742d35Cc6634C0532925a3b8D1d3e14C1C3E6FC8' // Your wallet address
},
{
location: z.string().describe('City name or coordinates'),
units: z.enum(['metric', 'imperial']).optional().describe('Temperature units')
},
async ({ location, units = 'metric' }) => {
// Call your weather API
const weather = await weatherAPI.getWeather(location, units);
return {
content: [{
type: 'text',
text: `Weather in ${location}: ${weather.temperature}°${units === 'metric' ? 'C' : 'F'}, ${weather.condition}`
}]
};
}
);
// Start server
const transport = new StdioServerTransport();
await server.connect(transport);Environment Setup
Your MCP server should handle these environment variables:
CDP_API_KEY_ID=your-api-key-id
CDP_API_KEY_SECRET=your-api-key-secretClient Usage
Clients need to provide payment headers when calling paid tools. The payment header should be generated using the x402 protocol with your specified price and recipient.
License
MIT