-- Grundschema. Siehe docs/03-data-model.md. -- Zugangsdaten stehen bewusst NICHT hier drin (ADR-0005) - diese Datei -- wird per VACUUM INTO auf die Windows-Seite gesichert. CREATE TABLE events ( id TEXT PRIMARY KEY, ts TEXT NOT NULL, type TEXT NOT NULL, stream_id TEXT, user_id TEXT, payload TEXT NOT NULL ); CREATE INDEX idx_events_ts ON events(ts); CREATE INDEX idx_events_type ON events(type, ts); CREATE INDEX idx_events_strm ON events(stream_id, ts); CREATE TABLE streams ( id TEXT PRIMARY KEY, started_at TEXT NOT NULL, ended_at TEXT, vod_id TEXT, peak_viewers INTEGER NOT NULL DEFAULT 0, avg_viewers REAL, unique_chatters INTEGER NOT NULL DEFAULT 0, new_followers INTEGER NOT NULL DEFAULT 0 ); CREATE TABLE stream_segments ( id INTEGER PRIMARY KEY, stream_id TEXT NOT NULL REFERENCES streams(id), started_at TEXT NOT NULL, ended_at TEXT, title TEXT, category_id TEXT, category TEXT, obs_scene TEXT ); CREATE INDEX idx_segments_stream ON stream_segments(stream_id, started_at); CREATE TABLE viewer_samples ( stream_id TEXT NOT NULL REFERENCES streams(id), ts TEXT NOT NULL, viewers INTEGER NOT NULL, PRIMARY KEY (stream_id, ts) ); CREATE TABLE users ( id TEXT PRIMARY KEY, login TEXT NOT NULL, display_name TEXT NOT NULL, first_seen_at TEXT NOT NULL, last_seen_at TEXT NOT NULL, streams_present INTEGER NOT NULL DEFAULT 0, streams_chatted INTEGER NOT NULL DEFAULT 0, message_count INTEGER NOT NULL DEFAULT 0, is_follower INTEGER NOT NULL DEFAULT 0, followed_at TEXT, is_sub INTEGER NOT NULL DEFAULT 0, sub_tier TEXT, points INTEGER NOT NULL DEFAULT 0, watch_minutes INTEGER NOT NULL DEFAULT 0, greeting TEXT, notes TEXT, pronouns TEXT, muted_greeting INTEGER NOT NULL DEFAULT 0 ); CREATE INDEX idx_users_login ON users(login); CREATE TABLE user_streams ( user_id TEXT NOT NULL REFERENCES users(id), stream_id TEXT NOT NULL REFERENCES streams(id), first_ts TEXT NOT NULL, last_ts TEXT NOT NULL, messages INTEGER NOT NULL DEFAULT 0, minutes INTEGER NOT NULL DEFAULT 0, PRIMARY KEY (user_id, stream_id) ); CREATE TABLE chat_messages ( id TEXT PRIMARY KEY, stream_id TEXT REFERENCES streams(id), ts TEXT NOT NULL, user_id TEXT NOT NULL REFERENCES users(id), text TEXT NOT NULL, emotes TEXT, is_first INTEGER NOT NULL DEFAULT 0, is_command INTEGER NOT NULL DEFAULT 0, bits INTEGER NOT NULL DEFAULT 0 ); CREATE INDEX idx_chat_stream_ts ON chat_messages(stream_id, ts); CREATE INDEX idx_chat_user ON chat_messages(user_id, ts); CREATE TABLE clips ( id TEXT PRIMARY KEY, twitch_clip_id TEXT, stream_id TEXT REFERENCES streams(id), created_at TEXT NOT NULL, trigger TEXT NOT NULL, trigger_score REAL, source TEXT NOT NULL, raw_path TEXT, vertical_path TEXT, subtitle_path TEXT, duration_s REAL, title TEXT, transcript TEXT, status TEXT NOT NULL, score REAL, uploaded_to TEXT ); CREATE INDEX idx_clips_stream ON clips(stream_id, created_at);