[FEAT] Allineamento NIS2 ↔ TRPG (Fasi 1-5): SSO + Sessions + Reset + Impersonate + Branding
Implementazione completa del progetto allineamento alla suite Evix (TRPG/lg231),
basato sul doc canonico docs/GAP_TRPG_NIS2_ALIGNMENT.md (5 fasi, 18 gap).
Version 1.0.0 → 1.5.0
Fase 1 — SSO Federation (v1.1.0)
- Migration 015_sso_columns: users.sso_identity_id + password_version
- application/services/SsoHelper.php (client SSO dual-mode, cURL nativo, zero deps)
- AuthController::login() + changePassword() conditional SSO (SSO_MODE=local default)
Fase 2 — Multi-device Sessions (v1.2.0)
- Migration 016_active_sessions: tabella + refresh_tokens.session_jti
- BaseController::requireAuth() verifica jti + last_activity throttle + parseDeviceLabel
- login() genera jti, logout/changePassword revoca selettiva
- GET/DELETE /auth/sessions[/{id}]
- UI settings.html tab Sicurezza con lista device + revoca
Fase 3 — Password Reset + Tenant Switcher (v1.3.0)
- Migration 017_password_reset_tokens (TTL 30min, single-use)
- POST /auth/forgot-password (risposta opaca) + reset-password
- Pagine forgot-password.html + reset-password.html (con strength bar)
- EmailService::sendPasswordReset
- POST /auth/switchContext con rotazione JWT + organization_id claim
- Dropdown tenant in sidebar esposto a tutti gli utenti con ≥2 org
Fase 4 — Impersonate + Preferences + Versioning UI (v1.4.0)
- POST /auth/impersonate (super_admin o consulente stesso firm, TTL 1h, audit)
- Migration 018_user_preferences: users.theme/timezone/notif_email/notif_inapp
- GET/PUT /auth/preferences
- Sidebar footer mostra versione + changelog modal su click
Fase 5 — Branding white-label + Auth-gate (v1.5.0)
- Migration 019_firm_branding (logo/colori/brand_name per consulting firm)
- BrandingController GET /branding/current (auth opzionale) + PUT
- common.js auto-applica CSS variables al boot
- public/js/auth-gate.js (gate password client-side per docs riservati, da TRPG)
Skip motivati:
- G15 demo login: simulator esistenti coprono
- G18 refactor controllers: rinviato (~5gg, valore tecnico solo)
Cron sync SSO: AgileHub Ticket #220 aperto a team AGILEHUB per estendere
sso-password-sync.sh al DB nis2_agile_db. Prerequisito per switch SSO_MODE=dual.
Backup files: tutti i file modificati hanno .bak.pre-{fase}-{ts} sia in DEV
sia in /var/www/nis2-agile/.backups/ su Hetzner (rollback ready).
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 4.7
parent
c37423f900
commit
e4f9e9179e
@@ -107,6 +107,8 @@ $controllerMap = [
|
||||
'contact' => 'ContactController', // legacy
|
||||
'mktg-lead' => 'MktgLeadController', // standard condiviso TRPG/NIS2
|
||||
'feedback' => 'FeedbackController', // segnalazioni & risoluzione AI
|
||||
'knowledgebase' => 'KnowledgeBaseController', // KB multi-livello (Migration 012-014)
|
||||
'branding' => 'BrandingController', // White-label firm (Fase 5 / G16)
|
||||
];
|
||||
|
||||
if (!isset($controllerMap[$controllerName])) {
|
||||
@@ -154,6 +156,20 @@ $actionMap = [
|
||||
'PUT:profile' => 'updateProfile',
|
||||
'POST:changePassword' => 'changePassword',
|
||||
'POST:validateInvite' => 'validateInvite', // valida invite_token (no auth)
|
||||
// Multi-device sessions (Fase 2 / G06)
|
||||
'GET:sessions' => 'listSessions',
|
||||
'DELETE:sessions/{id}' => 'revokeSession',
|
||||
'DELETE:sessions' => 'revokeAllSessions',
|
||||
// Password reset (Fase 3 / G08, no auth)
|
||||
'POST:forgotPassword' => 'forgotPassword',
|
||||
'POST:resetPassword' => 'resetPassword',
|
||||
// Context switch (Fase 3 / G09)
|
||||
'POST:switchContext' => 'switchContext',
|
||||
// Impersonate (Fase 4 / G11)
|
||||
'POST:impersonate' => 'impersonate',
|
||||
// Preferences (Fase 4 / G12)
|
||||
'GET:preferences' => 'getPreferences',
|
||||
'PUT:preferences' => 'updatePreferences',
|
||||
],
|
||||
|
||||
// ── OrganizationController ──────────────────────
|
||||
@@ -399,6 +415,21 @@ $actionMap = [
|
||||
'PUT:{id}' => 'update',
|
||||
'POST:{id}/resolve' => 'resolve',
|
||||
],
|
||||
|
||||
// ── KnowledgeBaseController — KB multi-livello (Migration 012-014) ──
|
||||
'knowledgebase' => [
|
||||
'POST:ingest' => 'ingest',
|
||||
'GET:list' => 'list',
|
||||
'GET:firmOrgs' => 'firmOrgs',
|
||||
'POST:search' => 'search',
|
||||
'DELETE:{id}' => 'delete',
|
||||
],
|
||||
|
||||
// ── BrandingController — White-label firm (Fase 5 / G16) ──
|
||||
'branding' => [
|
||||
'GET:current' => 'getCurrent',
|
||||
'PUT:index' => 'update',
|
||||
],
|
||||
];
|
||||
|
||||
// ═══════════════════════════════════════════════════════════════════════════
|
||||
|
||||
Reference in New Issue
Block a user