V8 / database /migrations.py
Drizzy0101's picture
Resolve merge conflicts
59c28b9
Raw
History Blame Contribute Delete
6.36 kB
"""Database migrations — schema versioning."""
SCHEMA_VERSION = 1
MIGRATIONS = {
1: """
CREATE TABLE IF NOT EXISTS users (
id TEXT PRIMARY KEY,
username TEXT UNIQUE NOT NULL,
display_name TEXT,
email TEXT,
avatar_url TEXT,
preferences TEXT DEFAULT '{}',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
CREATE TABLE IF NOT EXISTS conversations (
id TEXT PRIMARY KEY,
user_id TEXT,
title TEXT DEFAULT 'New Chat',
folder_id TEXT,
personality_id TEXT DEFAULT 'synapse',
mode TEXT DEFAULT 'agent',
is_pinned INTEGER DEFAULT 0,
is_bookmarked INTEGER DEFAULT 0,
summary TEXT,
metadata TEXT DEFAULT '{}',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS messages (
id TEXT PRIMARY KEY,
conversation_id TEXT NOT NULL,
role TEXT NOT NULL CHECK(role IN ('user','assistant','system','tool')),
content TEXT NOT NULL,
reasoning TEXT,
tool_calls TEXT,
tool_results TEXT,
model TEXT,
tokens_used INTEGER DEFAULT 0,
metadata TEXT DEFAULT '{}',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (conversation_id) REFERENCES conversations(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS folders (
id TEXT PRIMARY KEY,
user_id TEXT,
name TEXT NOT NULL,
parent_id TEXT,
color TEXT DEFAULT '#6366f1',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS memories (
id TEXT PRIMARY KEY,
user_id TEXT,
conversation_id TEXT,
content TEXT NOT NULL,
memory_type TEXT DEFAULT 'long_term',
importance REAL DEFAULT 0.5,
embedding BLOB,
is_pinned INTEGER DEFAULT 0,
tags TEXT DEFAULT '[]',
metadata TEXT DEFAULT '{}',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
accessed_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS user_facts (
id TEXT PRIMARY KEY,
user_id TEXT NOT NULL,
fact TEXT NOT NULL,
category TEXT DEFAULT 'general',
confidence REAL DEFAULT 1.0,
source TEXT,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS personalities (
id TEXT PRIMARY KEY,
name TEXT NOT NULL,
system_prompt TEXT NOT NULL,
description TEXT,
mood TEXT DEFAULT 'neutral',
humor_level REAL DEFAULT 0.5,
creativity_level REAL DEFAULT 0.7,
is_default INTEGER DEFAULT 0,
avatar_url TEXT,
metadata TEXT DEFAULT '{}',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
CREATE TABLE IF NOT EXISTS chat_history (
id TEXT PRIMARY KEY,
user_id TEXT,
conversation_id TEXT NOT NULL,
action TEXT NOT NULL,
old_value TEXT,
new_value TEXT,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (conversation_id) REFERENCES conversations(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS plugins (
id TEXT PRIMARY KEY,
name TEXT NOT NULL UNIQUE,
description TEXT,
version TEXT DEFAULT '1.0.0',
author TEXT,
enabled INTEGER DEFAULT 1,
config TEXT DEFAULT '{}',
tools TEXT DEFAULT '[]',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
CREATE TABLE IF NOT EXISTS generated_files (
id TEXT PRIMARY KEY,
user_id TEXT,
file_type TEXT NOT NULL,
file_path TEXT NOT NULL,
original_prompt TEXT,
metadata TEXT DEFAULT '{}',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS sessions (
id TEXT PRIMARY KEY,
user_id TEXT,
token TEXT UNIQUE NOT NULL,
ip_address TEXT,
user_agent TEXT,
expires_at TIMESTAMP,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS settings (
user_id TEXT,
key TEXT NOT NULL,
value TEXT,
PRIMARY KEY (user_id, key),
FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE
);
CREATE TABLE IF NOT EXISTS migrations (
version INTEGER PRIMARY KEY,
applied_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
CREATE INDEX IF NOT EXISTS idx_messages_conversation ON messages(conversation_id);
CREATE INDEX IF NOT EXISTS idx_messages_role ON messages(role);
CREATE INDEX IF NOT EXISTS idx_conversations_user ON conversations(user_id);
CREATE INDEX IF NOT EXISTS idx_memories_user ON memories(user_id);
CREATE INDEX IF NOT EXISTS idx_memories_type ON memories(memory_type);
CREATE INDEX IF NOT EXISTS idx_generated_files_user ON generated_files(user_id);
CREATE INDEX IF NOT EXISTS idx_chat_history_conversation ON chat_history(conversation_id);
""",
}
async def run_migrations(db):
await db.execute("""
CREATE TABLE IF NOT EXISTS migrations (
version INTEGER PRIMARY KEY,
applied_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
""")
await db.commit()
cursor = await db.execute(
"SELECT version FROM migrations ORDER BY version DESC LIMIT 1"
)
row = await cursor.fetchone()
current_version = row[0] if row else 0
for version, sql in sorted(MIGRATIONS.items()):
if version > current_version:
await db.executescript(sql)
await db.execute(
"INSERT INTO migrations (version) VALUES (?)", (version,)
)
await db.commit()