Skip to content

Latest commit

 

History

History
261 lines (216 loc) · 14.8 KB

File metadata and controls

261 lines (216 loc) · 14.8 KB

Morphkit

Semantic AI compiler + completion engine that converts TypeScript/React web apps to native SwiftUI iOS apps. Auto-detects backend services (Supabase, Stripe, SSE streaming) and generates the right iOS SDK integrations.

Project Structure

morphkit/
├── src/
│   ├── index.ts              # CLI entry point (10 commands: analyze, generate, plan, complete, verify, etc.)
│   ├── analyzer/             # Stage 1: Web app analysis (ts-morph AST parsing)
│   │   ├── repo-scanner.ts   # File discovery, framework detection
│   │   ├── ast-parser.ts     # TypeScript AST parsing, type/component extraction
│   │   ├── component-extractor.ts  # React component analysis
│   │   ├── route-extractor.ts      # Next.js App Router route tree
│   │   ├── state-extractor.ts      # useState/Zustand/Redux/Context detection
│   │   ├── api-extractor.ts        # fetch/axios/API route extraction
│   │   └── index.ts                # Orchestrator: analyzeRepo()
│   ├── semantic/             # Stage 2: Semantic model building
│   │   ├── model.ts          # Zod schemas — THE canonical type source
│   │   ├── builder.ts        # Analyzer output → SemanticAppModel
│   │   ├── adapter.ts        # Web patterns → iOS patterns mapping
│   │   └── index.ts
│   ├── generator/            # Stage 3: SwiftUI code generation
│   │   ├── swiftui-generator.ts    # Views (List, Form, Detail, Dashboard)
│   │   ├── model-generator.ts      # Swift Codable structs from entities
│   │   ├── navigation-generator.ts # TabView, NavigationStack, Router
│   │   ├── networking-generator.ts # URLSession API client
│   │   ├── project-generator.ts    # Xcode project orchestrator
│   │   └── index.ts
│   ├── ai/                   # AI integration (Claude, OpenAI, Grok)
│   │   ├── provider.ts       # Provider-agnostic AIProvider interface
│   │   ├── providers/        # claude.ts, grok.ts, openai.ts implementations
│   │   ├── structured-output.ts    # Zod schemas for AI responses
│   │   ├── prompts/          # Intent extraction, component mapping, code gen
│   │   └── index.ts
│   ├── mcp/                  # Model Context Protocol server
│   │   └── server.ts         # 9 MCP tools for Claude Code integration
│   └── verify.ts             # Project verification & completion tracking
├── templates/                # Swift/SwiftUI code templates
├── test/
│   ├── analyzer/             # Unit tests for each extractor
│   ├── semantic/             # Builder tests
│   ├── generator/            # Generator output tests
│   ├── e2e/                  # Full pipeline integration tests
│   └── __fixtures__/         # Sample Next.js app for testing
├── package.json
├── tsconfig.json
└── bunfig.toml

Tech Stack

  • Runtime: Bun 1.0+
  • Language: TypeScript (strict mode)
  • AST Parsing: ts-morph (TypeScript Compiler API)
  • AI: Multi-provider (Claude, OpenAI, Grok) — auto-detected from env vars, or --no-ai for heuristics only
  • Schemas: Zod for runtime validation + type inference
  • Testing: bun:test with coverage
  • CLI: Commander.js + chalk + ora

Key Conventions

Type System

  • src/semantic/model.ts is the single source of truth for all types
  • All types are Zod schemas first, TypeScript types inferred via z.infer<>
  • Generators must conform to the model types, not define their own
  • The analyzer has its own types (ExtractedComponent, ExtractedRoute, etc.) that are mapped to semantic model types in the builder

Pipeline Architecture

CLI → Analyzer (ts-morph) → Builder (→ SemanticAppModel) → Adapter (→ iOS mapping) → Generator (→ SwiftUI files)
  • Each stage is independent and testable
  • AI is optional — builder falls back to heuristics when XAI_API_KEY is not set
  • The SemanticAppModel is the boundary between analysis and generation

Code Generation

  • Generated Swift targets iOS 17+ (use @Observable, not ObservableObject; #Preview, not PreviewProvider)
  • All generated files start with // Generated by Morphkit from: {relative_source_path}
  • Confidence scoring: high/medium/low per generated file
  • Entity names are always PascalCase, variables camelCase in generated Swift
  • Generated networking includes a KeychainHelper.swift for secure iOS Keychain token storage
  • Generated APIConfiguration enforces HTTPS in production with TLS 1.2+ minimum
  • Generated APIClient uses APIConfiguration.secureSession with proper timeout/TLS config
  • Swift validation runs both swiftc -parse (per-file syntax) and swift build (cross-file types) after generation
  • Generated output compiles with zero errors across all 6 test fixtures (compilation guarantee)
  • ForEach closures use explicit type annotations (item: Entity) in to avoid Swift 6 type inference issues with complex view builders

Testing

  • Run: bun test
  • Typecheck: bun run typecheck
  • E2E test uses test/__fixtures__/sample-nextjs-app/ — a real Next.js e-commerce app
  • Tests should verify generated output structure, not exact string matches

Common Commands

bun test                    # Run all tests
bun run typecheck           # TypeScript strict checking
bun run src/index.ts analyze ./app          # Analyze a Next.js app
bun run src/index.ts plan ./app             # Generate iOS conversion plan (free)
bun run src/index.ts generate ./app -o ./ios # Generate SwiftUI project
bun run src/index.ts preview ./app          # Preview without writing files
bun run src/index.ts verify ./ios           # Check completion status of generated project
bun run src/index.ts complete ./ios         # Auto-complete all TODOs using Claude API
bun run src/index.ts setup                  # Register MCP server in Claude Code
bun run src/index.ts sync ./app ./ios       # Re-sync after web app changes
bun run src/index.ts watch ./app            # Watch mode — re-generate on changes
bun run src/index.ts doctor                 # Diagnose configuration

Authentication & Monetization

  • CLI supports API key auth: --api-key flag, MORPHKIT_API_KEY env var, or ~/.morphkit/config
  • Backend: Supabase Auth (magic link) + Stripe (webhooks via Edge Functions)
  • Tables: users, api_keys, subscriptions, usage_logs (see supabase/migrations/)
  • Edge Functions: validate-key, log-usage, stripe-webhook (see supabase/functions/)
  • Free tier: 20 conversions/month, Pro: unlimited
  • Dashboard: site/dashboard.html — usage tracking, API key management, Stripe checkout

Key Subsystems

AI Provider System (src/ai/provider.ts, src/ai/providers/)

  • Provider-agnostic abstraction: AIProvider interface with analyzeIntent, mapComponent, suggestStateArchitecture, generateCode methods
  • Three implementations: src/ai/providers/claude.ts, src/ai/providers/grok.ts, src/ai/providers/openai.ts
  • Factory function createProvider(config) auto-detects the best available provider from environment variables
  • CLI flags: --ai-provider <name> to force a provider, --no-ai to disable entirely
  • All responses validated with Zod schemas (AIIntentResultSchema, AIComponentMapResultSchema, etc.)

SwiftData Generation (src/generator/model-generator.ts)

  • Converts semantic Entity objects into Swift @Model classes for SwiftData persistence
  • Also generates DataManager with cache-first loading patterns
  • Produces both Codable structs (for networking) and @Model classes (for persistence)
  • Field type mapping uses mapTsTypeToSwift() and typeDefToSwift() from swiftui-generator.ts

React Route Extraction (src/analyzer/route-extractor.ts)

  • Handles Next.js App Router file-based routing (primary) and React Router detection (secondary)
  • App Router: scans app/ directory for page.tsx, layout.tsx, loading.tsx conventions
  • Dynamic routes ([id], [...slug]) mapped to parameterized NavigationStack destinations
  • Route groups (group) are recognized and flattened
  • React Router: detected via react-router-dom dependency in package.json

Watch Mode (src/watcher.ts)

  • File system watcher for iterative development workflow
  • Monitors source TypeScript/React files for changes and re-runs generation
  • Invoked via CLI with --watch flag on the generate command

Backend Detection (src/analyzer/repo-scanner.ts)

  • detectBackendServices() scans package.json for known services
  • Detected: Supabase (auth, database, storage, realtime), Stripe, Firebase, Clerk, OpenAI, Anthropic
  • For Supabase: scans source files to detect which features are actually used
  • Results populate backendIntegrations on the SemanticAppModel
  • Generators use this to produce platform-specific code (SupabaseManager.swift, PaymentManager.swift, SSEClient.swift)

Mobile Scope Planner (src/planner.ts)

  • generatePlan(model) scores each screen as essential/recommended/optional/skip
  • Estimates complexity (low/medium/high) based on data requirements, SSE streaming, payments
  • Produces a markdown plan document with detected stack, screen scoring, and next steps
  • CLI: morphkit plan <path> (always free — no API key required)

AI Completion Engine (src/complete.ts)

  • completeProject(path, options) iteratively resolves MORPHKIT-TODOs using Claude API
  • Builds structured context: view file + APIClient + models + reference implementation + CLAUDE.md
  • Validates completed code with swiftc --parse before writing
  • Early exits after 3 consecutive non-progress iterations
  • CLI: morphkit complete <path> (requires ANTHROPIC_API_KEY)

Linting

  • ESLint with @typescript-eslint/recommended — config in .eslintrc.json
  • no-explicit-any is set to warn (not error) due to existing as any casts
  • Run: bun run lint

MCP Server (src/mcp/server.ts)

9 tools exposed via the Model Context Protocol for Claude Code integration:

Tool Description
morphkit_analyze Analyze a web app → return semantic model summary
morphkit_generate Full pipeline: analyze → build → generate SwiftUI project
morphkit_plan Generate prioritized implementation plan for iOS conversion
morphkit_screen_context Return everything needed to complete a specific screen (view, models, API methods, reference patterns)
morphkit_verify Check project completion: build status, TODO census, screen/API/model completion %
morphkit_next_task Recommend the next screen to implement based on TODO count and dependency order
morphkit_completion_status Machine-readable JSON with exact TODO locations, line numbers, hints for automated loops
morphkit_complete_screen Full context for completing a single screen (view, APIClient, models, reference impl)
morphkit_fix_build_error Parse Swift build errors and return structured context with surrounding code

Register with morphkit setup — writes to .claude/settings.json.

Verify System (src/verify.ts)

verifyProject(path) returns a VerifyResult with:

  • buildStatus: pass/fail/skipped (runs swift build if toolchain available)
  • todosByCategory: counts of MORPHKIT-TODO: <category> markers
  • todosByFile: per-file TODO counts
  • screenCompletion, apiCoverage, modelCompleteness: percentage metrics
  • overallPercentage: weighted composite score
  • nextStep: human-readable recommendation

MORPHKIT-TODO System

Generated Swift files contain structured TODO markers: // MORPHKIT-TODO: <category>

Categories:

  • wire-api-fetch — Connect a view's data loading to APIClient
  • wire-api-action — Connect a user action (submit, delete) to APIClient
  • complete-model — Add real fields to a placeholder model
  • implement-auth — Wire authentication flow

Each generated view also has // MORPHKIT-TODO-COUNT: N for quick completeness checks.

AI Completion Engine (src/complete.ts)

morphkit complete <project-path> iteratively resolves all MORPHKIT-TODOs using the Claude API:

  1. Calls getDetailedTodos() to find remaining TODOs with exact file/line/context
  2. Builds structured context: view file + APIClient + models + reference implementation + CLAUDE.md
  3. Calls Claude with a system prompt enforcing iOS 17+ patterns (@Observable, .task, NavigationStack)
  4. Validates completed code with swiftc --parse before writing
  5. Repeats until all TODOs are resolved or max iterations reached

Requires ANTHROPIC_API_KEY environment variable.

Generated .claude/commands/

The generator creates slash commands for Claude Code in the output project:

  • /complete-screen — Complete a single screen by name
  • /verify — Run verification and show completion status
  • /next — Get the next recommended task
  • /complete-all — Complete all remaining screens sequentially

Important Notes

  • The AnalysisResult type in builder.ts must match what analyzeRepo() returns from analyzer/index.ts
  • When adding new fields to the semantic model, update the Zod schema in model.ts first, then update builder + generators
  • The typeDefToSwift() function in swiftui-generator.ts is the canonical TypeDefinition → Swift type converter — reuse it, don't duplicate
  • Entity inference comes from 3 sources: TypeScript interfaces (highest priority), state patterns, API response types
  • Tab inference uses route topology (top-level routes = tabs), not screen.isEntryPoint
  • ForEach with complex view builders (AsyncImage, multiple modifiers) requires explicit closure type annotations in Swift 6 — the generators handle this automatically
  • .onDelete on ForEach requires Binding arrays in Swift 6 — cart views use .swipeActions instead
  • Generated endpoint methods use plural names for list fetches (fetchProducts()) and singular for detail fetches (fetchProduct(id:))

Central Documentation Vault

Ashlr AI maintains a central documentation vault at ~/Desktop/documentation project/.

  • This product's vault path: 01-products/morphkit/
  • Agent briefing: ~/Desktop/documentation project/01-products/morphkit/agent-briefing.md
  • Sales context: ~/Desktop/documentation project/01-products/morphkit/sales-context.md
  • Full vault navigation: ~/Desktop/documentation project/CLAUDE.md

Update Triggers

When working in this repo, update the vault when:

  • Feature shipped → update changelog.md + agent-briefing.md (Current Priorities, Current State)
  • Architecture change → update architecture.md + agent-briefing.md (Architecture section)
  • Pricing change → update sales-context.md + agent-briefing.md (Business Context)
  • Priority shift → update roadmap.md + agent-briefing.md (Current Priorities)

Commit convention: vault: update morphkit/{file} — {reason}