Prodotto Vendibile — InitiativeV3 Evidence Closure¶
Data analisi: 2026-04-26
Repo locale analizzato: /Users/enrico/dwh
Commit base locale prima della chiusura: 6ca43b6a
Ambiente locale validato: Docker demo http://localhost:8065
Suite di riferimento: product_ready / test_e2e/scripts/product_ready/product-ready-matrix.spec.js
1. Scopo operativo¶
Questo documento è la fonte di verità per dichiarare se InitiativeV3 ha raggiunto il minimo vendibile: il Direttore Generale di un tenant deve poter entrare, capire cosa fare, approvare, firmare, vedere blocchi reali, trovare documenti nell'Archivio Unico e scaricare un pacchetto evidenze verificabile.
La chiusura non si basa su testo decorativo nella UI. Ogni promessa 1–15 è accettata solo quando esistono quattro prove:
- UI visibile dal ruolo DG o Superadmin.
- Side effect su DB o stato applicativo.
- Documento, evidenza o pacchetto scaricabile.
- Test Playwright reale che percorre il flusso senza update DB diretto per le azioni utente critiche.
2. Mappa codice delle superfici vendibili¶
| Superficie | Route UI | Codice principale | Dati/evidenze |
|---|---|---|---|
| Attivazione tenant | /organizzazione/{tenant} |
internal/service/tenant_setup_activation_svc.go, internal/handler/view/tenant_setup_view.go |
aziendas, tenant_setup_cases, adm_utenzes, issuer SSI tenant |
| Control room DG | /organizzazione/{tenant} |
internal/service/dg_control_room_svc.go, internal/service/dg_document_projection_svc.go |
task, approvazioni, firme, eccezioni, documenti |
| Approvazioni AI | /ai/approvals, /ai/approvals/{run} |
internal/service/ai_approval_svc.go, internal/handler/view/ai_view.go |
task_runs, ai_approvals, ai_approval_events, ai_evidence_emissions |
| Firma regolatoria | /firme/pending, /goesign/ceremony/{session} |
internal/handler/signature_handler.go, internal/handler/goesign_handler.go, internal/service/signature_svc.go |
sig_records, GoeSign receipt, SSI evidence |
| Profilo firma DG | /profilo/identita-firma |
internal/handler/view/ssi_profile_view.go, GoeSign dwhmock |
passkey WebAuthn demo reale, signer readiness |
| Operazioni AML | /operazioni/aml, /operazioni/aml/{cod} |
internal/handler/view/aml_operation_intake_view.go, internal/service/aml_operation_* |
aml_operations, aml_operation_reports, checklist task |
| Blocco non difendibile | /operazioni/aml/{cod}/report |
internal/service/aml_operation_report_svc.go |
quality snapshot, stato bloccato, motivazione utente |
| Archivio Unico | /archivio, /archivio/{cod}/download |
internal/handler/view/archive_view.go, internal/service/archive_svc.go, internal/service/archive_index_svc.go |
archive_document_indexes, document_artifacts, audit download |
| Pacchetto evidenze | /archivio/consegna/{package}/download |
internal/service/archive_svc.go |
delivery_packages, ZIP con manifest.json, delivery-list.pdf, documenti |
| QA gate | qa-reports/{run}/gates/product-ready-gate.json |
test_e2e/lib/gate-writer.js, registry Playwright |
sidecar JSON con 15 righe PV-001..PV-015 |
3. Fix anti-slop implementati durante la chiusura¶
| Classe | Gap trovato | Remediation applicata |
|---|---|---|
| P0 | Attivazione tenant lasciava il DG senza issuer SSI attivo; la firma poteva fallire dopo setup apparentemente verde. | TenantSetupActivationService ora fail-closed se non riesce a predisporre issuer SSI tenant. |
| P0 | DG vedeva CTA firma ma non sempre una action GoeSign reale dalla proiezione documenti. | DGDocumentProjectionService espone SignatureURL e SignatureCode; la riga documento renderizza form reale verso /firme/cosign. |
| P0 | Passkey/WebAuthn registrata ma test non verificava stato readiness effettivo. | product_ready aspetta risposta reale /webauthn/finish e poi verifica profilo firma attivo. |
| P0 | Controfirma DG registrava la seconda riga ma il test non distingueva prima firma e controfirma. | Fixture demo realistica con prima firma evidenziata; test verifica anche riga dual_second, hash evidenza e verification status. |
| P0 | Pacchetto consegna creato ready ma download ZIP poteva tornare 404 per artifact con bucket/key legacy duplicati. |
ArchiveService.ResolveArtifactStoragePath normalizza bucket/key e ArchiveView.Download usa la stessa risoluzione. |
| P0 | Il helper E2E legacy poteva navigare fuori dalla cerimonia mentre la fetch /sign era ancora in corso, abortendo una firma reale e lasciando GoSign in stato parziale. |
test_e2e/helpers/auth.js e product_ready attendono esplicitamente risposta /sign e completamento business prima di proseguire. |
| P1 | Approvazione AI poteva procedere senza motivazione sostanziale. | AIApprovalService.ApproveRun richiede note non vuote; UI espone textarea obbligatoria con minlength. |
| P1 | Copy tecnico interno (CEB_CONTEXT) poteva arrivare nella UI tenant. |
Lista approvazioni sanitizza titoli/descrizioni con SanitizeTenantVisibleText. |
| P1 | RBAC API operazioni AML non allineato ai ruoli usati nei test reali. | Policy aggiunte per DG, RFA, RSOS, TEAM, IA read-only e SUPERADMIN su API AML operations. |
| P1 | SSI issuer validava solo identificatore interno e non document URL runtime. | Verifica SSI accetta issuer attivo per IssuerIdentifier o IssuerDocumentURL. |
| P1 | Produzione pubblicava offerte WaltID con metadata issuer host.docker.internal, non raggiungibile dal wallet container. |
Docker demo ora usa SSI_ISSUER_BASE_URL=http://waltid-issuer:7002, advertised issuer host waltid-issuer e normalizzazione runtime per verifica SSI. |
| P2 | Runner DB product-ready via SSH interpretava -F | come pipe shell remota. |
product_ready_db.js quota ogni argomento del comando remoto; fix di harness, non modifica test funzionali Raffaele. |
| P2 | Registry QA non riconosceva gate product-ready come suite tracciabile. | Registry gates.yaml, scenarios.yaml, registry-loader.js e playwright.config.js aggiornati. |
4. Matrice 1–15 con prove¶
Stato locale: verde su http://localhost:8065.
Ultimo full gate locale: product-ready-full-local-20260426T101419Z.
Ultima regressione locale product-ready dopo fix WaltID: product-ready-local-20260426T110931Z-waltid-service-host.
Sidecar locale full: qa-reports/product-ready-full-local-20260426T101419Z/gates/product-ready-gate.json.
Tenant generato dal full gate locale: TPV-PVM8QMNTAX.
Stato produzione: verde su https://aml.rivdigital.it.
Ultimo gate produzione: product-ready-prod-20260426T113805Z-final.
Sidecar produzione: qa-reports/product-ready-prod-20260426T113805Z-final/gates/product-ready-gate.json.
Tenant generato dal run produzione: TPV-PVP2JNF8OK.
| # | Promessa | Route UI | Servizio dati | Tabella/evidenza | Test automatico | Stato locale | Stato produzione | Gap residuo | Remediation |
|---|---|---|---|---|---|---|---|---|---|
| 1 | Superadmin attiva un tenant | /organizzazione/{tenant} |
TenantSetupCase activation + AdmUtenze creation |
aziendas, tenant_setup_cases, adm_utenzes |
PV-001 |
Green | Green | Nessuno | Nessuna |
| 2 | DG entra | /organizzazione/{tenant} |
LoginView.resolveLandingPath |
adm_utenzes, scs_sessions |
PV-002 |
Green | Green | Nessuno | Nessuna |
| 3 | DG vede control room chiara | /organizzazione/{tenant} |
DGControlRoomService.BuildControlRoom |
task, run, firme, limitazioni | PV-003 |
Green | Green | Nessuno | Nessuna |
| 4 | DG vede cosa deve fare | /organizzazione/{tenant}#dg-block-todo |
DGControlRoomService.aggregateToDo |
checklist_tasks |
PV-004 |
Green | Green | Nessuno | Nessuna |
| 5 | DG vede cosa deve approvare | /ai/approvals |
AIApprovalService.ListPendingApprovals |
task_runs, checklist_tasks, ai_action_plans |
PV-005 |
Green | Green | Nessuno | Nessuna |
| 6 | DG vede cosa deve firmare | /firme/pending |
SignatureView.Pending, DGDocumentProjectionService.aggregateSignatureFallback |
sig_records, adm_utenzes |
PV-006 |
Green | Green | Nessuno | Nessuna |
| 7 | DG vede operazioni critiche | /operazioni/aml/{cod} |
AMLOperationIntakeView, AMLOperationService |
aml_operations, checklist_tasks |
PV-007 |
Green | Green | Nessuno | Nessuna |
| 8 | DG vede errori motore AML | /organizzazione/{tenant}#dg-block-exception |
DGControlRoomService.aggregateExceptions |
checklist_tasks, setup_limitations |
PV-008 |
Green | Green | Nessuno | Nessuna |
| 9 | DG apre documenti reali | /archivio + download |
ArchiveView.List, archive download |
archive_document_indexes |
PV-009 |
Green | Green | Nessuno | Nessuna |
| 10 | DG firma documenti reali | /goesign/ceremony/{session} |
GoesignHandler, SignatureHandler.CompleteCosign |
sig_records, SSI evidence |
PV-010 |
Green | Green | Nessuno | Nessuna |
| 11 | DG approva output AI reali | /ai/approvals/{run} |
AIApprovalService.ApproveRun |
ai_approvals, ai_approval_events, ai_evidence_emissions, task_runs |
PV-011 |
Green | Green | Nessuno | Nessuna |
| 12 | DG non chiude lavoro non difendibile | /operazioni/aml/{cod}/report |
AMLOperationReportService.SignReport quality gate |
aml_operation_reports.quality_snapshot_json |
PV-012 |
Green | Green | Nessuno | Nessuna |
| 13 | DG trova tutto nell'Archivio Unico | /archivio |
ArchiveIndexService projection |
archive_document_indexes |
PV-013 |
Green | Green | Nessuno | Nessuna |
| 14 | Sistema produce prove | /archivio/consegna/{package} |
ArchiveService.CreateDeliveryPackage, BuildDeliveryPackageZip |
delivery_packages, ZIP evidence pack |
PV-014 |
Green | Green | Nessuno | Nessuna |
| 15 | Test dimostrano il flusso | qa-reports/{run}/gates/product-ready-gate.json |
Playwright serial suite | sidecar JSON | PV-015 |
Green | Green | Nessuno | Nessuna |
5. Comandi QA locale eseguiti¶
node -c test_e2e/helpers/product_ready_db.js
node -c test_e2e/scripts/product_ready/product-ready-matrix.spec.js
go test ./internal/service ./internal/handler/view ./internal/handler
go test ./...
mkdocs build --strict
docker compose -f docker-compose.demo.yml --env-file .env.demo build app
docker compose -f docker-compose.demo.yml --env-file .env.demo up -d app
BASE_URL=http://localhost:8065 QA_GATE_RUN_ID=product-ready-local-20260426T093629Z npx playwright test --project=product-ready --reporter=line
BASE_URL=http://localhost:8065 QA_GATE_RUN_ID=product-ready-local-20260426T093756Z-stable-1 npx playwright test --project=product-ready --reporter=line
BASE_URL=http://localhost:8065 QA_GATE_RUN_ID=product-ready-local-20260426T093911Z-stable-2 npx playwright test --project=product-ready --reporter=line
BASE_URL=http://localhost:8065 QA_GATE_RUN_ID=product-ready-local-20260426T094025Z-stable-3 npx playwright test --project=product-ready --reporter=line
BASE_URL=http://localhost:8065 QA_GATE_RUN_ID=product-ready-local-20260426T100844Z-post-auth npx playwright test --project=product-ready --reporter=line
BASE_URL=http://localhost:8065 QA_GATE_RUN_ID=product-ready-local-20260426T105644Z-issuer-internal-2 npx playwright test --project=product-ready --reporter=line
BASE_URL=http://localhost:8065 QA_GATE_RUN_ID=product-ready-local-20260426T110931Z-waltid-service-host npx playwright test --project=product-ready --reporter=line
QA_GATE_RUN_ID=product-ready-full-local-20260426T101419Z bash scripts/qa-gate.sh full
Risultato: product-ready verde dopo l'attesa esplicita di /sign; full gate locale verde con 9/9 gate, 74/74 scenari passati, 0 fallimenti, durata 348s.
6. Produzione¶
Produzione aggiornata e validata il 2026-04-26 contro https://aml.rivdigital.it.
| Campo | Valore |
|---|---|
| Commit produzione DWH | dc8d21129 |
| Commit produzione GoeSign | 42695e0 |
| Run ID produzione | product-ready-prod-20260426T113805Z-final |
| Sidecar produzione | qa-reports/product-ready-prod-20260426T113805Z-final/gates/product-ready-gate.json |
| Tenant prodotto dal test | TPV-PVP2JNF8OK |
| Health produzione | Green: database, filesystem, GoeSign, LLM glm-5, queue, reconciliation, worker leases |
| Docs pubbliche | Green: GET /docs/ HTTP 200 |
| Login pubblico | Green: GET /login HTTP 200 |
| WaltID issuer metadata | Green: issuer advertised http://waltid-issuer:7002/draft13 raggiungibile dal wallet container |
| Esito product_ready produzione | Green: 15/15 scenari passati, durata 88s |
Comando produzione eseguito:
BASE_URL=https://aml.rivdigital.it \
E2E_SUPERADMIN_PASSWORD=demo123 \
E2E_DB_SSH_HOST=root@188.166.125.26 \
E2E_DB_CONTAINER=dwh-demo-postgres-1 \
QA_GATE_ENV=production \
QA_GATE_SKIP_DOCKER_CHECK=1 \
QA_GATE_RUN_ID=product-ready-prod-20260426T113805Z-final \
npx playwright test --project=product-ready --reporter=line
7. Verdetto corrente¶
- Locale: vendibile rispetto alla matrice InitiativeV3 1–15.
- Produzione: vendibile rispetto alla matrice InitiativeV3 1–15, con product-ready verde su
https://aml.rivdigital.it. - Regola operativa: se un futuro gate produzione fallisce, il verdetto torna
Non vendibilee il fix va fatto nel prodotto o nella fixture demo reale, non indebolendo i test.