JSPM

  • Created
  • Published
  • Downloads 1337
  • Score
    100M100P100Q113854F
  • License Apache-2.0

Unified CLI proxy for Claude Code, Codex CLI, and Gemini CLI with MCP-based multi-layer sub-agent orchestration

Package Exports

    This package does not declare an exports field, so the exports above have been automatically detected and optimized by JSPM instead. If any package subpath is missing, it is recommended to post an issue to the original package (@rk0429/agentic-relay) to support the "exports" field. If that is not possible, create a JSPM override to customize the exports field for this package.

    Readme

    agentic-relay

    CI npm version License: Apache-2.0 Node.js

    A unified CLI that brings Claude Code, Codex CLI, and Gemini CLI under a single interface -- solving tool fragmentation, enabling multi-layer sub-agent orchestration via MCP, and providing proactive context window monitoring.

    Why agentic-relay?

    Working with multiple AI coding CLIs means juggling different command syntaxes, configurations, and authentication flows. Nesting sub-agents across tools is not supported natively. And context window exhaustion catches you off guard.

    agentic-relay addresses three problems:

    Problem Solution
    Tool fragmentation -- three CLIs with different flags, config formats, and auth mechanisms Unified interface with backend adapters that normalize the differences
    No nested sub-agents -- parent agents cannot spawn grandchild agents through different backends MCP server mode lets any MCP-capable client spawn agents across all three backends, with recursion guards
    Context window surprise -- sessions silently hit token limits Hooks + ContextMonitor track usage and notify before the limit is reached

    Prerequisites

    Installation

    # Install globally
    npm install -g @rk0429/agentic-relay
    
    # Initialize project-level config (optional)
    relay init
    
    # Verify installation
    relay doctor

    From Source

    git clone https://github.com/RK0429/agentic-relay.git
    cd agentic-relay
    pnpm install
    pnpm build
    pnpm link --global

    Quick Start

    # Start an interactive session with Claude Code
    relay claude
    
    # One-shot prompt with Codex CLI
    relay codex -p "Refactor this function to use async/await"
    
    # Continue the latest Gemini session
    relay gemini -c
    
    # Check which backends are available
    relay doctor

    Usage

    Backend Commands

    relay claude|codex|gemini              # Interactive mode
    relay claude|codex|gemini -p "query"   # Non-interactive (one-shot)
    relay claude|codex|gemini -c           # Continue latest session
    relay claude|codex|gemini -r ID        # Resume session by ID
    relay claude|codex|gemini --agent NAME # Specify agent
    relay claude|codex|gemini --model NAME # Specify model

    Management Commands

    relay config show               # Show merged config
    relay config get <key>          # Get config value
    relay config set <key> <value>  # Set config value
    relay auth <backend> login      # Authenticate a backend
    relay auth <backend> status     # Check auth status
    relay sessions                  # List/search sessions
    relay update                    # Update backend tools
    relay version                   # Show versions
    relay doctor                    # Run diagnostics
    relay init                      # Initialize .relay/ config

    MCP Commands

    relay mcp list              # List MCP servers
    relay mcp add <name> -- CMD # Add MCP server
    relay mcp remove <name>     # Remove MCP server
    relay mcp sync              # Sync MCP config to backends
    relay mcp serve                              # Start as MCP server (stdio, default)
    relay mcp serve --transport http             # Start as MCP server (HTTP)
    relay mcp serve --transport http --port 8080 # Custom port

    Configuration

    agentic-relay uses a three-tier configuration system. Each tier overrides the one above it.

    Tier Path Scope
    Global ~/.relay/config.json User-wide defaults
    Project .relay/config.json Shared across team (commit to VCS)
    Local .relay/config.local.json Personal overrides (gitignored)

    Example configuration:

    {
      "defaultBackend": "claude",
      "mcpServers": {
        "filesystem": {
          "command": "npx",
          "args": ["-y", "@modelcontextprotocol/server-filesystem", "/path"]
        }
      },
      "hooks": {
        "hooks": [
          {
            "event": "ContextThreshold",
            "command": ["node", "scripts/save-state.js"],
            "timeoutMs": 5000,
            "onError": "warn"
          }
        ]
      },
      "contextMonitor": {
        "enabled": true,
        "thresholdPercent": 75,
        "notifyMethod": "hook"
      }
    }

    Environment Variables

    Variable Description Default
    RELAY_HOME Home directory for relay ~/.relay
    RELAY_LOG_LEVEL Log level (debug/info/warn/error) info
    RELAY_MAX_DEPTH Max recursion depth in MCP server mode 5
    RELAY_CONTEXT_THRESHOLD Context warning threshold (%) 75
    RELAY_CLAUDE_PERMISSION_MODE Claude permission mode (bypassPermissions or default) bypassPermissions
    ANTHROPIC_API_KEY Passed through to Claude Code (optional with subscription) --
    OPENAI_API_KEY Passed through to Codex CLI (optional with subscription) --
    GEMINI_API_KEY Passed through to Gemini CLI (optional with subscription) --

    Security Considerations

    • Claude adapter permission bypass: By default, the Claude adapter runs with bypassPermissions mode to enable non-interactive sub-agent execution. This means spawned Claude Code agents can execute tools without user confirmation. To change this behavior, set the RELAY_CLAUDE_PERMISSION_MODE environment variable to default.

    MCP Server Mode

    agentic-relay can act as an MCP (Model Context Protocol) server, allowing any MCP-capable client to spawn sub-agents across all three backends. This is how nested sub-agent orchestration works -- a parent agent calls relay via MCP, which spawns a child agent on any backend, and that child can call relay again to spawn a grandchild.

    Setup

    Add relay as an MCP server in your client's configuration. For Claude Code:

    {
      "mcpServers": {
        "relay": {
          "command": "relay",
          "args": ["mcp", "serve"]
        }
      }
    }

    Exposed Tools

    Tool Description
    spawn_agent Spawn a sub-agent on a specified backend
    list_sessions Retrieve session history
    get_context_status Query context window usage

    Recursion Guard

    The MCP server includes a three-layer recursion guard to prevent runaway agent chains:

    1. Depth limit -- rejects calls that exceed the maximum nesting depth (default: 5)
    2. Per-session call limit -- caps the total number of spawns within a single session (default: 20)
    3. Loop detection -- identifies repeated calls with the same backend + prompt hash

    Context propagation between parent and child agents uses environment variables: RELAY_TRACE_ID, RELAY_PARENT_SESSION_ID, and RELAY_DEPTH.

    Multi-layer Agent Call Flow

    sequenceDiagram
        participant User
        participant Parent as Parent Agent<br>(Claude Code)
        participant Relay as agentic-relay<br>(MCP Server)
        participant Child as Child Agent<br>(Codex CLI)
        participant Relay2 as agentic-relay<br>(MCP Server)
        participant Grandchild as Grandchild Agent<br>(Gemini CLI)
    
        User->>Parent: Task request
        Parent->>Relay: spawn_agent(codex, prompt)
        Note over Relay: RecursionGuard check<br>depth=1, calls=1
        Relay->>Child: Codex SDK thread.run("prompt")<br>RELAY_DEPTH=1
        Child->>Relay2: spawn_agent(gemini, sub-prompt)
        Note over Relay2: RecursionGuard check<br>depth=2, calls=1
        Relay2->>Grandchild: gemini -p "sub-prompt"<br>RELAY_DEPTH=2
        Grandchild-->>Relay2: Result
        Relay2-->>Child: Result
        Child-->>Relay: Result
        Relay-->>Parent: Result
        Parent-->>User: Final answer

    Architecture

    agentic-relay is organized into six layers.

    graph TD
        A["CLI Layer<br><i>citty entry point</i>"] --> B["Command Handlers<br><i>backend, mcp, config, auth,<br>update, sessions, version, doctor, init</i>"]
        B --> C["Core Layer<br><i>SessionManager, ConfigManager,<br>AuthManager, HooksEngine,<br>ContextMonitor, EventBus</i>"]
        B --> D["MCP Server<br><i>RelayMCPServer,<br>spawn_agent, list_sessions,<br>get_context_status, RecursionGuard</i>"]
        C --> E["Backend Adapters<br><i>BaseAdapter, ClaudeAdapter,<br>CodexAdapter, GeminiAdapter,<br>FlagMapper</i>"]
        C --> F["Infrastructure<br><i>ProcessManager, Logger</i>"]
        D --> E
        D --> F

    Backend Adapters

    Each backend CLI has different flags, output formats, and session handling. The adapter layer normalizes these differences behind a common BackendAdapter interface. Adding a new backend means implementing this interface and registering it with the AdapterRegistry.

    Non-interactive execution uses official SDKs where available:

    Backend Non-interactive (-p) Interactive Session listing
    Claude Code Agent SDK query() CLI spawn Agent SDK listSessions()
    Codex CLI Codex SDK thread.run() CLI spawn --
    Gemini CLI CLI spawn CLI spawn CLI --list-sessions

    Hooks Engine

    An event-driven hook system that executes external commands via stdin/stdout JSON pipes.

    Event Trigger
    SessionStart / SessionEnd Session lifecycle
    PreToolUse / PostToolUse Tool invocation
    PreCompact Before context compaction
    ContextThreshold Context usage exceeds threshold (relay-specific)
    SubagentSpawn / SubagentComplete Sub-agent lifecycle (relay-specific)

    Context Monitor

    Monitors context window usage and fires ContextThreshold events when usage exceeds the configured threshold. Notification methods: stderr (direct output) or hook (triggers the Hooks Engine).

    Project Structure

    src/
      bin/relay.ts                  # Entry point
      commands/                     # Command handlers
        backend.ts                  #   relay claude/codex/gemini
        mcp.ts                      #   relay mcp (list/add/remove/sync/serve)
        config.ts                   #   relay config
        auth.ts                     #   relay auth
        update.ts                   #   relay update
        sessions.ts                 #   relay sessions
        version.ts                  #   relay version
        doctor.ts                   #   relay doctor
        init.ts                     #   relay init
      core/                         # Core modules
        session-manager.ts
        config-manager.ts
        auth-manager.ts
        hooks-engine.ts
        context-monitor.ts
        event-bus.ts
      adapters/                     # Backend adapters
        base-adapter.ts
        claude-adapter.ts
        codex-adapter.ts
        gemini-adapter.ts
        adapter-registry.ts
        flag-mapper.ts
        install-guides.ts
      mcp-server/                   # MCP server mode
        server.ts
        recursion-guard.ts
        tools/
          spawn-agent.ts
          list-sessions.ts
          get-context-status.ts
      infrastructure/               # Infrastructure
        process-manager.ts
        logger.ts
      types/                        # Type definitions
      schemas/                      # Zod validation schemas

    Tech Stack

    • Runtime: Node.js 22+
    • Language: TypeScript
    • Package manager: pnpm
    • CLI framework: citty
    • Bundler: tsup (esbuild-based)
    • Backend SDKs: @anthropic-ai/claude-agent-sdk, @openai/codex-sdk
    • MCP: @modelcontextprotocol/sdk
    • Process management: execa (interactive modes, Gemini CLI)
    • Validation: zod
    • Logging: consola
    • Testing: vitest (771 tests across 35 files)
    • Coverage: @vitest/coverage-v8

    License

    Apache-2.0