-- Migration 001: Auth & Membership (von Mitai übernommen, angepasst) -- Erstellt: 2026-04-21 -- Beschreibung: Basis-Auth-System und Membership-Infrastruktur -- Profiles (Nutzer) CREATE TABLE profiles ( id SERIAL PRIMARY KEY, email VARCHAR(255) UNIQUE NOT NULL, pin_hash VARCHAR(255) NOT NULL, name VARCHAR(200), role VARCHAR(50) DEFAULT 'user', tier VARCHAR(50) DEFAULT 'free', email_verified BOOLEAN DEFAULT false, verification_token VARCHAR(255), created_at TIMESTAMP DEFAULT NOW(), updated_at TIMESTAMP DEFAULT NOW() ); CREATE INDEX idx_profiles_email ON profiles(email); CREATE INDEX idx_profiles_role ON profiles(role); -- Sessions (Auth-Tokens) CREATE TABLE sessions ( id SERIAL PRIMARY KEY, profile_id INT REFERENCES profiles(id) ON DELETE CASCADE, token VARCHAR(255) UNIQUE NOT NULL, created_at TIMESTAMP DEFAULT NOW(), expires_at TIMESTAMP NOT NULL ); CREATE INDEX idx_sessions_token ON sessions(token); CREATE INDEX idx_sessions_profile ON sessions(profile_id); -- Features (Feature-Definitionen) CREATE TABLE features ( id SERIAL PRIMARY KEY, name VARCHAR(100) UNIQUE NOT NULL, display_name VARCHAR(200), description TEXT, created_at TIMESTAMP DEFAULT NOW() ); -- Tier Limits (Limits pro Tier) CREATE TABLE tier_limits ( id SERIAL PRIMARY KEY, tier VARCHAR(50) NOT NULL, feature_id INT REFERENCES features(id), limit_value INT, -- -1 = unlimited created_at TIMESTAMP DEFAULT NOW(), UNIQUE(tier, feature_id) ); -- Subscriptions (Nutzer-Subscriptions) CREATE TABLE subscriptions ( id SERIAL PRIMARY KEY, profile_id INT REFERENCES profiles(id) ON DELETE CASCADE, tier VARCHAR(50) NOT NULL, status VARCHAR(50) DEFAULT 'trial', start_date DATE NOT NULL, end_date DATE, created_at TIMESTAMP DEFAULT NOW() ); CREATE INDEX idx_subscriptions_profile ON subscriptions(profile_id); -- User Feature Usage (Tracking) CREATE TABLE user_feature_usage ( id SERIAL PRIMARY KEY, profile_id INT REFERENCES profiles(id) ON DELETE CASCADE, feature_id INT REFERENCES features(id), usage_count INT DEFAULT 0, last_used TIMESTAMP, last_reset TIMESTAMP DEFAULT NOW(), created_at TIMESTAMP DEFAULT NOW(), UNIQUE(profile_id, feature_id) ); CREATE INDEX idx_usage_profile_feature ON user_feature_usage(profile_id, feature_id); -- Insert Default Features (Shinkan-spezifisch) INSERT INTO features (name, display_name, description) VALUES ('exercises', 'Übungen', 'Anzahl Übungen pro Verein'), ('training_units', 'Trainingseinheiten', 'Anzahl Trainingseinheiten pro Monat'), ('training_programs', 'Trainingsprogramme', 'Anzahl aktive Trainingsprogramme'), ('exercise_media', 'Medien-Uploads', 'Anzahl Medien-Uploads pro Monat'), ('wiki_import', 'MediaWiki-Import', 'Zugriff auf MediaWiki-Import'), ('ai_analysis', 'KI-Analysen', 'Anzahl KI-Analysen pro Monat (zukünftig)'); -- Insert Default Tier Limits -- Free Tier INSERT INTO tier_limits (tier, feature_id, limit_value) SELECT 'free', id, CASE WHEN name = 'exercises' THEN 50 WHEN name = 'training_units' THEN 20 WHEN name = 'training_programs' THEN 2 WHEN name = 'exercise_media' THEN 10 WHEN name = 'wiki_import' THEN 0 WHEN name = 'ai_analysis' THEN 0 END FROM features; -- Premium Tier INSERT INTO tier_limits (tier, feature_id, limit_value) SELECT 'premium', id, CASE WHEN name = 'exercises' THEN -1 -- unlimited WHEN name = 'training_units' THEN -1 WHEN name = 'training_programs' THEN -1 WHEN name = 'exercise_media' THEN 100 WHEN name = 'wiki_import' THEN 1 WHEN name = 'ai_analysis' THEN 50 END FROM features;