-- 020_rbac_and_profiles.sql -- Role Based Access Control and User Profiles (Aligned with ORIGIN) -- === ROLES === CREATE TABLE public.roles ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), name VARCHAR(50) NOT NULL, display_name VARCHAR(100) NOT NULL, description TEXT, is_system BOOLEAN DEFAULT false, is_active BOOLEAN DEFAULT true, created_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP, updated_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP, CONSTRAINT uni_roles_name UNIQUE (name) ); -- === PERMISSIONS === CREATE TABLE public.permissions ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), name VARCHAR(100) NOT NULL, resource VARCHAR(50) NOT NULL, action VARCHAR(50) NOT NULL, description TEXT, created_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP, CONSTRAINT uni_permissions_name UNIQUE (name) ); -- === USER ROLES (Assignments) === CREATE TABLE public.user_roles ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), user_id UUID NOT NULL REFERENCES public.users(id) ON DELETE CASCADE, role_id UUID REFERENCES public.roles(id) ON DELETE SET NULL, assigned_by UUID REFERENCES public.users(id) ON DELETE SET NULL, -- Origin Alignment (adding missing fields) role VARCHAR(50) NOT NULL, -- kept for redundancy/legacy or simple checks verified BOOLEAN NOT NULL DEFAULT false, verified_at TIMESTAMPTZ, verified_by UUID REFERENCES public.users(id), -- Legacy assigned_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP, expires_at TIMESTAMPTZ, is_active BOOLEAN DEFAULT true, created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(), CONSTRAINT uq_user_roles_user_role UNIQUE (user_id, role) ); CREATE INDEX idx_user_roles_user_id ON public.user_roles(user_id); CREATE INDEX idx_user_roles_role_id ON public.user_roles(role_id); CREATE INDEX idx_user_roles_role ON public.user_roles(role); -- === ROLE PERMISSIONS (Mapping) === CREATE TABLE public.role_permissions ( role_id UUID NOT NULL REFERENCES public.roles(id) ON DELETE CASCADE, permission_id UUID NOT NULL REFERENCES public.permissions(id) ON DELETE CASCADE, CONSTRAINT pk_role_permissions PRIMARY KEY (role_id, permission_id) ); CREATE INDEX idx_role_permissions_role_id ON public.role_permissions(role_id); CREATE INDEX idx_role_permissions_permission_id ON public.role_permissions(permission_id); -- === USER PROFILES (Origin Standard) === CREATE TABLE public.user_profiles ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), user_id UUID NOT NULL REFERENCES public.users(id) ON DELETE CASCADE, -- Profile Info bio TEXT, tagline VARCHAR(255), location VARCHAR(255), website_url VARCHAR(500), -- Personal Info birthdate DATE, gender VARCHAR(50), -- Media avatar_url TEXT, banner_url TEXT, -- Preferences language VARCHAR(5) DEFAULT 'en', timezone VARCHAR(50) DEFAULT 'UTC', theme VARCHAR(20) DEFAULT 'auto', -- Privacy profile_visibility public.visibility NOT NULL DEFAULT 'public', show_email BOOLEAN NOT NULL DEFAULT false, show_location BOOLEAN NOT NULL DEFAULT true, -- Counts follower_count INTEGER NOT NULL DEFAULT 0, following_count INTEGER NOT NULL DEFAULT 0, track_count INTEGER NOT NULL DEFAULT 0, playlist_count INTEGER NOT NULL DEFAULT 0, -- Timestamps created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(), updated_at TIMESTAMPTZ NOT NULL DEFAULT NOW(), CONSTRAINT uq_user_profiles_user_id UNIQUE (user_id) ); CREATE INDEX idx_user_profiles_location ON public.user_profiles(location) WHERE location IS NOT NULL; -- === USER SETTINGS (Origin Standard) === CREATE TABLE public.user_settings ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), user_id UUID NOT NULL REFERENCES public.users(id) ON DELETE CASCADE, -- Notification Preferences email_notifications BOOLEAN NOT NULL DEFAULT true, push_notifications BOOLEAN NOT NULL DEFAULT true, browser_notifications BOOLEAN NOT NULL DEFAULT true, -- Email Notification Types email_on_follow BOOLEAN NOT NULL DEFAULT true, email_on_like BOOLEAN NOT NULL DEFAULT true, email_on_comment BOOLEAN NOT NULL DEFAULT true, email_on_message BOOLEAN NOT NULL DEFAULT true, email_on_mention BOOLEAN NOT NULL DEFAULT true, email_marketing BOOLEAN NOT NULL DEFAULT false, -- Privacy allow_search_indexing BOOLEAN NOT NULL DEFAULT true, show_activity BOOLEAN NOT NULL DEFAULT true, -- Content explicit_content BOOLEAN NOT NULL DEFAULT false, autoplay BOOLEAN NOT NULL DEFAULT true, -- Timestamps created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(), updated_at TIMESTAMPTZ NOT NULL DEFAULT NOW(), CONSTRAINT uq_user_settings_user_id UNIQUE (user_id) ); -- === ADMIN SETTINGS (Legacy) === CREATE TABLE public.admin_settings ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), key VARCHAR(255) NOT NULL, value TEXT, type VARCHAR(50), description TEXT, category VARCHAR(50), is_public BOOLEAN DEFAULT false, updated_by UUID REFERENCES public.users(id) ON DELETE SET NULL, updated_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP, CONSTRAINT uq_admin_settings_key UNIQUE (key) );