From bebd3c74da282d76997161892185e43876abb17f Mon Sep 17 00:00:00 2001 From: Julien Martin Date: Sun, 30 Nov 2025 15:34:28 +0100 Subject: [PATCH] feat(bdd): ajout tables documents_legaux et acceptations_documents #7 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Création table documents_legaux (versioning + hash SHA-256) - Création table acceptations_documents (traçabilité RGPD) - Ajout colonnes dans utilisateurs (cgu_version_acceptee, etc.) - Seed documents génériques v1 (CGU + Privacy) - Index pour performance Réf: docs/22_DOCUMENTS-LEGAUX.md --- database/BDD.sql | 55 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 55 insertions(+) diff --git a/database/BDD.sql b/database/BDD.sql index 920aae3..c5e7c5a 100644 --- a/database/BDD.sql +++ b/database/BDD.sql @@ -287,3 +287,58 @@ INSERT INTO configuration (cle, valeur, type, categorie, description) VALUES ('jwt_expiry_hours', '24', 'number', 'security', 'Durée de validité des sessions JWT (en heures)'), ('max_upload_size_mb', '5', 'number', 'security', 'Taille maximale des fichiers uploadés (en MB)'), ('bcrypt_rounds', '12', 'number', 'security', 'Nombre de rounds bcrypt pour le hachage des mots de passe'); + +-- ========================================================== +-- Table : documents_legaux +-- ========================================================== +CREATE TABLE documents_legaux ( + id UUID PRIMARY KEY DEFAULT gen_random_uuid(), + type VARCHAR(50) NOT NULL, -- 'cgu' ou 'privacy' + version INTEGER NOT NULL, -- Numéro de version (auto-incrémenté) + fichier_nom VARCHAR(255) NOT NULL, -- Nom original du fichier + fichier_path VARCHAR(500) NOT NULL, -- Chemin de stockage + fichier_hash VARCHAR(64) NOT NULL, -- Hash SHA-256 pour intégrité + actif BOOLEAN DEFAULT false, -- Version actuellement active + televerse_par UUID REFERENCES utilisateurs(id), -- Qui a uploadé + televerse_le TIMESTAMPTZ DEFAULT now(), -- Date d'upload + active_le TIMESTAMPTZ, -- Date d'activation + UNIQUE(type, version) -- Pas de doublon version +); + +-- Index pour performance +CREATE INDEX idx_documents_legaux_type_actif ON documents_legaux(type, actif); +CREATE INDEX idx_documents_legaux_version ON documents_legaux(type, version DESC); + +-- ========================================================== +-- Table : acceptations_documents +-- ========================================================== +CREATE TABLE acceptations_documents ( + id UUID PRIMARY KEY DEFAULT gen_random_uuid(), + id_utilisateur UUID REFERENCES utilisateurs(id) ON DELETE CASCADE, + id_document UUID REFERENCES documents_legaux(id), + type_document VARCHAR(50) NOT NULL, -- 'cgu' ou 'privacy' + version_document INTEGER NOT NULL, -- Version acceptée + accepte_le TIMESTAMPTZ DEFAULT now(), -- Date d'acceptation + ip_address INET, -- IP de l'utilisateur (RGPD) + user_agent TEXT -- Navigateur (preuve) +); + +-- Index pour performance +CREATE INDEX idx_acceptations_utilisateur ON acceptations_documents(id_utilisateur); +CREATE INDEX idx_acceptations_document ON acceptations_documents(id_document); + +-- ========================================================== +-- Modification Table : utilisateurs (ajout colonnes documents) +-- ========================================================== +ALTER TABLE utilisateurs + ADD COLUMN IF NOT EXISTS cgu_version_acceptee INTEGER, + ADD COLUMN IF NOT EXISTS cgu_acceptee_le TIMESTAMPTZ, + ADD COLUMN IF NOT EXISTS privacy_version_acceptee INTEGER, + ADD COLUMN IF NOT EXISTS privacy_acceptee_le TIMESTAMPTZ; + +-- ========================================================== +-- Seed : Documents légaux génériques v1 +-- ========================================================== +INSERT INTO documents_legaux (type, version, fichier_nom, fichier_path, fichier_hash, actif, televerse_le, active_le) VALUES +('cgu', 1, 'cgu_v1_default.pdf', '/documents/legaux/cgu_v1_default.pdf', 'a3f8b2c4d5e6f7a8b9c0d1e2f3a4b5c6d7e8f9a0b1c2d3e4f5a6b7c8d9e0f1a2', true, now(), now()), +('privacy', 1, 'privacy_v1_default.pdf', '/documents/legaux/privacy_v1_default.pdf', 'b4f9c3d6e7f8a9b0c1d2e3f4a5b6c7d8e9f0a1b2c3d4e5f6a7b8c9d0e1f2a3b4', true, now(), now());