Registro controlli ricorrenti (owner/frequenza/metodo/controllo SoA-NIS2 collegato) + registro esecuzioni come EVIDENZA (data/esito/note) con avanzamento automatico della scadenza; da esito non conforme generazione NC o NC+azione correttiva (riuso non_conformities/capa_actions, nuova source 'monitoring'); report scheda+storico stampabile; scadenze nel Calendario unico. mig.057: periodic_controls + periodic_control_executions (FK CASCADE, UNIQUE (organization_id, code)). PeriodicControlController (slug periodic-controls) + controlli-periodici.html + CalendarController.srcPeriodicControls. Fix da flotta di verifica avversariale (9 finding confermati): - advance(): correzione overflow strtotime '+1 month' (31/01 -> 28/02, no salto mese) via DateTimeImmutable con clamp all'ultimo giorno valido (mensile/ trimestrale/semestrale/annuale); giornaliero/settimanale/custom invariati. - create(): retry-on-duplicate del codice CTL-NNN con UNIQUE (org_id, code). - update(): array_key_exists per azzerare owner_role_id / next_due_date. - delete(): rimossa cleanup morta su review_schedule (il calendario legge diretto). - CalendarController.srcReviewSchedule: esclude internal_audit/stakeholder_activity (gia' con sorgente diretta) -> fix doppia comparsa nel calendario. - calendario.html: TYPE_META 'periodic_control' (chip filtro + label + colore). Additivo. Cache-buster ?v= bump (sidebar) + sw cache nis2-shell-v1.23.0. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
66 lines
3.9 KiB
SQL
66 lines
3.9 KiB
SQL
-- =====================================================================
|
|
-- 057 — Controlli periodici (control monitoring con frequenza + esecuzioni + NC/AC)
|
|
-- =====================================================================
|
|
-- Registro dei controlli RICORRENTI con frequenza, owner e metodo; ogni
|
|
-- ESECUZIONE è registrata (data, esito, note, evidenze su evidence_files) =
|
|
-- EVIDENZA del monitoraggio periodico (ISO 27001 §9.1 / A.8.16; buona prassi,
|
|
-- non obbligo). Da un esito non conforme si genera una NC o un'azione correttiva
|
|
-- (riuso non_conformities/capa_actions). Distinto da: compliance_controls
|
|
-- (registro stato), review_schedule (cadenza generica), internal_audits (audit
|
|
-- puntuale). Vedi docs/DESIGN_CONTROLLI_PERIODICI.md.
|
|
--
|
|
-- Additivo, reversibile. Runner-safe: CREATE TABLE IF NOT EXISTS con FK inline;
|
|
-- l'ALTER dell'ENUM non_conformities.source è applicata dal seeder idempotente
|
|
-- (preservando i valori) — application/cli/seed_periodic_controls.php.
|
|
-- =====================================================================
|
|
|
|
CREATE TABLE IF NOT EXISTS periodic_controls (
|
|
id INT NOT NULL AUTO_INCREMENT,
|
|
organization_id INT NOT NULL,
|
|
code VARCHAR(20) NULL, -- CTL-NNN per org
|
|
title VARCHAR(255) NOT NULL,
|
|
description TEXT NULL,
|
|
category VARCHAR(100) NULL,
|
|
control_ref VARCHAR(32) NULL, -- codice SoA/NIS2 collegato (es. A.8.13)
|
|
owner_role_id INT NULL, -- responsabile (org_roles)
|
|
frequency ENUM('giornaliero','settimanale','mensile','trimestrale','semestrale','annuale','custom') NOT NULL DEFAULT 'mensile',
|
|
frequency_days INT NULL, -- usato se frequency='custom'
|
|
method TEXT NULL, -- metodologia di verifica
|
|
next_due_date DATE NULL,
|
|
last_executed_at DATE NULL,
|
|
status ENUM('active','suspended') NOT NULL DEFAULT 'active',
|
|
created_by INT NULL,
|
|
created_at DATETIME DEFAULT CURRENT_TIMESTAMP,
|
|
updated_at DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
|
|
PRIMARY KEY (id),
|
|
KEY idx_pctl_org (organization_id),
|
|
KEY idx_pctl_due (organization_id, next_due_date),
|
|
CONSTRAINT fk_pctl_org FOREIGN KEY (organization_id) REFERENCES organizations (id) ON DELETE CASCADE,
|
|
CONSTRAINT fk_pctl_role FOREIGN KEY (owner_role_id) REFERENCES org_roles (id) ON DELETE SET NULL,
|
|
CONSTRAINT fk_pctl_user FOREIGN KEY (created_by) REFERENCES users (id) ON DELETE SET NULL
|
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
|
|
|
|
CREATE TABLE IF NOT EXISTS periodic_control_executions (
|
|
id INT NOT NULL AUTO_INCREMENT,
|
|
control_id INT NOT NULL,
|
|
executed_at DATE NOT NULL,
|
|
executed_by INT NULL,
|
|
outcome ENUM('conforme','non_conforme','parziale','non_applicabile') NOT NULL DEFAULT 'conforme',
|
|
notes TEXT NULL,
|
|
ncr_id INT NULL, -- NC eventualmente generata
|
|
created_at DATETIME DEFAULT CURRENT_TIMESTAMP,
|
|
PRIMARY KEY (id),
|
|
KEY idx_pcexec_control (control_id),
|
|
CONSTRAINT fk_pcexec_control FOREIGN KEY (control_id) REFERENCES periodic_controls (id) ON DELETE CASCADE,
|
|
CONSTRAINT fk_pcexec_user FOREIGN KEY (executed_by) REFERENCES users (id) ON DELETE SET NULL,
|
|
CONSTRAINT fk_pcexec_ncr FOREIGN KEY (ncr_id) REFERENCES non_conformities (id) ON DELETE SET NULL
|
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
|
|
|
|
-- ALTER non_conformities.source: aggiunge 'monitoring' (eseguita dal seeder, idempotente).
|
|
-- ALTER TABLE non_conformities MODIFY COLUMN source ENUM('assessment','audit','incident','supplier_review','management_review','external_audit','monitoring','other') NOT NULL DEFAULT 'assessment';
|
|
|
|
-- ROLLBACK (manuale):
|
|
-- DROP TABLE IF EXISTS periodic_control_executions
|
|
-- DROP TABLE IF EXISTS periodic_controls
|
|
-- (non_conformities.source: rimuovere 'monitoring' dall'ENUM dopo aver riclassificato le NC relative)
|