-- RLS Policies and Seeding Script for Hoteles Estelar Variable Remuneration System SET app.current_user_role = 'admin'; -- ========================================== -- 0. TEMPORARILY DISABLE RLS FOR SEEDING -- ========================================== ALTER TABLE "regions" DISABLE ROW LEVEL SECURITY; ALTER TABLE "hotels" DISABLE ROW LEVEL SECURITY; ALTER TABLE "users" DISABLE ROW LEVEL SECURITY; ALTER TABLE "goals" DISABLE ROW LEVEL SECURITY; ALTER TABLE "sales_results" DISABLE ROW LEVEL SECURITY; ALTER TABLE "settlements" DISABLE ROW LEVEL SECURITY; ALTER TABLE "audit_logs" DISABLE ROW LEVEL SECURITY; ALTER TABLE "compensation_plans" DISABLE ROW LEVEL SECURITY; ALTER TABLE "calculation_rules" DISABLE ROW LEVEL SECURITY; -- ========================================== -- 1. CLEAN UP OLD POLICIES -- ========================================== DROP POLICY IF EXISTS audit_logs_insert_policy ON "audit_logs"; DROP POLICY IF EXISTS audit_logs_select_policy ON "audit_logs"; DROP POLICY IF EXISTS regions_select_policy ON "regions"; DROP POLICY IF EXISTS regions_modify_policy ON "regions"; DROP POLICY IF EXISTS hotels_select_policy ON "hotels"; DROP POLICY IF EXISTS hotels_modify_policy ON "hotels"; DROP POLICY IF EXISTS users_select_policy ON "users"; DROP POLICY IF EXISTS users_modify_policy ON "users"; DROP POLICY IF EXISTS goals_select_policy ON "goals"; DROP POLICY IF EXISTS goals_modify_policy ON "goals"; DROP POLICY IF EXISTS sales_results_select_policy ON "sales_results"; DROP POLICY IF EXISTS sales_results_modify_policy ON "sales_results"; DROP POLICY IF EXISTS settlements_select_policy ON "settlements"; DROP POLICY IF EXISTS settlements_modify_policy ON "settlements"; DROP POLICY IF EXISTS plans_select_policy ON "compensation_plans"; DROP POLICY IF EXISTS plans_modify_policy ON "compensation_plans"; DROP POLICY IF EXISTS rules_select_policy ON "calculation_rules"; DROP POLICY IF EXISTS rules_modify_policy ON "calculation_rules"; -- ========================================== -- 2. SEED DATA -- ========================================== -- Seed Regions INSERT INTO "regions" ("name", "code") VALUES ('Bogotá', 'BOG'), ('Antioquia', 'ANT'), ('Caribe', 'CAR') ON CONFLICT ("code") DO NOTHING; -- Seed Hotels INSERT INTO "hotels" ("name", "code", "region_id", "status") VALUES ('Estelar Parque de la 93', 'EST-P93', (SELECT id FROM regions WHERE code = 'BOG'), 'ACTIVE'), ('Estelar Medellin', 'EST-MDE', (SELECT id FROM regions WHERE code = 'ANT'), 'ACTIVE'), ('Estelar Cartagena', 'EST-CTG', (SELECT id FROM regions WHERE code = 'CAR'), 'ACTIVE') ON CONFLICT ("code") DO NOTHING; -- Seed Users -- password_hash is bcrypt hash of 'password123' INSERT INTO "users" ("username", "email", "password_hash", "role", "hotel_id", "area", "status", "created_at") VALUES ('admin', 'admin@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'admin', (SELECT id FROM hotels WHERE code = 'EST-P93'), 'Sistemas', 'ACTIVE', NOW()), ('director', 'director@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'director', (SELECT id FROM hotels WHERE code = 'EST-P93'), 'Comercial', 'ACTIVE', NOW()), ('gerente_mde', 'gerente.mde@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'hotel_manager', (SELECT id FROM hotels WHERE code = 'EST-MDE'), 'Administracion', 'ACTIVE', NOW()), ('gerente_ctg', 'gerente.ctg@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'hotel_manager', (SELECT id FROM hotels WHERE code = 'EST-CTG'), 'Administracion', 'ACTIVE', NOW()), ('lider_ctg', 'lider.ctg@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'commercial_leader', (SELECT id FROM hotels WHERE code = 'EST-CTG'), 'Ventas', 'ACTIVE', NOW()), ('lider_mde', 'lider.mde@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'commercial_leader', (SELECT id FROM hotels WHERE code = 'EST-MDE'), 'Ventas', 'ACTIVE', NOW()), ('analista', 'analista@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'analyst', (SELECT id FROM hotels WHERE code = 'EST-P93'), 'Finanzas', 'ACTIVE', NOW()), ('consulta', 'consulta@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'auditor', (SELECT id FROM hotels WHERE code = 'EST-P93'), 'Auditoria', 'ACTIVE', NOW()), ('colaborador_mde', 'colaborador.mde@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'collaborator', (SELECT id FROM hotels WHERE code = 'EST-MDE'), 'Ventas', 'ACTIVE', NOW()), ('colaborador_ctg', 'colaborador.ctg@estelar.com', '$2b$10$lRn/GrwzaEGxWqqQGGz0f.44nBywObKkGWRajlxWeDGZ3o4f7ayjy', 'collaborator', (SELECT id FROM hotels WHERE code = 'EST-CTG'), 'Ventas', 'ACTIVE', NOW()) ON CONFLICT ("username") DO UPDATE SET role = EXCLUDED.role; -- ========================================== -- 3. ENABLE ROW-LEVEL SECURITY -- ========================================== ALTER TABLE "regions" ENABLE ROW LEVEL SECURITY; ALTER TABLE "hotels" ENABLE ROW LEVEL SECURITY; ALTER TABLE "users" ENABLE ROW LEVEL SECURITY; ALTER TABLE "goals" ENABLE ROW LEVEL SECURITY; ALTER TABLE "sales_results" ENABLE ROW LEVEL SECURITY; ALTER TABLE "settlements" ENABLE ROW LEVEL SECURITY; ALTER TABLE "audit_logs" ENABLE ROW LEVEL SECURITY; ALTER TABLE "compensation_plans" ENABLE ROW LEVEL SECURITY; ALTER TABLE "calculation_rules" ENABLE ROW LEVEL SECURITY; ALTER TABLE "regions" FORCE ROW LEVEL SECURITY; ALTER TABLE "hotels" FORCE ROW LEVEL SECURITY; ALTER TABLE "users" FORCE ROW LEVEL SECURITY; ALTER TABLE "goals" FORCE ROW LEVEL SECURITY; ALTER TABLE "sales_results" FORCE ROW LEVEL SECURITY; ALTER TABLE "settlements" FORCE ROW LEVEL SECURITY; ALTER TABLE "audit_logs" FORCE ROW LEVEL SECURITY; ALTER TABLE "compensation_plans" FORCE ROW LEVEL SECURITY; ALTER TABLE "calculation_rules" FORCE ROW LEVEL SECURITY; -- ========================================== -- 4. CREATE RLS POLICIES -- ========================================== -- A. Audit Logs Policies (Insert allowed for all, Select only for Admin/Analista, No Updates/Deletes) CREATE POLICY audit_logs_insert_policy ON "audit_logs" FOR INSERT WITH CHECK (true); CREATE POLICY audit_logs_select_policy ON "audit_logs" FOR SELECT USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst') OR user_id = NULLIF(current_setting('app.current_user_id', true), '')::integer ); -- B. Regions Policies CREATE POLICY regions_select_policy ON "regions" FOR SELECT USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst', 'director') OR id = NULLIF(current_setting('app.current_region_id', true), '')::integer ); CREATE POLICY regions_modify_policy ON "regions" FOR ALL USING (current_setting('app.current_user_role', true) IN ('admin', 'director')); -- C. Hotels Policies CREATE POLICY hotels_select_policy ON "hotels" FOR SELECT USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst', 'director') OR region_id = NULLIF(current_setting('app.current_region_id', true), '')::integer OR id = NULLIF(current_setting('app.current_hotel_id', true), '')::integer ); CREATE POLICY hotels_modify_policy ON "hotels" FOR ALL USING (current_setting('app.current_user_role', true) IN ('admin', 'director')); -- D. Users Policies CREATE POLICY users_select_policy ON "users" FOR SELECT USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst', 'director') OR ( current_setting('app.current_user_role', true) = 'hotel_manager' AND hotel_id = NULLIF(current_setting('app.current_hotel_id', true), '')::integer ) OR ( current_setting('app.current_user_role', true) = 'commercial_leader' AND hotel_id IN (SELECT id FROM hotels WHERE region_id = NULLIF(current_setting('app.current_region_id', true), '')::integer) ) OR id = NULLIF(current_setting('app.current_user_id', true), '')::integer ); CREATE POLICY users_modify_policy ON "users" FOR ALL USING (current_setting('app.current_user_role', true) = 'admin'); -- E. Goals Policies CREATE POLICY goals_select_policy ON "goals" FOR SELECT USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst', 'director') OR target_id = NULLIF(current_setting('app.current_user_id', true), '')::integer OR target_id IN ( SELECT u.id FROM users u WHERE u.hotel_id = NULLIF(current_setting('app.current_hotel_id', true), '')::integer ) OR target_id IN ( SELECT u.id FROM users u JOIN hotels h ON u.hotel_id = h.id WHERE h.region_id = NULLIF(current_setting('app.current_region_id', true), '')::integer ) ); CREATE POLICY goals_modify_policy ON "goals" FOR ALL USING (current_setting('app.current_user_role', true) IN ('admin', 'director')); -- F. Sales Results Policies CREATE POLICY sales_results_select_policy ON "sales_results" FOR SELECT USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst', 'director') OR user_id = NULLIF(current_setting('app.current_user_id', true), '')::integer OR hotel_id = NULLIF(current_setting('app.current_hotel_id', true), '')::integer OR hotel_id IN ( SELECT id FROM hotels WHERE region_id = NULLIF(current_setting('app.current_region_id', true), '')::integer ) ); CREATE POLICY sales_results_modify_policy ON "sales_results" FOR ALL USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst') OR ( current_setting('app.current_user_role', true) = 'commercial_leader' AND hotel_id IN ( SELECT id FROM hotels WHERE region_id = NULLIF(current_setting('app.current_region_id', true), '')::integer ) ) ); -- G. Settlements Policies CREATE POLICY settlements_select_policy ON "settlements" FOR SELECT USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst', 'director') OR user_id = NULLIF(current_setting('app.current_user_id', true), '')::integer OR user_id IN ( SELECT u.id FROM users u WHERE u.hotel_id = NULLIF(current_setting('app.current_hotel_id', true), '')::integer ) OR user_id IN ( SELECT u.id FROM users u JOIN hotels h ON u.hotel_id = h.id WHERE h.region_id = NULLIF(current_setting('app.current_region_id', true), '')::integer ) ); CREATE POLICY settlements_modify_policy ON "settlements" FOR ALL USING ( current_setting('app.current_user_role', true) IN ('admin', 'analyst') OR ( current_setting('app.current_user_role', true) = 'commercial_leader' AND user_id IN ( SELECT u.id FROM users u JOIN hotels h ON u.hotel_id = h.id WHERE h.region_id = NULLIF(current_setting('app.current_region_id', true), '')::integer ) ) ); -- H. Compensation Plans Policies CREATE POLICY plans_select_policy ON "compensation_plans" FOR SELECT USING (true); CREATE POLICY plans_modify_policy ON "compensation_plans" FOR ALL USING (current_setting('app.current_user_role', true) IN ('admin', 'director', 'analyst')); -- I. Calculation Rules Policies CREATE POLICY rules_select_policy ON "calculation_rules" FOR SELECT USING (true); CREATE POLICY rules_modify_policy ON "calculation_rules" FOR ALL USING (current_setting('app.current_user_role', true) IN ('admin', 'director', 'analyst'));