ctx0-implementation-plan.md

ctx0 — Implementation Plan

This document outlines the implementation plan for ctx0, the context management system for bot0.


Architecture Decision: Hybrid Storage (Option C)

After evaluating three options, we chose a hybrid approach:

  1. Hosted mode (default): ctx0 data lives in Bytespace Supabase with RLS isolation per user. Zero setup for users.

  2. Self-hosted mode: Users can migrate to their own Supabase instance. They own their database completely.

┌─────────────────────────────────────────────────────────────────────────┐
│                        BYTESPACE SUPABASE                                │
│                                                                         │
│  Platform Layer (shared)              ctx0 Layer (per-user, RLS)        │
│  ├── users                            ├── ctx0_entries                  │
│  ├── billing                          ├── ctx0_sessions                 │
│  ├── subscriptions                    ├── ctx0_embeddings               │
│  └── sync_orchestration               └── ctx0_storage (bucket)         │
│                                                                         │
└─────────────────────────────────────────────────────────────────────────┘
                                    │
                                    │ User wants self-hosted?
                                    ▼
┌─────────────────────────────────────────────────────────────────────────┐
│                        USER'S OWN SUPABASE                               │
│                                                                         │
│  Same schema, exported:                                                 │
│  ├── ctx0_entries                                                       │
│  ├── ctx0_sessions                                                      │
│  └── ctx0_storage (bucket)                                              │
│                                                                         │
└─────────────────────────────────────────────────────────────────────────┘

Why This Approach

  • Fast onboarding — Default is hosted, zero infrastructure setup
  • True ownership when wanted — Migrate to self-hosted anytime
  • Uses existing infrastructure — Bytespace Supabase, sync agents
  • One codebase — Same code works for both modes

Authentication

Hosted Mode

Desktop App / CLI  →  Bytespace Auth (Google SSO)  →  JWT Token
                                                          ↓
                                                   Stored locally
                                                   ~/.bot0/credentials.json
                                                          ↓
                                                   Used for Supabase requests
                                                   RLS: auth.uid() = user_id

Self-Hosted Mode

User provides Supabase URL + service role key
                    ↓
             Stored locally
             ~/.ctx0/config.yaml
                    ↓
             Daemon uses credentials directly
             No Bytespace auth for ctx0 operations

Package Structure

@bot0/ctx0 (Core Library)

packages/ctx0/
├── src/
│   ├── index.ts                    # Main exports
│   │
│   ├── types/
│   │   ├── index.ts                # All type exports
│   │   ├── config.ts               # Ctx0Config, StorageConfig
│   │   ├── session.ts              # SessionLog, Message, ToolCall, etc.
│   │   ├── entry.ts                # Entry, EntryVersion, EntryKind
│   │   ├── query.ts                # LearnedQuery, QueryPlan
│   │   └── sync.ts                 # FileChange, SyncResult
│   │
│   ├── config/
│   │   ├── index.ts
│   │   └── config-manager.ts       # Load/save ~/.ctx0/config.yaml
│   │
│   ├── auth/
│   │   ├── index.ts
│   │   ├── auth-manager.ts         # Handle hosted vs self-hosted auth
│   │   └── credentials.ts          # Store/load credentials
│   │
│   ├── storage/
│   │   ├── index.ts
│   │   ├── supabase-client.ts      # Dynamic client (hosted or self-hosted)
│   │   ├── entries.ts              # ctx0_entries CRUD
│   │   ├── sessions.ts             # ctx0_sessions CRUD
│   │   └── vault-storage.ts        # ctx0-vault bucket operations
│   │
│   ├── session/
│   │   ├── index.ts
│   │   ├── session-tracker.ts      # Track messages, tools, decisions
│   │   └── triggers.ts             # Compaction, idle, session end
│   │
│   ├── subagents/
│   │   ├── index.ts
│   │   ├── base-subagent.ts        # Base class using Bot0Agent
│   │   ├── extractor.ts            # Retrieve context on-demand
│   │   ├── librarian.ts            # Archive sessions to vault
│   │   └── curator.ts              # Maintain vault health
│   │
│   ├── export/
│   │   ├── index.ts
│   │   └── codebase-export.ts      # DB → filesystem export
│   │
│   ├── sync/
│   │   ├── index.ts
│   │   ├── sync-layer.ts           # Bidirectional sync
│   │   ├── conflict-resolution.ts  # Merge strategies
│   │   └── sync-agent-mapper.ts    # Map Bytespace sync agents → ctx0
│   │
│   └── tools/
│       ├── index.ts
│       ├── ctx0-retrieve.ts        # ctx0_retrieve tool
│       ├── ctx0-remember.ts        # ctx0_remember tool
│       ├── ctx0-query.ts           # ctx0_query tool
│       └── ctx0-archive.ts         # ctx0_archive_now tool
│
├── migrations/
│   └── 001_ctx0_schema.sql         # Tables + RLS + indexes
│
├── package.json
├── tsconfig.json
└── tsup.config.ts

@bot0/ctx0-cli (Standalone CLI)

packages/ctx0-cli/
├── src/
│   ├── index.ts                    # CLI entry point
│   └── commands/
│       ├── init.ts                 # ctx0 init [--self-hosted]
│       ├── login.ts                # ctx0 login
│       ├── logout.ts               # ctx0 logout
│       ├── status.ts               # ctx0 status
│       ├── export.ts               # ctx0 export [--scope] [--output]
│       ├── sync.ts                 # ctx0 sync [--push|--pull|--watch]
│       └── migrate.ts              # ctx0 migrate --to-self-hosted
│
├── bin/
│   └── ctx0.js                     # CLI entry point
│
├── package.json
└── tsconfig.json

Database Schema

All tables prefixed with ctx0_ to separate from existing Bytespace tables.

ctx0_entries

The core vault storage — tree structure with metadata and embeddings.

sql
CREATE TABLE ctx0_entries ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), user_id UUID REFERENCES users(id) ON DELETE CASCADE, -- Tree structure path TEXT NOT NULL, -- "/contacts/sarah-chen" parent_path TEXT NOT NULL, -- "/contacts" name TEXT NOT NULL, -- "sarah-chen" entry_kind TEXT NOT NULL, -- "file" | "folder" -- Content (for files) content_ref TEXT, -- Storage bucket reference content_preview TEXT, -- First 500 chars content_hash TEXT, -- For change detection -- Metadata entry_type TEXT, -- "contact" | "project" | "note" | etc. tags TEXT[] DEFAULT '{}', frontmatter JSONB, -- Parsed YAML frontmatter -- Relationships links UUID[] DEFAULT '{}', -- Linked entry IDs -- Sync agent mappings sync_sources JSONB, -- [{ service: 'gmail', external_id: '...' }] -- Versioning version INT DEFAULT 1, -- Vector embedding (pgvector) embedding VECTOR(1536), -- Timestamps created_at TIMESTAMPTZ DEFAULT NOW(), updated_at TIMESTAMPTZ DEFAULT NOW(), accessed_at TIMESTAMPTZ DEFAULT NOW(), access_count INT DEFAULT 0, UNIQUE(user_id, path) );

ctx0_entry_versions

Version history for entries.

sql
CREATE TABLE ctx0_entry_versions ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), entry_id UUID REFERENCES ctx0_entries(id) ON DELETE CASCADE, version INT NOT NULL, content_ref TEXT NOT NULL, changed_at TIMESTAMPTZ DEFAULT NOW(), changed_by TEXT, change_summary TEXT );

ctx0_sessions

Session logs from agent interactions.

sql
CREATE TABLE ctx0_sessions ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), user_id UUID REFERENCES users(id) ON DELETE CASCADE, session_id TEXT NOT NULL, agent TEXT NOT NULL, -- "bot0" | "claude_code" | etc. -- Session data log_ref TEXT, -- Storage reference to full log summary TEXT, -- Stats message_count INT DEFAULT 0, tool_call_count INT DEFAULT 0, files_modified INT DEFAULT 0, -- Status status TEXT DEFAULT 'active', -- "active" | "archived" | "processing" -- Timestamps started_at TIMESTAMPTZ DEFAULT NOW(), ended_at TIMESTAMPTZ, archived_at TIMESTAMPTZ, UNIQUE(user_id, session_id) );

ctx0_learned_queries

SQL templates that get smarter with use.

sql
CREATE TABLE ctx0_learned_queries ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), user_id UUID REFERENCES users(id) ON DELETE CASCADE, name TEXT NOT NULL, natural_language TEXT[] NOT NULL, sql_template TEXT NOT NULL, params JSONB, use_count INT DEFAULT 0, avg_latency_ms INT, last_used TIMESTAMPTZ, created_at TIMESTAMPTZ DEFAULT NOW(), UNIQUE(user_id, name) );

ctx0_embedding_queue

Async embedding updates.

sql
CREATE TABLE ctx0_embedding_queue ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), user_id UUID REFERENCES users(id) ON DELETE CASCADE, entry_id UUID REFERENCES ctx0_entries(id) ON DELETE CASCADE, status TEXT DEFAULT 'pending', -- "pending" | "processing" | "done" | "failed" created_at TIMESTAMPTZ DEFAULT NOW(), processed_at TIMESTAMPTZ );

ctx0_user_config

Per-user ctx0 configuration (storage mode, etc.).

sql
CREATE TABLE ctx0_user_config ( user_id UUID PRIMARY KEY REFERENCES users(id), storage_mode TEXT DEFAULT 'hosted', self_hosted_url TEXT, vault_stats JSONB, created_at TIMESTAMPTZ DEFAULT NOW(), updated_at TIMESTAMPTZ DEFAULT NOW() );

Storage Bucket

New bucket: ctx0-vault

ctx0-vault/
├── {userId}/
│   ├── vault/                     # Entry file contents
│   │   ├── contacts/
│   │   ├── projects/
│   │   └── ...
│   └── sessions/                  # Session archives
│       └── {sessionId}/
│           ├── log.json
│           └── summary.md

Sync Agent Mapping

ctx0 entries can link to Bytespace sync agent data via sync_sources:

typescript
// Example: Contact linked to Gmail and Slack { path: '/contacts/sarah-chen', entry_type: 'contact', frontmatter: { name: 'Sarah Chen', email: 'sarah@example.com' }, sync_sources: [ { service: 'gmail', table: 'sync_gmail_contacts', external_id: 'contact_123' }, { service: 'slack', table: 'sync_slack_users', external_id: 'U123456' } ] }

The Curator subagent queries Bytespace sync tables and updates ctx0 entries.


Implementation Steps

Step 1: Package Setup & Types

  • Create packages/ctx0 with package.json, tsconfig, tsup.config
  • Create packages/ctx0-cli with package.json, tsconfig
  • Define all TypeScript types in src/types/

Step 2: Supabase Schema

  • Write migration SQL (migrations/001_ctx0_schema.sql)
  • Create ctx0-vault storage bucket in Bytespace Supabase
  • Set up RLS policies
  • Enable pgvector extension

Step 3: Config & Auth

  • Config manager (config/config-manager.ts)
  • Auth manager (auth/auth-manager.ts)
  • Credentials storage (auth/credentials.ts)
  • Dynamic Supabase client (storage/supabase-client.ts)

Step 4: Storage Layer

  • Entry CRUD (storage/entries.ts)
  • Session CRUD (storage/sessions.ts)
  • Vault storage bucket ops (storage/vault-storage.ts)

Step 5: Session Tracker

  • SessionTracker class (session/session-tracker.ts)
  • Trigger system (session/triggers.ts)

Step 6: Subagents

  • Base subagent class (subagents/base-subagent.ts)
  • Extractor (subagents/extractor.ts)
  • Librarian (subagents/librarian.ts)
  • Curator (subagents/curator.ts)

Step 7: ctx0 Tools

  • ctx0_retrieve (tools/ctx0-retrieve.ts)
  • ctx0_remember (tools/ctx0-remember.ts)
  • ctx0_query (tools/ctx0-query.ts)
  • ctx0_archive_now (tools/ctx0-archive.ts)

Step 8: Export & Sync

  • Codebase export (export/codebase-export.ts)
  • Sync layer (sync/sync-layer.ts)
  • Conflict resolution (sync/conflict-resolution.ts)
  • Sync agent mapper (sync/sync-agent-mapper.ts)

Step 9: CLI Commands

  • ctx0 init
  • ctx0 login / logout
  • ctx0 status
  • ctx0 export
  • ctx0 sync
  • ctx0 migrate

Step 10: bot0 Daemon Integration

  • Hook SessionTracker into agent loop
  • Register ctx0 tools
  • Set up triggers (compaction, idle, session end)
  • Add ctx0 IPC methods

CLI Commands

bash
# Initialize ctx0 (creates config, sets up vault) ctx0 init ctx0 init --self-hosted --supabase-url https://xxx.supabase.co # Authentication ctx0 login # Opens browser for Google SSO ctx0 logout ctx0 status # Shows connection status, vault stats # Export vault to filesystem ctx0 export # Full export to ~/.ctx0/vault ctx0 export --scope contacts,projects # Selective export ctx0 export --output ./my-context # Custom output path # Sync ctx0 sync --pull # Pull from Supabase to local ctx0 sync --push # Push local changes to Supabase ctx0 sync --watch # Real-time bidirectional sync # Migrate to self-hosted ctx0 migrate --to-self-hosted \ --supabase-url https://my-project.supabase.co \ --supabase-key xxx

ctx0 Tools for Agents

These tools are available to bot0 (and other agents via MCP):

ToolPurpose
ctx0_retrieveGet context from vault (spawns Extractor)
ctx0_rememberStore information for later archival
ctx0_queryExecute a learned query by name
ctx0_archive_nowImmediately archive current session