Skip to main content
Glama

Nikola TEST MCP Server

by Traia-IO
server.py6.72 kB
#!/usr/bin/env python3 """ Nikola TEST MCP MCP Server - FastMCP with D402 Transport Wrapper Uses FastMCP from official MCP SDK with D402MCPTransport wrapper for HTTP 402. Architecture: - FastMCP for tool decorators and Context objects - D402MCPTransport wraps the /mcp route for HTTP 402 interception - Proper HTTP 402 status codes (not JSON-RPC wrapped) Generated from OpenAPI: Environment Variables: - SERVER_ADDRESS: Payment address (IATP wallet contract) - MCP_OPERATOR_PRIVATE_KEY: Operator signing key - D402_TESTING_MODE: Skip facilitator (default: true) """ import os import logging import sys from typing import Dict, Any, Optional from datetime import datetime import requests from retry import retry from dotenv import load_dotenv import uvicorn load_dotenv() # Configure logging logging.basicConfig( level=os.getenv("LOG_LEVEL", "INFO").upper(), format='%(asctime)s - %(name)s - %(levelname)s - %(message)s' ) logger = logging.getLogger('nikola-test-mcp_mcp') # FastMCP from official SDK from mcp.server.fastmcp import FastMCP, Context from starlette.requests import Request from starlette.responses import JSONResponse # D402 payment protocol - using Starlette middleware from traia_iatp.d402.starlette_middleware import D402PaymentMiddleware from traia_iatp.d402.mcp_middleware import require_payment_for_tool, get_active_api_key from traia_iatp.d402.payment_introspection import extract_payment_configs_from_mcp from traia_iatp.d402.types import TokenAmount, TokenAsset, EIP712Domain # Configuration STAGE = os.getenv("STAGE", "MAINNET").upper() PORT = int(os.getenv("PORT", "8000")) SERVER_ADDRESS = os.getenv("SERVER_ADDRESS") if not SERVER_ADDRESS: raise ValueError("SERVER_ADDRESS required for payment protocol") API_KEY = None logger.info("="*80) logger.info(f"Nikola TEST MCP MCP Server (FastMCP + D402 Wrapper)") logger.info(f"API: https://petstore.swagger.io/") logger.info(f"Payment: {SERVER_ADDRESS}") logger.info("="*80) # Create FastMCP server mcp = FastMCP("Nikola TEST MCP MCP Server") logger.info(f"✅ FastMCP server created") # ============================================================================ # TOOL IMPLEMENTATIONS # ============================================================================ # Tool implementations will be added here by endpoint_implementer_crew # Each tool will use the @mcp.tool() and @require_payment_for_tool() decorators # TODO: Add your API-specific functions here # ============================================================================ # APPLICATION SETUP WITH STARLETTE MIDDLEWARE # ============================================================================ def create_app_with_middleware(): """ Create Starlette app with d402 payment middleware. Strategy: 1. Get FastMCP's Starlette app via streamable_http_app() 2. Extract payment configs from @require_payment_for_tool decorators 3. Add Starlette middleware with extracted configs 4. Single source of truth - no duplication! """ logger.info("🔧 Creating FastMCP app with middleware...") # Get FastMCP's Starlette app app = mcp.streamable_http_app() logger.info(f"✅ Got FastMCP Starlette app") # Extract payment configs from decorators (single source of truth!) tool_payment_configs = extract_payment_configs_from_mcp(mcp, SERVER_ADDRESS) logger.info(f"📊 Extracted {len(tool_payment_configs)} payment configs from @require_payment_for_tool decorators") # D402 Configuration facilitator_url = os.getenv("FACILITATOR_URL") or os.getenv("D402_FACILITATOR_URL") operator_key = os.getenv("MCP_OPERATOR_PRIVATE_KEY") network = os.getenv("NETWORK", "sepolia") testing_mode = os.getenv("D402_TESTING_MODE", "false").lower() == "true" # Log D402 configuration with prominent facilitator info logger.info("="*60) logger.info("D402 Payment Protocol Configuration:") logger.info(f" Server Address: {SERVER_ADDRESS}") logger.info(f" Network: {network}") logger.info(f" Operator Key: {'✅ Set' if operator_key else '❌ Not set'}") logger.info(f" Testing Mode: {'⚠️ ENABLED (bypasses facilitator)' if testing_mode else '✅ DISABLED (uses facilitator)'}") logger.info("="*60) if not facilitator_url and not testing_mode: logger.error("❌ FACILITATOR_URL required when testing_mode is disabled!") raise ValueError("Set FACILITATOR_URL or enable D402_TESTING_MODE=true") if facilitator_url: logger.info(f"🌐 FACILITATOR: {facilitator_url}") if "localhost" in facilitator_url or "127.0.0.1" in facilitator_url or "host.docker.internal" in facilitator_url: logger.info(f" 📍 Using LOCAL facilitator for development") else: logger.info(f" 🌍 Using REMOTE facilitator for production") else: logger.warning("⚠️ D402 Testing Mode - Facilitator bypassed") logger.info("="*60) # Add D402 payment middleware with extracted configs app.add_middleware( D402PaymentMiddleware, tool_payment_configs=tool_payment_configs, server_address=SERVER_ADDRESS, requires_auth=False, # Only checks payment testing_mode=testing_mode, facilitator_url=facilitator_url, facilitator_api_key=os.getenv("D402_FACILITATOR_API_KEY"), server_name="nikola-test-mcp-mcp-server" # MCP server ID for tracking ) logger.info("✅ Added D402PaymentMiddleware") logger.info(" - Payment-only mode") # Add health check endpoint (bypasses middleware) @app.route("/health", methods=["GET"]) async def health_check(request: Request) -> JSONResponse: """Health check endpoint for container orchestration.""" return JSONResponse( content={ "status": "healthy", "service": "nikola-test-mcp-mcp-server", "timestamp": datetime.now().isoformat() } ) logger.info("✅ Added /health endpoint") return app if __name__ == "__main__": logger.info("="*80) logger.info(f"Starting Nikola TEST MCP MCP Server") logger.info("="*80) logger.info("Architecture:") logger.info(" 1. D402PaymentMiddleware intercepts requests") logger.info(" - Checks payment → HTTP 402 if missing") logger.info(" 2. FastMCP processes valid requests with tool decorators") logger.info("="*80) # Create app with middleware app = create_app_with_middleware() # Run with uvicorn uvicorn.run( app, host="0.0.0.0", port=PORT, log_level=os.getenv("LOG_LEVEL", "info").lower() )

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/Traia-IO/nikola-test-mcp-mcp-server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server