const schema = ` CREATE TABLE IF NOT EXISTS sessions ( id INTEGER PRIMARY KEY AUTOINCREMENT, external_id TEXT UNIQUE NOT NULL, created_at INTEGER NOT NULL DEFAULT (unixepoch()), updated_at INTEGER NOT NULL DEFAULT (unixepoch()), metadata TEXT ); CREATE TABLE IF NOT EXISTS episodes ( id INTEGER PRIMARY KEY AUTOINCREMENT, session_id INTEGER NOT NULL REFERENCES sessions(id) ON DELETE CASCADE, user_message TEXT NOT NULL, ai_response TEXT NOT NULL, created_at INTEGER NOT NULL DEFAULT (unixepoch()), token_count INTEGER, metadata TEXT ); CREATE TABLE IF NOT EXISTS entities ( id INTEGER PRIMARY KEY AUTOINCREMENT, name TEXT NOT NULL, type TEXT NOT NULL, notes TEXT, created_at INTEGER NOT NULL DEFAULT (unixepoch()), updated_at INTEGER NOT NULL DEFAULT (unixepoch()), metadata TEXT, UNIQUE(name, type) ); CREATE TABLE IF NOT EXISTS relationships ( id INTEGER PRIMARY KEY AUTOINCREMENT, from_id INTEGER NOT NULL REFERENCES entities(id) ON DELETE CASCADE, to_id INTEGER NOT NULL REFERENCES entities(id) ON DELETE CASCADE, label TEXT NOT NULL, created_at INTEGER NOT NULL DEFAULT (unixepoch()), metadata TEXT, UNIQUE(from_id, to_id, label) ); CREATE INDEX IF NOT EXISTS idx_relationships_from ON relationships(from_id); CREATE INDEX IF NOT EXISTS idx_relationships_to ON relationships(to_id); CREATE TABLE IF NOT EXISTS entity_episodes ( entity_id INTEGER NOT NULL REFERENCES entities(id) ON DELETE CASCADE, episode_id INTEGER NOT NULL REFERENCES episodes(id) ON DELETE CASCADE, PRIMARY KEY (entity_id, episode_id) ); CREATE INDEX IF NOT EXISTS idx_entity_episodes_entity ON entity_episodes(entity_id); CREATE INDEX IF NOT EXISTS idx_entity_episodes_episode ON entity_episodes(episode_id); CREATE TABLE IF NOT EXISTS projects ( id INTEGER PRIMARY KEY AUTOINCREMENT, name TEXT NOT NULL, description TEXT, colour TEXT, icon TEXT, created_at INTEGER NOT NULL DEFAULT (unixepoch()) ); CREATE TABLE IF NOT EXISTS summaries ( id INTEGER PRIMARY KEY AUTOINCREMENT, session_id INTEGER REFERENCES sessions(id) ON DELETE CASCADE, project_id INTEGER REFERENCES projects(id) ON DELETE CASCADE, content TEXT NOT NULL, token_count INTEGER, episode_range TEXT, created_at INTEGER NOT NULL DEFAULT (unixepoch()), metadata TEXT ); CREATE INDEX IF NOT EXISTS idx_episodes_session ON episodes(session_id); CREATE INDEX IF NOT EXISTS idx_episodes_created ON episodes(created_at); CREATE INDEX IF NOT EXISTS idx_entities_type ON entities(type); CREATE VIRTUAL TABLE IF NOT EXISTS episodes_fts USING fts5(user_message, ai_response, content=episodes, content_rowid=id); CREATE TRIGGER IF NOT EXISTS episodes_fts_insert AFTER INSERT ON episodes BEGIN INSERT INTO episodes_fts(rowid, user_message, ai_response) VALUES (new.id, new.user_message, new.ai_response); END; CREATE TRIGGER IF NOT EXISTS episodes_fts_delete AFTER DELETE ON episodes BEGIN INSERT INTO episodes_fts(episodes_fts, rowid, user_message, ai_response) VALUES ('delete', old.id, old.user_message, old.ai_response); END; CREATE TRIGGER IF NOT EXISTS episodes_fts_update AFTER UPDATE ON episodes BEGIN INSERT INTO episodes_fts(episodes_fts, rowid, user_message, ai_response) VALUES ('delete', old.id, old.user_message, old.ai_response); INSERT INTO episodes_fts(rowid, user_message, ai_response) VALUES (new.id, new.user_message, new.ai_response); END; `; module.exports = schema;