Skip to content

Latest commit

 

History

History
425 lines (349 loc) · 23.3 KB

File metadata and controls

425 lines (349 loc) · 23.3 KB

CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

Project Overview

XC-MCP is a Model Context Protocol (MCP) server that provides intelligent access to Xcode command-line tools with advanced caching and progressive disclosure features. It wraps xcodebuild, simctl, and idb commands to solve token overflow issues while maintaining full functionality.

Architecture (V4.0.0)

70 discrete tools, MCP-spec-modernized, with deferred loading (~1k tokens at startup).

Evolution:

Version Tools Architecture
Pre-RTFM (v1.2.1) 51 Individual tools (~7,850 tokens)
V1.3.2 (RTFM) 51 Individual + RTFM (~3,000 tokens)
V2.0.0 28 Operation-enum routers + accessibility-first
V3.0.0 30 Deferred loading + workflows (~1k startup)
V4.0.0 (Current) 70 Discrete tools + MCP spec (annotations / outputSchema / resources) + skill feature parity

V4.0 modernizes the MCP layer and reaches feature parity with the ios-simulator-skill:

  • SDK: @modelcontextprotocol/sdk@^1.29, protocol 2025-06-18. Zod v4.
  • Routers dissolved → discrete tools: the v2 operation-enum routers are gone. Annotations and outputSchema are per-tool, so each operation is now its own tool (deferred loading already covers the token cost). See the Migration Guide below.
  • Tool annotations: every tool declares title + readOnlyHint/destructiveHint/idempotentHint/openWorldHint so clients can gate destructive ops (delete/erase/uninstall/clear).
  • Structured output: high-value tools (xcodebuild-build/-test, accessibility-audit, localization-audit, xcode-model-inspect, visual-diff) declare outputSchema and return validated structuredContent.
  • Resources: large cached output is exposed via the resources capability at xcmcp://response/{cacheId}; build/test/list/ui-describe emit resource_link blocks (cache IDs retained for back-compat).
  • listChanged capability declared for deferred/dynamic tool loading.
  • Deferred loading retained (XC_MCP_DEFER_LOADING); rtfm provides progressive docs; old router names still fuzzy-match in rtfm.

Tool Categories (V4.0):

  • build: xcodebuild-version/-list/-build/-clean/-test/-get-details/-showsdks/-inspect-scheme/-validate-capabilities
  • simulator: simctl-list/-get-details/-health-check/-suggest + lifecycle: simctl-boot/-shutdown/-create/-delete/-erase/-clone/-rename
  • app: simctl-install/-uninstall/-launch/-terminate/-get-app-container/-container/-openurl
  • idb: idb-ui-describe/-find-element/-tap/-input/-gesture, accessibility-quality-check, accessibility-audit, idb-targets, idb-list-apps, idb-install/-uninstall/-launch/-terminate
  • io: simctl-io, screenshot
  • devicestate: simctl-appearance, simctl-location
  • analysis: localization-audit, xcode-model-inspect, visual-diff
  • diagnostics: hang-start/-stop/-get-details/-list (HangBuster)
  • cache: cache-get-stats/-get-config/-set-config/-clear
  • workflow: workflow-tap-element/-fresh-install/-build-and-run, test-record-step, test-record-report
  • system: rtfm, persistence-enable/-disable/-status, simctl-push/-addmedia/-pbcopy/-privacy/-status-bar/-stream-logs

V4.0 Migration Guide (breaking)

The v2/v3 operation-enum routers were removed. Call the discrete tool directly:

OLD (router)                                   NEW (discrete tool)
─────────────────────────────────────────────────────────────────
simctl-device({operation:"boot", ...})       → simctl-boot({...})
simctl-device({operation:"shutdown", ...})   → simctl-shutdown({...})
simctl-device({operation:"create", ...})     → simctl-create({...})
simctl-device({operation:"delete", ...})     → simctl-delete({...})
simctl-device({operation:"erase", ...})      → simctl-erase({...})
simctl-device({operation:"clone", ...})      → simctl-clone({...})
simctl-device({operation:"rename", ...})     → simctl-rename({...})
simctl-app({operation:"install", ...})       → simctl-install({...})
simctl-app({operation:"uninstall", ...})     → simctl-uninstall({...})
simctl-app({operation:"launch", ...})        → simctl-launch({...})
simctl-app({operation:"terminate", ...})     → simctl-terminate({...})
idb-app({operation:"install", ...})          → idb-install({...})
idb-app({operation:"uninstall", ...})        → idb-uninstall({...})
idb-app({operation:"launch", ...})           → idb-launch({...})
idb-app({operation:"terminate", ...})        → idb-terminate({...})
cache({operation:"get-stats"})               → cache-get-stats({...})
cache({operation:"get-config"})              → cache-get-config({...})
cache({operation:"set-config", ...})         → cache-set-config({...})
cache({operation:"clear", ...})              → cache-clear({...})
persistence({operation:"enable", ...})       → persistence-enable({...})
persistence({operation:"disable", ...})      → persistence-disable({...})
persistence({operation:"status"})            → persistence-status({...})

Operation-specific parameters are unchanged; just drop the operation field and use the matching tool name. rtfm({ toolName: "simctl-device" }) still fuzzy-suggests the discrete tools.

New in V4 (feature parity with ios-simulator-skill):

  • simctl-appearance (theme/Dynamic Type/locale+RTL), simctl-location (GPS/city/GPX/waypoints)
  • simctl-container (app sandbox ls/cat/userdefaults/coredata-path)
  • enhanced simctl-stream-logs (severity filter + dedup + statistics)
  • accessibility-audit (WCAG-tier audit), localization-audit (.xcstrings), xcode-model-inspect (Core Data/SwiftData), visual-diff (PNG pixel diff)
  • HangBuster: hang-start/hang-stop/hang-get-details/hang-list (main-thread hang capture + clustering)
  • test-record-step/test-record-report (test recording + markdown report)

Development Commands

Build and Development

  • npm run build - Compile TypeScript to JavaScript in dist/
  • npm run dev - Development mode with TypeScript watch compilation
  • npm start - Start the MCP server from compiled JavaScript
  • npm run clean - Remove dist/ build artifacts

Code Quality and Testing

  • npm run lint - Run ESLint on TypeScript source files
  • npm run lint:fix - Auto-fix ESLint issues where possible
  • npm run format - Format code with Prettier
  • npm run format:check - Check code formatting without making changes
  • npm test - Run Jest test suite with ESM support
  • npm run test -- --watch - Run tests in watch mode during development
  • npm run test -- --coverage - Run tests with coverage report (80% threshold required)
  • npm run test -- tests/tests/utils/ - Run specific test directory
  • npm run test -- --testNamePattern="cache" - Run tests matching pattern

Git Hooks and Pre-commit

  • npm run precommit - Run lint-staged (triggered automatically by Husky)
  • npm run prepare - Set up Husky git hooks
  • Lint-staged automatically runs prettier and eslint on staged TypeScript files

MCP Server Testing

  • node dist/index.js - Run the MCP server directly after building
  • Use stdio transport for MCP client testing
  • Validate Xcode installation is available before server operations

Architecture Overview

Core Components

  • src/index.ts - Main MCP server with tool registration and request routing
  • src/tools/ - Tool implementations organized by command category:
    • xcodebuild/ - Build, test, clean, list, version tools with intelligent defaults
    • simctl/ - Simulator management with progressive disclosure
    • cache/ - Cache management and statistics tools
  • src/state/ - Intelligent caching system:
    • simulator-cache.ts - Simulator state with usage tracking and performance metrics
    • project-cache.ts - Project configuration memory and build history
    • build-settings-cache.ts - Xcode build settings with auto-discovery of bundle IDs, deployment targets, and capabilities
  • src/utils/ - Shared utilities for command execution and validation
  • src/types/ - TypeScript definitions for Xcode data structures

Key Architectural Features

  • Progressive Disclosure: Returns concise summaries by default, full details on demand via cache IDs
  • Intelligent Caching: 4-layer cache system (simulator, project, build settings, response) with smart invalidation
  • Performance Tracking: Boot times, build metrics, and usage patterns for optimization
  • Smart Defaults: Learns from successful builds and suggests optimal configurations

Cache System Design

  • SimulatorCache: 1-hour default retention, tracks device usage and boot performance
  • ProjectCache: Remembers successful build configurations per project
  • BuildSettingsCache: 1-hour default retention, auto-discovers bundle IDs, deployment targets, device families, and app capabilities from project build settings
  • ResponseCache: 30-minute retention for progressive disclosure of large outputs
  • All caches support configurable timeouts and selective clearing

Tool Response Pattern

Tools return structured responses with:

  • Success indicators and error handling
  • Cache IDs for progressive disclosure when outputs exceed token limits
  • Smart recommendations based on usage history
  • Performance metrics for optimization insights

Critical Tool Categories and Usage Patterns

  • xcodebuild-build: Returns buildId for progressive access to full logs via xcodebuild-get-details
  • xcodebuild-test: Returns testId for progressive access to full test logs via xcodebuild-get-details
  • simctl-list: Returns cacheId for progressive access to full device data via simctl-get-details
  • simctl-device: Consolidated router with 7 operations (boot, shutdown, create, delete, erase, clone, rename)
  • simctl-app: Consolidated router with 4 operations (install, uninstall, launch, terminate)
  • cache: Consolidated router with 4 operations (get-stats, get-config, set-config, clear)
  • Progressive Disclosure: Large outputs (10k+ tokens) automatically cached to prevent MCP token overflow

Accessibility-First Workflow (V2.0)

Core Philosophy: XC-MCP promotes accessibility-first automation to encourage inclusive app development while enabling faster, cheaper AI interaction.

Workflow Pattern:

  1. Assess Quality: accessibility-quality-check({ screenContext: "LoginScreen" })

    • Returns: rich (>3 tappable) | moderate (2-3) | minimal (≤1)
    • Cost: ~30 tokens, ~80ms
  2. Decision Branch:

    • IF rich or moderate: Use idb-ui-find-element + idb-ui-tap (semantic approach)
    • IF minimal: Fall back to screenshot (visual approach last resort)
  3. Semantic Element Search: idb-ui-find-element({ query: "login" })

    • Returns: Tap-ready coordinates (centerX, centerY) with frame boundaries
    • Cost: ~40 tokens, ~120ms
    • 3-4x faster and cheaper than screenshot analysis

Performance Comparison:

Approach Tokens Latency When to Use
Accessibility Tree ~50 ~120ms Rich UIs (>3 tappable elements)
Screenshot Analysis ~170 ~2000ms Minimal UIs (≤1 tappable element)
Efficiency Gain 3.4x cheaper 16x faster When accessibility sufficient

Why This Matters:

  • Encourages developers to build accessible UIs benefiting all users
  • Enables precise semantic targeting vs visual pattern matching
  • Reduces token cost and execution time significantly
  • Promotes inclusive app development practices

V2.0 Migration Notes

Major Changes from V1.3.2:

  • Tool consolidation: 51 → 28 tools (21 tools → 6 routers with operation enums)
  • Token reduction: 3,000 → 1,980 tokens (40% additional savings beyond RTFM)
  • Accessibility-first: 3 new tools for semantic UI automation workflow
  • Operation enums: simctl-device({ operation: "boot" }) instead of simctl-boot

Tool Consolidation Mapping:

Old (V1.3.2)              → New (V2.0.0)
─────────────────────────────────────────────────────────
simctl-boot              → simctl-device({ operation: "boot" })
simctl-shutdown          → simctl-device({ operation: "shutdown" })
simctl-create            → simctl-device({ operation: "create" })
simctl-delete            → simctl-device({ operation: "delete" })
simctl-erase             → simctl-device({ operation: "erase" })
simctl-clone             → simctl-device({ operation: "clone" })
simctl-rename            → simctl-device({ operation: "rename" })

simctl-install           → simctl-app({ operation: "install" })
simctl-uninstall         → simctl-app({ operation: "uninstall" })
simctl-launch            → simctl-app({ operation: "launch" })
simctl-terminate         → simctl-app({ operation: "terminate" })

idb-install              → idb-app({ operation: "install" })
idb-uninstall            → idb-app({ operation: "uninstall" })
idb-launch               → idb-app({ operation: "launch" })
idb-terminate            → idb-app({ operation: "terminate" })

cache-get-stats          → cache({ operation: "get-stats" })
cache-get-config         → cache({ operation: "get-config" })
cache-set-config         → cache({ operation: "set-config" })
cache-clear              → cache({ operation: "clear" })

persistence-enable       → persistence({ operation: "enable" })
persistence-disable      → persistence({ operation: "disable" })
persistence-status       → persistence({ operation: "status" })

New Tools in V2.0:

  • idb-ui-find-element: Semantic element search by label/identifier
  • accessibility-quality-check: Rapid UI richness assessment
  • Enhanced idb-ui-describe: Optimized accessibility tree queries with progressive disclosure

Removed Tools (Niche Use Cases):

  • xcodebuild-showsdks: Use xcodebuild-version instead
  • simctl-suggest: Use simctl-list quick-access recommendations
  • simctl-addmedia, simctl-privacy, simctl-pbcopy, simctl-status-bar: Commented out to reduce schema bloat
  • list-cached-responses: Integrated into main cache tools

For Claude Code (V2.0):

  • Use rtfm() to discover tools progressively
  • Prefer accessibility-quality-check before screenshots
  • Use idb-ui-find-element for semantic element search
  • Progressive disclosure via cache IDs (buildId, testId, cacheId, uiTreeId)

V3.0 Architecture Changes

Major Changes from V2.0:

  • Deferred loading: Only tool-search and rtfm visible at startup (~1k tokens vs ~18.7k)
  • Tool count: 28 → 30 tools (added 2 workflow tools)
  • Dynamic discovery: Agents discover tools on-demand via tool-search
  • Auto-enabling: Discovered tools automatically added to agent context
  • Startup optimization: 94% reduction in initial context overhead
  • Full feature parity: All V2.0 features preserved with dynamic loading

New Tools in V3.0:

  • tool-search: Dynamic tool discovery by name, description, category, or capability
  • workflow-tap-element: High-level semantic tap workflow combining accessibility assessment and element interaction
  • workflow-fresh-install: Clean slate installation workflow for testing

Tool Search Usage:

// Discover build tools
tool-search({ query: "build", category: "build" })

// Find simulator tools
tool-search({ query: "boot" })

// List all tools in a category
tool-search({ category: "idb" })

Workflow Tools:

  • workflow-tap-element: Combines accessibility-quality-check + idb-ui-find-element + idb-ui-tap into single high-level operation
  • workflow-fresh-install: Combines device cleanup, fresh install, and app launch into single operation

For Claude Code (V3.0):

  • Start with tool-search to discover relevant tools
  • Use rtfm() for detailed documentation once tools are discovered
  • workflow-tap-element for accessibility-first UI interaction
  • workflow-fresh-install for test environment setup
  • Progressive disclosure via cache IDs (buildId, testId, cacheId, uiTreeId)

Environment Variables:

  • XC_MCP_DEFER_LOADING=false - Disables deferred loading and loads all tools like V2.x (default: true)

Development Guidelines

Code Style and Quality Standards

  • ESLint Configuration: TypeScript-specific rules with Prettier integration
  • Formatting: 100-character line width, 2-space indentation, single quotes
  • Language Target: ES2020+ with Node.js ESM modules ("type": "module")
  • Coverage Requirements: 60% minimum across branches, functions, lines, statements (current: 60.28%)
  • Pre-commit Validation: Husky + lint-staged ensures code quality before commits
  • Unused Variables: Prefix with underscore (_unused) to satisfy linting

Error Handling

  • All tools validate Xcode installation before execution
  • Proper async/await patterns with comprehensive error catching
  • MCP-compliant error responses with appropriate error codes

Cache Management

  • Cache validity checks based on file modification times
  • Configurable cache timeouts via tool parameters
  • Graceful degradation when caches are invalid or missing

Progressive Disclosure Implementation

  • Large command outputs (>token limits) automatically cached with unique IDs
  • Summary responses provide key information upfront
  • Detail retrieval tools allow drilling down into cached full outputs
  • Smart filtering and pagination for large datasets

Testing and Quality Assurance

Test Architecture

  • Jest with ESM Support: Uses ts-jest preset with ES module transformation
  • Test Structure: Tests in tests/__tests__/ mirror src/ structure
  • Coverage Thresholds: 80% minimum across all metrics (enforced in CI)
  • Mock Integration: Custom MCP SDK mocks for testing tool responses
  • Test Categories: State management, utility functions, command execution, and validation

Running Tests

  • All Tests: npm test (includes TypeScript compilation validation)
  • Specific Tests: npm test tests/__tests__/state/ (test specific modules)
  • Coverage Report: npm test -- --coverage (generates HTML + LCOV reports)
  • Watch Mode: npm test -- --watch (re-run tests on file changes)
  • Pattern Matching: npm test -- --testNamePattern="cache" (test specific functionality)

Pre-commit Requirements (Automated via Husky)

  • TypeScript Compilation: Must compile without errors
  • ESLint Validation: No errors (warnings acceptable, max 50 on staged files)
  • Prettier Formatting: Automatically applied to staged files
  • Test Suite: All tests must pass before commits
  • Git Hooks: Husky enforces pre-commit validation automatically

Environment Dependencies

  • macOS Required: Xcode command-line tools must be installed
  • Xcode Validation: Tools validate installation before execution
  • Compatibility: Xcode 15+ and iOS simulators
  • Node.js: Version 18+ required for ESM support

MCP Integration

Server Configuration

  • Uses @modelcontextprotocol/sdk for MCP protocol compliance
  • Stdio transport for Claude Desktop integration
  • Tool schema definitions with comprehensive parameter validation

Client Setup Example

{
  "mcpServers": {
    "xc-mcp": {
      "command": "node",
      "args": ["/path/to/xc-mcp/dist/index.js"]
    }
  }
}

MCP Tool Implementation Architecture

  • Main Server: src/index.ts - Tool registration, request routing, and MCP protocol handling
  • Tool Modules: Organized by command category in src/tools/ with consistent return patterns
  • Shared State: Global caches in src/state/ for cross-tool intelligence
  • Validation Layer: src/utils/validation.ts validates Xcode installation before tool execution
  • Command Execution: src/utils/command.ts handles secure subprocess execution with proper error handling

Tool Categories

  • Project Discovery: xcodebuild-list, xcodebuild-showsdks, xcodebuild-version
  • Build Operations: xcodebuild-build, xcodebuild-clean, xcodebuild-get-details
  • Test Operations: xcodebuild-test (with support for test plans, filtering, and test-without-building)
  • Simulator Discovery: simctl-list, simctl-get-details, simctl-suggest
  • Simulator Lifecycle: simctl-create, simctl-delete, simctl-erase, simctl-clone, simctl-rename, simctl-health-check
  • Simulator Control: simctl-boot, simctl-shutdown
  • App Management: simctl-install, simctl-uninstall, simctl-get-app-container
  • App Control: simctl-launch, simctl-terminate, simctl-openurl
  • I/O & Media: simctl-io (screenshots/videos), simctl-addmedia (photo library)
  • Advanced Testing: simctl-privacy (permissions), simctl-push (notifications), simctl-pbcopy (clipboard), simctl-status-bar (status bar override)
  • Cache Management: cache-get-stats, cache-set-config, cache-get-config, cache-clear, list-cached-responses
  • Documentation: rtfm (Read The Manual - progressive disclosure documentation for all 51 tools)

LLM Optimization Patterns

XC-MCP implements context engineering patterns specifically optimized for LLM/AI agent usage. These patterns enable agents to reason effectively about simulator state and testing workflows.

Implemented Patterns

1. Semantic Screenshot Naming (simctl-io)

Screenshots can be named semantically to help agents understand screen context:

  • Parameters: appName, screenName, state
  • Generated filename: {appName}_{screenName}_{state}_{date}.png
  • Example: MyApp_LoginScreen_Empty_2025-01-23.png
  • Agent benefit: Agents can reason about which screen was captured and track state progression

2. Structured Test Context (simctl-push)

Push notifications include structured test tracking:

  • Parameters: testName, expectedBehavior
  • Response includes: deliveryInfo (sent/sentAt) and testContext (testName, expectedBehavior, actualBehavior, passed)
  • Agent benefit: Agents can verify push delivery and validate app behavior matches expectations

3. Permission Audit Trails (simctl-privacy)

Permission changes are tracked with audit context:

  • Parameters: scenario, step
  • Response includes: auditEntry with timestamp, action, service, success, and test context
  • Agent benefit: Agents can track permission state changes across test scenarios and verify permissions at each step

Design Principles

All tools follow these LLM optimization principles:

  1. Semantic Metadata: Include descriptive parameters that help agents reason about operations (e.g., appName, screenName, state)
  2. Structured Context: Responses include context objects (semanticMetadata, deliveryInfo, auditEntry, testContext) for agent reasoning
  3. Progressive Disclosure: Large outputs use cache IDs; summaries provide upfront value
  4. Verification Guidance: Responses suggest next steps for agents to verify outcomes (e.g., "Take screenshot to confirm visual delivery")
  5. Consistent Naming: Tool parameters and response fields follow consistent patterns for agent predictability

Future Optimization Areas

See docs/LLM_OPTIMIZATION.md for comprehensive patterns including:

  • Session logging with artifact indexing for workflow reconstruction
  • Video recording with scene markers and metadata
  • Test result summaries with structured comparison
  • Media library with semantic indexing
  • Status bar before/after snapshots
  • Operation chaining with explicit dependencies