remote-mcp-kernel 0.1.0-alpha.5

A microkernel-based MCP (Model Context Protocol) server with OAuth authentication and multiple transport protocols
Documentation
//! Example demonstrating how to attach custom routers to the microkernel server
//!
//! This example shows how to use the custom router functionality to extend
//! the microkernel server with arbitrary endpoints while maintaining
//! microkernel design principles.
//!
//! Run with:
//! ```bash
//! cargo run --example custom_router_example
//! ```

use axum::{
    Router,
    extract::Path,
    response::{Html, Json},
    routing::{get, post},
};
use oauth_provider_rs::{GitHubOAuthProvider, OAuthProvider, provider_trait::OAuthProviderConfig};
use remote_mcp_kernel::microkernel::{
    GitHubMicrokernelServer, MicrokernelServer, core::CustomRouterConfig,
};
use serde_json::json;
use std::net::SocketAddr;

/// Custom health check endpoint
async fn health_check() -> Json<serde_json::Value> {
    Json(json!({
        "status": "healthy",
        "timestamp": std::time::SystemTime::now()
            .duration_since(std::time::UNIX_EPOCH)
            .unwrap()
            .as_secs(),
        "service": "custom-router-example"
    }))
}

/// Custom metrics endpoint
async fn metrics() -> Json<serde_json::Value> {
    Json(json!({
        "uptime": "5 minutes",
        "requests": 42,
        "memory_usage": "128MB"
    }))
}

/// Custom API endpoint with path parameter
async fn api_status(Path(version): Path<String>) -> Json<serde_json::Value> {
    Json(json!({
        "api_version": version,
        "status": "operational",
        "endpoints": [
            "/health",
            "/metrics",
            "/api/v1/status"
        ]
    }))
}

/// Custom admin dashboard endpoint
async fn admin_dashboard() -> Html<&'static str> {
    Html(
        r#"
        <!DOCTYPE html>
        <html>
        <head>
            <title>Admin Dashboard</title>
            <style>
                body { font-family: Arial, sans-serif; margin: 40px; }
                .card { border: 1px solid #ddd; padding: 20px; margin: 10px 0; border-radius: 5px; }
                .header { color: #333; }
            </style>
        </head>
        <body>
            <h1 class="header">Microkernel Admin Dashboard</h1>
            <div class="card">
                <h3>Server Status</h3>
                <p>✅ Microkernel Server: Running</p>
                <p>✅ OAuth Provider: Connected</p>
                <p>✅ Custom Routers: 3 attached</p>
            </div>
            <div class="card">
                <h3>Available Endpoints</h3>
                <ul>
                    <li><a href="/health">Health Check</a></li>
                    <li><a href="/monitoring/metrics">Metrics</a></li>
                    <li><a href="/api/v1/status">API Status</a></li>
                    <li><a href="/admin">Admin Dashboard</a></li>
                </ul>
            </div>
        </body>
        </html>
    "#,
    )
}

/// Custom webhook endpoint
async fn webhook_handler() -> Json<serde_json::Value> {
    Json(json!({
        "message": "Webhook received",
        "processed": true,
        "timestamp": std::time::SystemTime::now()
            .duration_since(std::time::UNIX_EPOCH)
            .unwrap()
            .as_secs()
    }))
}

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    // Initialize tracing for logging
    tracing_subscriber::fmt::init();

    // Create GitHub OAuth provider
    let github_config = OAuthProviderConfig::with_oauth_config(
        std::env::var("GITHUB_CLIENT_ID").unwrap_or_else(|_| "demo_client_id".to_string()),
        std::env::var("GITHUB_CLIENT_SECRET").unwrap_or_else(|_| "demo_client_secret".to_string()),
        "http://localhost:8080/oauth/callback".to_string(),
        "read:user".to_string(),
        "github".to_string(),
    );

    let github_oauth_provider = GitHubOAuthProvider::new_github(github_config);
    let oauth_provider = OAuthProvider::new(
        github_oauth_provider,
        oauth_provider_rs::http_integration::config::OAuthProviderConfig::default(),
    );

    // Create custom routers

    // 1. Health and basic endpoints router
    let health_router = Router::new()
        .route("/health", get(health_check))
        .route("/webhooks", post(webhook_handler));

    // 2. Monitoring router with path prefix
    let monitoring_router = Router::new().route("/metrics", get(metrics));

    // 3. API router with versioned endpoints
    let api_router = Router::new()
        .route("/v1/status", get(api_status))
        .route("/{version}/status", get(api_status));

    // 4. Admin router with HTML interface
    let admin_router = Router::new().route("/", get(admin_dashboard));

    // Configure custom routers with different configurations
    let custom_routers = vec![
        // Health router without prefix (attached to root)
        (health_router, CustomRouterConfig::default()),
        // Monitoring router with prefix and name
        (
            monitoring_router,
            CustomRouterConfig::with_name_and_prefix("Monitoring", "/monitoring"),
        ),
        // API router with prefix
        (
            api_router,
            CustomRouterConfig::with_name_and_prefix("API", "/api"),
        ),
        // Admin router with prefix
        (
            admin_router,
            CustomRouterConfig::with_name_and_prefix("Admin Dashboard", "/admin"),
        ),
    ];

    // Build the microkernel server with OAuth provider and custom routers
    let microkernel: GitHubMicrokernelServer = MicrokernelServer::new()
        .with_oauth_provider(oauth_provider)
        .with_custom_routers(custom_routers);

    // Define the bind address
    let bind_address: SocketAddr = "127.0.0.1:8080".parse()?;

    // Print available endpoints
    println!("🚀 Starting microkernel server with custom routers...");
    println!("📍 Server listening on: http://{}", bind_address);
    println!("\n📋 Available endpoints:");
    println!("  OAuth:");
    println!("    GET  /oauth/login");
    println!("    GET  /oauth/callback");
    println!("    POST /oauth/token");
    println!("  Custom Endpoints:");
    println!("    GET  /health                  - Health check");
    println!("    POST /webhooks                - Webhook handler");
    println!("    GET  /monitoring/metrics      - System metrics");
    println!("    GET  /api/v1/status           - API status");
    println!("    GET  /api/{{version}}/status   - Versioned API status");
    println!("    GET  /admin                   - Admin dashboard");
    println!("\n🔧 Try these commands:");
    println!("  curl http://localhost:8080/health");
    println!("  curl http://localhost:8080/monitoring/metrics");
    println!("  curl http://localhost:8080/api/v1/status");
    println!("  open http://localhost:8080/admin");

    // Start the server
    microkernel.serve(bind_address).await?;

    Ok(())
}