# NOVA InvoiceSuite - Guida Utente Completa

## Indice

1. [Panoramica della Piattaforma](#1-panoramica-della-piattaforma)
2. [Architettura Applicativa](#2-architettura-applicativa)
3. [Ruoli e Autorizzazioni](#3-ruoli-e-autorizzazioni)
4. [Navigazione nel Fiori Launchpad](#4-navigazione-nel-fiori-launchpad)
5. [Il Processo di Elaborazione Fatture in 6 Fasi](#5-il-processo-di-elaborazione-fatture-in-6-fasi)
6. [Manuale App: Fatture Passive (Gestione Operativa)](#6-manuale-app-fatture-passive)
7. [Manuale App: Panoramica (Dashboard KPI)](#7-manuale-app-panoramica)
8. [Manuale App: Estrazione AI (DOX)](#8-manuale-app-estrazione-ai)
9. [Manuale App: Analisi Strategica](#9-manuale-app-analisi-strategica)
10. [Manuale App: Regole & Workflow (Governance)](#10-manuale-app-regole--workflow)
11. [Manuale App: Configurazione (Setup)](#11-manuale-app-configurazione)
12. [Manuale App: Operazioni (Ops)](#12-manuale-app-operazioni)
13. [Manuale App: Approvazioni (Coda Approver)](#13-manuale-app-approvazioni)
14. [Manuale App: Platform Admin (SuperAdmin)](#14-manuale-app-platform-admin)
15. [Glossario](#15-glossario)

---

## 1. Panoramica della Piattaforma

NOVA InvoiceSuite è una piattaforma di gestione fatture passive (Vendor Invoice Management) costruita su SAP BTP con tecnologia SAP CAP e frontend Fiori Elements V4. Gestisce l'intero ciclo di vita delle fatture elettroniche italiane (FatturaPA/SDI) dalla ricezione fino all'archiviazione sostitutiva.

### Canali di Acquisizione Supportati

| Canale | Descrizione |
|--------|-------------|
| **SDI** | Sistema di Interscambio - canale ufficiale fatturazione elettronica italiana |
| **DOX** | SAP Document Information Extraction - estrazione AI da PDF/immagini |
| **EDI** | Electronic Data Interchange - scambio strutturato B2B |
| **EMAIL** | Acquisizione da casella PEC/email dedicata |
| **WEBHOOK** | Integrazione push da sistemi esterni |
| **MANUAL** | Inserimento manuale per casistiche legacy |

### Tipologie di Fattura

| Tipo | Descrizione | Flusso |
|------|-------------|--------|
| **PO** | Fattura con riferimento Ordine di Acquisto | Matching PO + 3-Way Match |
| **NON_PO** | Fattura senza ordine (servizi, utenze, etc.) | Allocazione costi manuale/automatica |
| **MIXED** | Fattura con righe PO e righe libere | Flusso ibrido |

---

## 2. Architettura Applicativa

La suite è composta da **9 applicazioni Fiori Elements**: 8 condividono il servizio OData V4 `OrchestratorService`, la nona (`Platform Admin`) è esposta sul service dedicato `/platform-admin` (SuperAdmin-only). Platform è dentro il conteggio di 9, non in aggiunta:

```
Fiori Launchpad (FLP)
  |
  +-- Panoramica ............. Dashboard KPI e accesso rapido
  +-- Fatture Passive ........ Elaborazione operativa (app principale)
  +-- Estrazione AI .......... Cattura documenti con DOX
  +-- Analisi Strategica ..... KPI C-Level e trend
  +-- Regole & Workflow ...... Configurazione approvazioni
  +-- Configurazione ......... Parametri sistema e integrazioni
  +-- Operazioni ............. Monitoraggio piattaforma (12 sezioni inclusa Billing Snapshots)
  +-- Approvazioni ........... Worklist dedicata Approver / ApproverManager
  +-- Platform Admin ......... Tooling SuperAdmin (Certificate Mgr + MinIO/S3 Browser)
```

> NOTA: la sezione *Billing Snapshots* — descritta in versioni precedenti come app standalone "Billing & Metering" — è ora una sub-sezione della app **Operazioni** (Ops). Le entità `BillingSnapshots`, `BillingTotalsMonthly` rimangono invariate; cambia solo il punto di accesso UI.

**Backend:** SAP CAP (Node.js) su SAP BTP, con connessione a SAP S/4HANA Cloud via OData per Business Partner, Purchase Order, Supplier Invoice, Electronic Document File.

---

## 3. Ruoli e Autorizzazioni

I ruoli canonici sono **15** (non 4): sono definiti in `xs-security.json`, nel realm Keycloak e nei gruppi
IAS, ed enforced via `@restrict` in `srv/services-auth.cds`.

| Ruolo | Descrizione | Capacità |
|-------|-------------|----------|
| **Viewer** | Consultazione | Lettura fatture e analytics, limitata alla propria società |
| **Worker** | Operatore | Viewer + azioni operative (risolvi BP, verifica duplicati, analisi rischio, validazione fiscale, match PO, conferma fase, gestione eccezioni) |
| **Approver** | Approvatore | Viewer + approva / rifiuta / delega / escala nel workflow |
| **ApproverManager** | Approvatore manager | Approver + soglia superiore via `ApprovalRule.ApproverRole` |
| **ApproverTax** | Approvatore fiscale | Approver + override su eccezioni fiscali |
| **ApproverSenior** | Approvatore senior | Approver + soglia superiore |
| **ApproverDirector** | Direttore | Approver + soglia superiore |
| **ApproverCFO** | CFO | Approver + soglia massima |
| **PostingOfficer** | Addetto registrazione | `postInvoice` / `reverseInvoice` / `archiveInvoice`. **In mutex SoD con Approver** |
| **Admin** | Amministratore | Accesso completo **sulla propria società** (`CompanyCode = $user.CompanyCode`), configurazione, master data, trasporto |
| **AdminConfig** | Amministratore di configurazione | Solo configurazione e master data — NESSUNA azione di lifecycle o operativa |
| **OperationalAdmin** | Amministratore operativo | Combo Approver + PostingOfficer, **esente dal mutex SoD** (access review trimestrale obbligatoria) |
| **FlexKeyUser** | Key user UI | Salvataggio delle varianti UI5 Flexibility |
| **SuperAdmin** | Super amministratore | Unico ruolo **cross-company** (`grant: '*'` senza filtro società) + override di policy. Ogni sua lettura genera un `AuditLogEntry` `SUPERADMIN_QUERY` |
| **system-user** | Utenza tecnica | Callback di webhook (`bpaCallback`) — non assegnabile a una persona |

Oltre ai 15 esistono 4 ruoli **non assegnabili a utenti**, riservati a service key e integrazioni:
`InboundConnector` (canali in ingresso), `SACAnalyticsConsumer` (tenant SAP Analytics Cloud), `AIAgent`
(agenti AI su `NovaAgentService`) e `Token_Exchange` (tecnico XSUAA).

> **Admin non è SuperAdmin.** Ogni entità con `CompanyCode` — master data inclusi — filtra le righe di un
> Admin sulla sua società. Le operazioni a scope globale (es. i due pulsanti del pannello Trasporto,
> §11.2.6) richiedono SuperAdmin.

---

## 4. Navigazione nel Fiori Launchpad

Il Fiori Launchpad è organizzato in **4 pagine** all'interno dello space "NOVA InvoiceSuite":

### Pagina 1: Panoramica
- **Panoramica** - Vista unificata KPI e App

### Pagina 2: Monitoraggio Operativo
Sezione *Elaborazione Fatture* — 3 tile:
- **Fatture Passive** - Elaborazione & Workflow
- **Approvazioni** - Inbox Personale
- **Estrazione AI** - DOX Intelligence

### Pagina 3: Intelligence & Analytics
Sezione *Analisi e Governance* — 3 tile:
- **Analisi Strategica** - Dashboard C-Level
- **Regole & Workflow** - Soglie Finanziarie
- **Gestione SLA** - Regole Scadenza & Escalation (apre l'app Regole & Workflow sull'entità `SLAConfigurations`)

### Pagina 4: Amministrazione
Sezione *Configurazione e Operazioni* — 2 tile:
- **Configurazione** - Parametri Sistema
- **Operazioni** - Salute & Sincronizzazione

Sezione *Platform Admin (SuperAdmin)* — 1 tile:
- **Platform Admin** - Certificati & MinIO (visibile al solo SuperAdmin)

> Totale: **10 tile** su 4 pagine per 9 app (l'app Regole & Workflow ha due tile, una per entità).
> Fonte: `app/flp/cdm.json`. Le tile che aprono un'app amministrativa restano comunque soggette ai
> `@restrict` del backend: vederla non significa poterla usare.

---

## 5. Il Processo di Elaborazione Fatture in 6 Fasi

> Questa sezione è la sintesi **orientata all'operatore**. Il riferimento tecnico del ciclo di vita —
> status, boundary di fase, branching TD04, phase gate, invarianti — è
> [`INVOICE_LIFECYCLE_DESIGN.md`](./INVOICE_LIFECYCLE_DESIGN.md): in caso di discordanza fa fede quello.

Ogni fattura attraversa un processo strutturato in 6 fasi sequenziali, visualizzate nell'app principale tramite un wizard e un indicatore di progresso.

```
Fase 1          Fase 2          Fase 3          Fase 4          Fase 5          Fase 6
RICEZIONE  -->  RISOLUZIONE --> VERIFICHE  -->  ABBINAMENTO --> APPROVAZIONE -> REGISTRAZIONE
(XML Parse)     (Business       (Duplicati,     (PO Match,      (Workflow       (Posting S/4,
                 Partner)        Fiscale,        3-Way Match,     multi-livello)  Archiviazione)
                                 Rischio)        Costi)
                                                   |
                                                   +--> Fase 3_BIS [TD04 only]
                                                        CREDIT_MATCHING
                                                        (Match con fattura
                                                         originale)
```

**Branch F3_BIS — Note di Credito (TD04):** quando il documento è classificato `SDIDocumentType=TD04`, il flusso devia subito dopo la Fase 3 verso lo stato `CREDIT_MATCHING`. Qui l'utente esegue il match con la fattura originale (action `matchCreditNoteToOriginal`). Solo dopo il match riuscito il documento rientra nel ramo principale verso la Fase 5 (`PENDING_APPROVAL`). Vedi §5.7 per dettaglio.

**Phase gate:** i due check `COST_ALLOCATION_REQUIRED` (NON_PO senza cost allocation) e `CREDIT_NOTE_MATCH_MISSING` (TD04 senza match) sono **phase gate globali** marcati `IsPhaseGate=true` nel catalog `ProcessStepCheck`. NON sono disabilitabili tramite `CompanyCheckOverride.IsDisabled` (governance globale, vedi [CLAUDE.md](../CLAUDE.md#draft--bound-actions--regole-critiche)). Admin può solo modificare la severity (ERROR → WARNING) per consentire override-with-justification.

**Parità single ↔ mass (R9):** la funzione `resolveNextAction(status, invoice)` è SSOT per determinare la
prossima action eseguibile su una invoice. Sia il bottone single dell'ObjectPage sia la mass action su
`processNext` invocano la stessa risoluzione.

> ⚠️ `STOP_ACTIONS` **non è la lista degli stati terminali**: è un insieme di **nomi di action**
> (`sendForApproval`, `postInvoice`, `archiveInvoice`, `matchCreditNoteToOriginal`, `parkInvoice`,
> `reverseInvoice`, `rejectAndCloseInvoice`, `reopenInvoice`) che la catena automatica non deve
> concatenare — servono una conferma dell'utente o hanno una guard di stato propria. Gli stati terminali
> sono un dato **diverso**: `IsTerminal=true` nel seed `ProcessingStatuses` (vedi tabella in fondo a
> questa sezione).

### Fase 1: Ricezione e Parsing

**Obiettivo:** Acquisire la fattura elettronica e parsificare i dati XML FatturaPA.

**Status invoice:** `NEW` (unico stato iniziale runtime, post-2026-04-28)

> **Nota architetturale 2026-04-28**: ricezione e parsing sono concerns dell'ingestione, non del lifecycle invoice. Sono tracciati su `InboundMessage.Status` (`RECEIVED → PROCESSING → NORMALIZED → DUPLICATE/FAILED`). Solo dopo NORMALIZED si crea il record `GuidEdocInvoice` con `ProcessingStatus='NEW'`. Le righe storiche in `RECEIVED`/`XML_PARSED` sono migrate a `NEW` da `db/migrations/{pg,hana}/009_invoice_status_dedupe.sql`.

**Cosa succede:**
1. La fattura arriva tramite uno dei canali supportati (SDI, DOX, EDI, Email, Webhook) — `InboundMessage.Status='RECEIVED'`
2. Il parser FatturaPA estrae dati generali, fornitore, righe — `InboundMessage.Status='PROCESSING' → 'NORMALIZED'`
3. Il sistema genera il record `GuidEdocInvoice` con `ProcessingStatus='NEW'`

**Campi editabili (se necessario):** ⚠️ **nessuno per default.** I campi letti dall'XML FatturaPA —
numero documento, data, importo, valuta, tipo documento SDI, ragione sociale, codice fiscale e P.IVA del
fornitore, IBAN, scadenza — sono in **sola lettura** finché un amministratore non provisiona una policy
`CompanyFieldEditability` (Configurazione → *Field Editability per Company*) per la combinazione
società + ruolo + fase. È il default conservativo della governance ADR 0006: il valore di ripiego è
"ReadOnly", non "editabile". Vedi §11 e la voce 17.4 di [TROUBLESHOOTING.md](TROUBLESHOOTING.md).

Tre campi non sono apribili **da nessuna policy e da nessun ruolo, SuperAdmin incluso**
(`LegalImmutable`): `createdAt`, `eDocumentGuid`, `SDIIdentificativoSdI`.

**Azione disponibile:**
- `Risolvi Fornitore` - Avvia la risoluzione automatica del Business Partner
- `Elaborazione Automatica` - Tenta l'elaborazione touchless completa

### Fase 2: Risoluzione Business Partner

**Obiettivo:** Identificare il Business Partner SAP corrispondente al fornitore della fattura.

**Status attraversati:** `NEW` -> `BP_RESOLVED`

**Cosa succede:**
1. Il sistema cerca il BP in S/4HANA per codice fiscale, P.IVA o ragione sociale
2. Se trovato con confidenza >= 95%: assegnazione automatica
3. Se trovato con confidenza 70-94%: assegnazione con warning (eccezione BP_LOW_CONFIDENCE)
4. Se confidenza < 70% o non trovato: richiede intervento manuale
5. Validazione IBAN fattura vs IBAN master data del fornitore
6. Controllo flag di cancellazione/blocco sul BP

**Intervento manuale (campo editabile):**
- **Business Partner SAP** (`ResolvedBPNumber`): campo editabile con value help che mostra la lista fornitori dal `SupplierScorecards`. Quando l'utente inserisce manualmente un BP:
  - Il metodo di risoluzione diventa `MANUAL`
  - La confidenza viene impostata al 100%
  - Lo stato avanza automaticamente a `BP_RESOLVED`
  - L'IBAN viene validato contro i dati master del nuovo BP

**Per fatture NON_PO:** in questa fase si gestisce anche l'allocazione costi (centro di costo, conto CoGe, ordine interno).

**Azione disponibile:**
- `Verifica Duplicati` - Avvia il controllo duplicati

### Fase 3: Verifiche di Compliance

**Obiettivo:** Controllare duplicati, validare la compliance fiscale e analizzare il rischio.

**Status attraversati:** `BP_RESOLVED` -> `DUPLICATE_CHECK` -> `VALIDATED` -> `RISK_ASSESSED`

**Sotto-fase 3a: Controllo Duplicati**
- Confronto normalizzato del numero fattura (strip caratteri speciali, case insensitive)
- Matching fuzzy su fornitore + importo + data entro una finestra temporale
- Esiti (5 etichette): Non Verificato · **Nessun Duplicato** · **Sospetto Duplicato** · **Duplicato Confermato** · **Sbloccato Manualmente** (duplicato rilevato e sbloccato con motivazione registrata)
- Se sospetto: creazione eccezione `DUPLICATE` con riferimento al gruppo duplicati

**Sotto-fase 3b: Validazione Fiscale**
- Verifica consistenza P.IVA tra XML e master data
- Controllo applicabilità Split Payment / Reverse Charge
- Validazione tipo documento SDI (TD01-TD28) vs mappatura configurata
- Verifica ritenuta d'acconto e cassa previdenza
- Esiti (nella UI si legge l'**etichetta**, non il codice): Non Validato · **Superata** · **Avviso** · **Fallita**

**Sotto-fase 3c: Analisi Rischio**
- Score 0-100 basato su: importo, BP noto/sconosciuto, risultato duplicati, stato fiscale, storico fornitore
- Classificazione: Basso (0-40) · Medio (41-70) · Alto (71-100) — le soglie sono amministrabili per società (`RiskAmountTier` / `RiskFeatureWeight`)
- Rilevamento anomalie (flag `AnomalyDetected`)
- Creazione eccezioni automatiche per rischio elevato

**Eccezioni visibili:** la tabella eccezioni mostra tipo, severità (**Errore** bloccante · **Avviso** non bloccante · **Informativa**), stato e note.

**Azioni disponibili:**
- `Validazione Fiscale` - Esegui validazione fiscale
- `Analisi Rischio` - Calcola score di rischio

### Fase 4: Abbinamento PO e Three-Way Match

**Obiettivo:** Abbinare la fattura all'ordine di acquisto e verificare la coerenza PO-GR-Fattura.

**Status attraversati:** `MATCHING_PENDING` -> `PO_MATCHED` -> `THREE_WAY_OK` (si entra da `RISK_ASSESSED` con «Conferma e Avanza Fase»)

**Sotto-fase 4a: Abbinamento Ordine di Acquisto**
- Ricerca PO in S/4HANA per fornitore e riferimenti nella fattura
- Scoring di matching basato su: importo, fornitore, data, riferimenti testuali
- Se match automatico non possibile: campo PO editabile per inserimento manuale

**Intervento manuale (campi editabili):**
- **Ordine di Acquisto** (`MatchedPurchaseOrder`): inserimento numero PO con validazione
- **Posizione OdA** (`MatchedPOItem`): posizione specifica dell'ordine

Quando l'utente inserisce manualmente un PO:
- Il metodo diventa `MANUAL`, lo score 100%
- Lo stato avanza a `PO_MATCHED`

**Sotto-fase 4b: Three-Way Match**
- Confronto riga per riga: quantità PO vs quantità entrata merci vs quantità fattura
- Confronto prezzi: prezzo unitario PO vs prezzo unitario fattura
- Applicazione tolleranze configurate per company code
- Esiti **di riga** (6): Superato · Errore Quantità · Errore Prezzo · Errore Totale · In Tolleranza · **Entrata Merci Assente**
- Esiti **di testata** (9): Non Avviato · Non Applicabile · Parziale · Superato · Errore Quantità · Errore Prezzo · Errore Totale · In Tolleranza · Fallito

> I due domini sono **distinti**, non sinonimi: «Entrata Merci Assente» esiste solo a livello di riga
> (una posizione d'ordine fatturata senza entrata merci registrata) e la testata non può assumerlo.
> Servivano quindi due liste separate — nella lista fatture il filtro «3-Way Match» proponeva un valore che
> la testata non poteva mostrare, e la cella restava **bianca**. Anche il riepilogo di riga viene mostrato
> per etichetta.

**Dettaglio match:** tabella con colonne N. Riga Fattura, PO, Posizione OdA, Qta OdA, Qta Entrata Merci, Qta Fattura, Varianza Prezzo, Risultato.

**Per fatture NON_PO:** questa fase e sostituita dall'allocazione costi (Fase 4 alternativa).

**Azioni disponibili:**
- `Abbina Ordine` - Avvia matching PO automatico
- `Esegui Three-Way Match` - Esegui verifica a 3 vie

### Fase 5: Approvazione

**Obiettivo:** Sottoporre la fattura al workflow di approvazione configurato.

**Status attraversati:** `THREE_WAY_OK` (ramo PO) / `COST_VALIDATED` o `COST_ALLOCATED` (ramo NON_PO) -> `PENDING_APPROVAL` -> `APPROVED`. Un rifiuto in approvazione riporta a **`REWORK`**, che nell'indicatore di progresso appare come nodo *interrotto*, non come step 5.

**Cosa succede:**
1. Il sistema identifica la regola di approvazione applicabile (per company code, range importo, categoria fornitore)
2. Crea un item di workflow assegnato all'approvatore designato
3. L'approvatore vede un riepilogo completo di tutte le fasi precedenti
4. Workflow multi-livello: se la regola ha un `NextRuleId`, dopo l'approvazione del primo livello si crea automaticamente il livello successivo

**Azioni dell'approvatore:**
- **Approva** (`approveInvoice`): con commento opzionale. Se tutti i livelli approvano -> `APPROVED`
- **Rifiuta** (`rejectInvoice`): con commento obbligatorio e codice motivo. La fattura passa a `REWORK` per correzione
- **Delega** (`delegateApproval`): trasferisce ad altro approvatore (con commento e destinatario)
- **Escala** (`escalateWorkflow`): invia al livello superiore (con motivo)
- **Richiedi Info** (`requestInfo`): mette in pausa per chiarimenti

**Riepilogo mostrato:** stato duplicati, stato fiscale, livello rischio, stato 3-Way Match, score auto-processing, idoneità touchless.

**Azione disponibile:**
- `Invia per Approvazione` - Sottoponi al workflow

### Fase 6: Registrazione e Archiviazione

**Obiettivo:** Contabilizzare la fattura in S/4HANA e archiviarla a norma di legge.

**Status attraversati:** `APPROVED` -> `POSTED` -> `ARCHIVED`

**Sotto-fase 6a: Registrazione (Posting)**
- Simulazione posting per preview (senza commit)
- Posting reale via API S/4HANA `API_SUPPLIERINVOICE_PROCESS_SRV`
- Per fatture NON_PO senza PO: posting FI diretto via `API_JOURNALENTRYITEMBASIC`
- Risultato: numero documento FI, anno fiscale, data contabilizzazione

**Sotto-fase 6b: Archiviazione Sostitutiva**
- Invio al provider di conservazione sostitutiva (Blueprint 12 Conservatore)
- Generazione hash documento, firma digitale, pacchetto di versamento
- Esiti: `PENDING` -> `ARCHIVED` | `FAILED`

**Sotto-fase 6c: Storno (se necessario)**
- Creazione richiesta di storno con motivazione obbligatoria
- Workflow doppia approvazione per lo storno
- Chiamata S/4HANA per reversal del documento FI
- Invalidazione dell'archiviazione

**Azioni disponibili:**
- `Simula Registrazione` - Preview senza commit
- `Registra in S/4` - Posting definitivo
- `Parcheggia` - Posting preliminare
- `Storna` - Reversal del documento contabile
- `Archivia` - Conservazione sostitutiva

### Fase 3_BIS: Credit Note Matching (solo TD04)

**Obiettivo:** abbinare la nota di credito (TD04) alla fattura originale che la ha generata, prima di sottometterla ad approvazione.

**Status attraversati:** `RISK_ASSESSED` (con `SDIDocumentType=TD04`) -> `CREDIT_MATCHING` -> `PENDING_APPROVAL`

**Cosa succede:**
1. Il flusso lifecycle, dopo la Fase 3 (Verifiche Compliance), rileva `SDIDocumentType=TD04`
2. Lo stato avanza a `CREDIT_MATCHING` (entry point F3_BIS)
3. Il sistema applica `raiseNonPoPhaseGateExceptions(tx, invoice)` — il phase gate `CREDIT_NOTE_MATCH_MISSING` viene sollevato come exception severità ERROR / `OverridePolicy=SELF_SIGNED`
4. L'utente deve risolvere il phase gate prima di poter avanzare:

**Opzioni di risoluzione:**
- **Match automatico**: il sistema cerca per `OriginalInvoiceNumber` + `SupplierTaxCode` + `CompanyCode` se rispecchiati in XML
- **Match manuale**: action `matchCreditNoteToOriginal` con `OriginalInvoiceGuid` esplicito (modal con value-help su fatture POSTED/APPROVED dello stesso fornitore)
- **Self-signed override**: action `dismissException` con `JustificationText` (min length da `CompanyCheckOverride.JustificationMinLength`) — richiede ruolo `Approver` o superiore

**Tolleranza match:** parametro `CREDIT_NOTE_MATCH_TOLERANCE_PCT` (default 5%) consente match anche con piccole differenze di importo.

**Auto-match:** se `SystemParameters.CREDIT_NOTE_AUTO_MATCH=true` e c'è un'unica fattura candidata, il match avviene senza intervento (audit con `MatchMethod=AUTO`).

**Mass action TD04:** dall'app Fatture Passive, ListReport con filtro `SDIDocumentType=TD04 AND Status=CREDIT_MATCHING`, tasto "Match Notes Credito Massivo" — itera invoice per invoice applicando auto-match dove possibile, riportando un summary degli skip.

**Severity downgrade (admin):** in casi specifici, `CompanyCheckOverride.Severity=WARNING` consente di proseguire senza match esplicito (audit con `OverrideReason='SEVERITY_DOWNGRADE'`).

**Azioni disponibili:**
- `Match Nota Credito` - Avvia match (auto o manuale)
- `Annulla Eccezione` - Self-signed override con justification
- `Match Massivo TD04` - Su ListReport filtrato

### Azioni Trasversali (disponibili in qualsiasi fase)

- **Blocco Pagamento** (`setPaymentBlock`): blocca il pagamento con codice (A=Bloccato, B=In revisione, R=Rischio, Z=Custom) e motivazione
- **Sblocco Pagamento** (`releasePaymentBlock`): rimuove il blocco
- **Avanza Stato** (`advanceStatus`): admin override per forzare lo stato (con motivazione e audit log)

### Meccanismo di Rework

Quando un approvatore rifiuta o un campo viene modificato:
- La modifica del BP invalida tutti i risultati a valle (PO match, 3-Way, costi, workflow)
- La modifica del PO invalida 3-Way match e allocazioni costi
- Il sistema esegue un **cascade reset** dei campi e dei record correlati
- La fattura torna allo stato corrispondente alla fase modificata

**REWORK loop:** dopo `rejectInvoice`, lo stato `REWORK` consente all'utente di correggere e ri-sottomettere. La transizione è bidirezionale: `REWORK -> NEW|BP_RESOLVED|RISK_ASSESSED` (a seconda del campo modificato), poi nuovamente verso `PENDING_APPROVAL`.

### Stati terminali

Gli stati elencati di seguito sono **terminali**: nessuna ulteriore azione di lifecycle è possibile e i
bottoni di avanzamento sono nascosti. L'elenco autorevole è la colonna `IsTerminal` del seed
`db/data/sap.passive.invoice-ProcessingStatuses.csv` — sono **5**, e `DISCARDED` non è uno di essi
(`DISCARDED` è uno stato di `AICapturedInvoice`, l'app Estrazione AI, non della fattura).

| Stato | Significato | Reversibile? |
|---|---|---|
| `POSTED` | Documento contabilizzato in S/4HANA con numero FI | Sì, via `reverseInvoice` (porta a `REVERSED`) |
| `ARCHIVED` | Conservazione sostitutiva completata | Solo storno: `reverseInvoice` è disponibile anche da `ARCHIVED` e invalida l'archiviazione |
| `REVERSED` | Storno completato in S/4 | No, terminale |
| `REJECTED` | Rifiutata e chiusa (`rejectAndCloseInvoice`) | Sì, via `reopenInvoice` — vedi sotto |
| `CANCELLED` | Annullata | No, terminale |

> ⚠️ **L'action `restartInvoice` non esiste.** Per riportare in lavorazione una fattura `REJECTED` si usa
> **`reopenInvoice`**, riservata al ruolo `Admin`, che chiede lo *Stato di ripresa* (`resumeStatus`, con
> value help su `ReopenResumeStatuses`). Vincoli reali: è applicabile **solo** a `ProcessingStatus =
> 'REJECTED'` (altrimenti 409), solo se il motivo del rifiuto era **SOFT** (i rifiuti HARD sono
> definitivi), e viene rifiutata se esistono ancora workflow item attivi. Non esiste alcun audit
> `LIFECYCLE_RESTART`: la chiusura registra `INVOICE_REJECTED`.

---

## 6. Manuale App: Fatture Passive

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Fatture Passive |
| **Sottotitolo** | Elaborazione & Workflow |
| **Icona** | monitor-payments |
| **Tipo** | ListReport + ObjectPage (Draft-enabled) |
| **Servizio OData** | `/odata/v4/orchestrator/` |
| **Entità principale** | `Invoices` (proiezione su `GuidEdocInvoice`) |

### 6.1 Lista Fatture (ListReport)

All'apertura dell'app si presenta la lista di tutte le fatture con le seguenti **colonne**:

Le **10 colonne** della `UI.LineItem` di `Invoices` (`app/annotations.cds`, misurate 2026-08-22):

| Colonna | Campo | Note |
|---------|-------|------|
| N. Documento | `GeneralDocumentData_Number` | Numero fattura fornitore |
| Data | `GeneralDocumentData_Date` | Data documento |
| Fornitore | `SupplierData_Description` | Ragione sociale |
| Importo | `GeneralDocumentData_TotalAmount` | Con valuta |
| Stato | `ProcessingStatus` | Codice + etichetta dalla code list `ProcessingStatuses`, con criticality (colori) |
| Prossima azione | `NextActionMessage` | Frase che indica cosa fare e in quale sezione — colonna assente da questo elenco fino al 2026-08-22 |
| Match | `fiMatchStatus` | Stato abbinamento FI |
| Rischio | `RiskLevel` | Basso/Medio/Alto con colori |
| Società | `companyCode` | Codice società SAP |
| Canale | `AcquisitionChannel` | SDI/DOX/EDI/Email/Webhook/Manuale |

> Le etichette leggibili non arrivano da campi `*Text` separati: i codici sono associati a una
> `sap.common.CodeList` e resi con `@Common.Text` + `@Common.TextArrangement`. La colonna
> **Categoria** (`InvoiceCategory`) non è nella lista di default — si aggiunge dalle impostazioni
> colonna della tabella.

#### Filtri disponibili

| Filtro | Tipo | Note |
|--------|------|------|
| Società | Value List | Lista company code attivi |
| Stato Elaborazione | Value List | Tutti gli stati del processo |
| Fornitore | Testo libero | Ricerca per ragione sociale |
| Data Documento | Range date | Da/A |
| Livello Rischio | Value List | Basso/Medio/Alto |
| Canale Acquisizione | Value List | SDI/DOX/EDI/Email/Webhook/Manuale |
| Categoria Fattura | Value List | PO/NON_PO/MIXED |

#### Ordinamento predefinito
Per data documento decrescente (fatture più recenti in alto).

#### Azioni di massa (toolbar)

La toolbar della lista espone **due** azioni di massa, non cinque, più l'export standard di Fiori:

| Azione | Action OData | Condizione |
|--------|--------------|------------|
| Elabora Prossimo Passo | `processNext` | Esegue il prossimo step per le righe selezionate; salta le fatture in stato terminale e quelle la cui prossima azione è in `STOP_ACTIONS` |
| Approva Selezionate | `approveSelected` | Ruoli `Approver` / `Admin` / `OperationalAdmin`. Rifiuta (409) le righe non in `PENDING_APPROVAL`, quelle senza un workflow item in attesa e le NON_PO senza allocazione confermata quando l'allocazione è obbligatoria |
| Esporta (Excel) | — | Funzione standard FE v4 (`enableExport`), sempre disponibile |

> **Registrazione e archiviazione NON sono azioni di massa della lista**, e la riga che le indicava tale
> è stata corretta il 2026-08-22. È una scelta di design esplicita, annotata nel codice: nel ListReport
> restano solo le azioni batch quotidiane, mentre fase, posting e archiviazione vivono nelle sezioni
> dell'ObjectPage «dove l'utente ha contesto». `postInvoice` e `archiveInvoice` si trovano nella sezione
> **Posting**.

#### Interazione step-by-step: Apertura lista

1. Aprire l'app "Fatture Passive" dal Launchpad
2. La lista si carica automaticamente con tutte le fatture
3. Utilizzare la barra filtri in alto per restringere la ricerca
4. Cliccare su "Adatta filtri" per mostrare filtri aggiuntivi
5. Selezionare una o più fatture con le checkbox per azioni di massa
6. Cliccare su una riga per aprire il dettaglio (ObjectPage)

### 6.2 Dettaglio Fattura (ObjectPage)

L'ObjectPage mostra il dettaglio completo della fattura con:

#### Header (Testata)
- **Indicatore di Progresso**: barra 0-100% con colore (verde >80%, giallo 40-80%, rosso <40%)
- **Stato Elaborazione**: con badge colorato (criticality)
- **Importo Totale**: con valuta
- **Livello Rischio**: con badge colorato
- **Stato 3-Way Match**: con indicatore

#### Wizard di Processo (6 Step)

L'ObjectPage contiene un **wizard a 6 passi** che guida l'utente attraverso le fasi del processo. Il passo corrente e evidenziato dall'indicatore di progresso in alto.

**Navigazione nel wizard:**
- Lo step corrente è quello corrispondente allo stato della fattura
- Gli step completati sono marcati con icona verde
- Gli step futuri mostrano icona grigia
- L'utente può navigare liberamente tra gli step per consultazione

##### Step 1 - Ricezione

**Sezioni visibili:**
- Dati Generali: numero, data, importo, valuta, tipo documento
- Dati Fornitore: ragione sociale, codice fiscale, P.IVA
- Dettagli SDI: tipo documento SDI, identificativo SDI, progressivo invio, stato notifica
- Pagamento: scadenza, modalità, IBAN
- Canale: canale acquisizione con testo leggibile
- Righe Fattura: tabella con numero riga, descrizione, quantità, prezzo unitario, totale riga, aliquota IVA

**Campi editabili** — governati da policy, **non** dallo stato soltanto. I 13 campi RAW_PARSED FatturaPA
(dati generali: numero, data, importo, valuta, tipo documento; fornitore: ragione sociale, CF, P.IVA;
pagamento: IBAN, scadenza; aggregati fiscali: bollo, ritenuta, cassa previdenza) espongono un
`FieldControl` il cui **default è `7` = ReadOnly**. Diventano editabili solo se
`CompanyFieldEditability` ha una regola che combacia con società + ruolo + fase corrente; senza policy
restano grigi anche in stato `NEW` o `REWORK`.

> Il campo grigio non è un difetto: è il default conservativo della governance dei campi. Chi deve poterli correggere
> chiede all'amministratore una policy in Configurazione → *Field Editability per Company*. Se la policy
> c'è e il campo resta grigio, l'invalidazione della cache impiega fino a ~60s — vedi
> [TROUBLESHOOTING §17.4](TROUBLESHOOTING.md#174-field-shows-readonly-even-with-policy-configured).

**Bottoni azione:**
- `Risolvi Fornitore` - visibile quando `CanResolvePartner = true`
- `Elaborazione Automatica` - visibile quando `CanAutoProcess = true`

##### Step 2 - Risoluzione

**Sezioni visibili:**
- Business Partner: BP risolto, metodo (Auto/Manuale), confidenza %, data risoluzione
- Allocazioni Costo (solo per NON_PO): tabella con conto CoGe, centro di costo, centro di profitto, importo, percentuale

**Interazione manuale BP:**
1. Se il BP non è stato risolto automaticamente o la confidenza è bassa, il campo "Business Partner SAP" e editabile
2. Cliccare sul campo per aprire il value help con la lista fornitori
3. Selezionare il fornitore corretto dalla lista (mostra BP number + ragione sociale)
4. Oppure digitare direttamente il numero BP (10 cifre)
5. Al salvataggio: il sistema imposta automaticamente metodo=MANUAL, confidenza=100%, e avanza lo stato a BP_RESOLVED
6. I campi correlati (IBAN, flag blocco/cancellazione) vengono aggiornati via SideEffect

**Bottone azione:**
- `Verifica Duplicati` - visibile quando `CanCheckDuplicate = true`

##### Step 3 - Verifiche

**Sezioni visibili:**
- Controllo Duplicati: stato (Non verificato/Chiaro/Sospetto/Confermato), flag duplicato
- Validazione Fiscale: stato (Non validato/Superato/Fallito/Warning), consistenza IVA, Split Payment, Reverse Charge
- Analisi Rischio: score (0-100), livello (Basso/Medio/Alto), note, flag anomalia
- Ritenuta d'Acconto: tipo, aliquota, importo, base
- Bollo e Cassa Previdenza: bollo virtuale, tipo cassa, importo, aliquota
- Eccezioni: tabella con tipo, severità, stato, note, data creazione

**Tutti i campi sono di sola lettura** (risultati delle verifiche automatiche).

**Bottoni azione:**
- `Validazione Fiscale` - visibile quando `CanValidateFiscal = true`
- `Analisi Rischio` - visibile quando `CanAnalyzeRisk = true`

##### Step 4 - Abbinamento

**Sezioni visibili:**
- Ordine di Acquisto: numero OdA, posizione, metodo match, score, data match
- Three-Way Match: stato globale, risultato, entrata merci, foglio servizi, tolleranza
- Dettaglio Match: tabella riga per riga con quantità/prezzi PO vs GR vs fattura

**Campi editabili** (quando lo stato e tra VALIDATED/PO_MATCHED/REWORK):
- **Ordine di Acquisto** (`MatchedPurchaseOrder`): inserimento manuale numero PO
- **Posizione OdA** (`MatchedPOItem`): posizione specifica

**Interazione manuale PO:**
1. Se il matching automatico non ha trovato un PO, i campi OdA sono editabili
2. Inserire il numero dell'ordine di acquisto (10 cifre)
3. Inserire la posizione (6 cifre, opzionale)
4. Al salvataggio: metodo=MANUAL, score=100%, stato -> PO_MATCHED

**Bottoni azione:**
- `Abbina Ordine` - visibile quando `CanMatchPO = true`
- `Esegui Three-Way Match` - visibile quando `CanThreeWayMatch = true`

##### Step 5 - Approvazione

**Sezioni visibili:**
- Riepilogo Verifiche: stato duplicati, fiscale, rischio, 3-Way (vista consolidata)
- Auto-Processing: score, idoneità touchless
- Workflow: tabella items con stato, assegnato a, data scadenza, livello, SLA

**Tutti i campi sono di sola lettura** (riepilogo decisionale per l'approvatore).

**Bottone azione:**
- `Invia per Approvazione` - visibile quando `CanSendApproval = true`

##### Step 6 - Registrazione

**Sezioni visibili:**
- Posting: numero documento FI, anno fiscale, data posting, errore (se presente)
- Archiviazione: stato archivio, ID documento archivio, data archiviazione
- Storno: stato storno, documento storno, motivo
- Riepilogo Finale: esecuzioni step del processo, canale, stato notifica SDI

**Tutti i campi sono di sola lettura** (risultati finali).

**Bottoni azione:**
- `Simula Registrazione` - visibile quando `CanSimulatePosting = true`
- `Registra in S/4` - visibile quando `CanPostInvoice = true`
- `Parcheggia` - visibile quando `CanParkInvoice = true`
- `Storna` - visibile quando `CanReverseInvoice = true` (solo dopo POSTED)
- `Archivia` - visibile quando `CanArchiveInvoice = true` (solo dopo POSTED)

#### Tab dell'ObjectPage (oltre al wizard)

L'ObjectPage ha **9 sezioni** di primo livello (non 5). I nomi qui sotto sono le etichette che compaiono
davvero a schermo — sono quelle usate anche dai messaggi di `Conferma Fase` quando indicano dove andare a
risolvere un blocco:

| Sezione (etichetta a schermo) | ID facet | Contenuto |
|---|---|---|
| **Documento** | `SectionDocumento` | Dati FatturaPA / testata documento, righe, documenti allegati |
| **Business Partner & Fornitore** | `SectionRicezione` | Fase di ricezione, canale di acquisizione, risoluzione BP |
| **Verifiche** | `SectionVerifiche` | Duplicati, validazione fiscale, rischio, eccezioni |
| **Gestione PO** | `SectionMatching` | Match ordine, three-way match, service entry sheet |
| **Gestione Senza OdA** | `SectionNonPO` | Allocazione costi e flusso NON_PO |
| **Note di Credito** | `SectionCreditoNota` | Matching nota di credito (TD04) |
| **Approvazione** | `SectionApprovazione` | Workflow approvativo ed eccezioni di override |
| **Posting** | `SectionRegistrazione` | Registrazione S/4HANA e archiviazione |
| **Monitoraggio** | `SectionMonitoraggio` | Lifecycle, audit trail, KPI tecnici |

> Fonte: le `UI.CollectionFacet` di `app/annotations.cds` e il seed
> `db/data/sap.passive.invoice-UISectionCodes.csv`. Attenzione al doppio nome: il seed chiama la quinta
> sezione `NON-PO`, ma l'utente a schermo legge **Gestione Senza OdA** — è quest'ultimo il nome da usare
> in una procedura.

#### Azioni trasversali (sempre disponibili)

| Azione | Parametri | Note |
|--------|-----------|------|
| Blocca Pagamento | Codice blocco (A/B/R/Z), motivo | Apre un dialog con campo codice e motivo |
| Sblocca Pagamento | - | Rimuove il blocco |
| Avanza Stato | Stato target, motivo | Solo Admin — forza lo stato |

### 6.3 Workflow Completo: Elaborazione di una Fattura PO

**Scenario:** Arriva una fattura SDI da fornitore noto, con PO.

1. **Apertura lista** -> filtro su Stato = "Nuova" + Società = "1000"
2. **Click sulla fattura** -> si apre l'ObjectPage
3. **Step 1 verificato** -> i dati XML sono già parsificati, visibili nella sezione Ricezione
4. **Click "Risolvi Fornitore"** -> il sistema cerca il BP in S/4HANA
   - Se trovato: la confidenza appare (es. 98%), metodo "AUTO_TAXCODE"
   - Se non trovato: inserire manualmente il numero BP nel campo editabile
5. **Avanzamento a Step 2** -> BP risolto, ora visibile nella sezione Risoluzione
6. **Click "Verifica Duplicati"** -> il sistema confronta con fatture esistenti
7. **Click "Validazione Fiscale"** -> verifica compliance italiana
8. **Click "Analisi Rischio"** -> score calcolato, livello assegnato
9. **Avanzamento a Step 4** -> click "Abbina Ordine"
   - Se PO trovato: match automatico con score
   - Se non trovato: inserire manualmente numero PO
10. **Click "Esegui Three-Way Match"** -> confronto PO vs GR vs Fattura riga per riga
11. **Step 5** -> click "Invia per Approvazione"
12. **L'approvatore** riceve la fattura nella sua coda -> approva con commento
13. **Step 6** -> click "Simula Registrazione" per preview, poi "Registra in S/4"
14. **Dopo posting** -> click "Archivia" per conservazione sostitutiva
15. **Stato finale:** `ARCHIVED` con indicatore di progresso al 100%

### 6.4 Workflow Completo: Elaborazione di una Fattura NON_PO

**Scenario:** Fattura per servizi di consulenza senza ordine di acquisto.

1-8. **Come sopra** fino all'analisi rischio
9. **Step 2 (Risoluzione)** -> sezione Allocazioni Costo visibile
   - Inserire conto CoGe, centro di costo, ordine interno
   - Verificare che la somma delle percentuali = 100%
   - Il sistema valida i centri di costo via API S/4HANA
10. **Step 4 saltato** (non applicabile per NON_PO) -> 3-Way Match = "Non Applicabile"
11. **Proseguire con Step 5-6** come per fatture PO

---

## 7. Manuale App: Panoramica

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Panoramica |
| **Sottotitolo** | Vista unificata KPI e App |
| **Icona** | home |
| **Tipo** | Custom Overview Page |
| **Servizio OData** | `/odata/v4/orchestrator/` |

### 7.1 Descrizione

La Panoramica è la landing page centrale della suite. Fornisce una vista aggregata dei KPI principali e un accesso rapido a tutte le applicazioni.

### 7.2 Contenuti Visualizzati

| Sezione | Dati | Fonte |
|---------|------|-------|
| Totale Fatture | Conteggio per stato elaborazione | `Invoices` aggregate |
| Distribuzione Canali | Ripartizione SDI/DOX/EDI/Email/Webhook | `ChannelKPIs` |
| Eccezioni Aperte | Conteggio per stato (Aperte, In lavorazione, Risolte) | `InvoiceExceptions` |
| Distribuzione Rischio | Torta LOW/MEDIUM/HIGH | `Invoices` aggregate |
| Successo 3-Way Match | Tasso di successo matching | `Invoices` aggregate |
| Quick Links | Accesso diretto alle altre **8** app della suite (tutte tranne Panoramica stessa), **filtrate per ruolo**: Approvazioni solo al track Approver/Admin/OperationalAdmin, Estrazione AI a Worker/Admin, Regole & Workflow e Configurazione ad Admin/AdminConfig, Platform Admin al solo SuperAdmin | Navigazione FLP (`semanticObject` + `semanticAction`) |

### 7.3 Interazione

1. Aprire la tile "Panoramica" dal Launchpad
2. I KPI si caricano automaticamente con dati live
3. Cliccare su un KPI o un grafico per navigare all'app di dettaglio
4. Utilizzare i quick links per accedere direttamente a qualsiasi app della suite

---

## 8. Manuale App: Estrazione AI

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Estrazione AI |
| **Sottotitolo** | DOX Intelligence |
| **Icona** | machine |
| **Tipo** | ListReport + ObjectPage |
| **Servizio OData** | `/odata/v4/orchestrator/` |
| **Entità principale** | `AICapturedInvoices` |

### 8.1 Scopo

Gestisce l'estrazione automatica dei dati da documenti fattura (PDF, immagini) tramite SAP Document Information Extraction (DOX). Ogni documento estratto viene validato, corretto se necessario, e poi abbinato a un record fattura nel sistema principale.

### 8.2 Lista Catture (ListReport)

**Colonne:**

| Colonna | Descrizione |
|---------|-------------|
| N. Fattura | Numero fattura estratto |
| Data | Data documento estratta |
| Fornitore | Ragione sociale estratta |
| P.IVA | Partita IVA estratta |
| Importo | Totale estratto con valuta |
| Stato | Caricato/In attesa/In estrazione/Estratto/Abbinato/Parziale/Non abbinato/Errore |
| Confidenza | Percentuale di confidenza DOX (con colori: verde >90%, giallo >70%, rosso <=70%) |

### 8.3 Dettaglio Cattura (ObjectPage)

**Header:** Numero fattura, stato con criticality, confidenza con badge colorato

**Sezioni:**
- **Dati Estratti:** tutti i campi estratti da DOX con confidenza per campo
- **Righe Estratte:** tabella `AICapturedItem` con dettaglio righe
- **Campi JSON Grezzi:** visualizzazione dei dati raw DOX per debug

### 8.4 Azioni

| Azione | Descrizione | Quando |
|--------|-------------|--------|
| Abbina con Ordine | Tenta matching PO automatico sui dati estratti | Dopo estrazione completata |
| Invia Correzione | Feedback loop: corregge i dati e reinvia a DOX per migliorare il modello | Quando i dati estratti sono errati |

### 8.5 Workflow Tipico

1. Un documento viene caricato (manualmente o tramite canale automatico)
2. DOX processa il documento -> stato `EXTRACTING`
3. Al completamento -> stato `EXTRACTED` con confidenza
4. L'operatore verifica i dati estratti
5. Se corretti: click "Abbina con Ordine" -> il record viene collegato alla fattura principale
6. Se errati: corregge i campi e click "Invia Correzione" -> DOX impara per il futuro
7. Il record passa a `MATCHED` o `PARTIAL` a seconda del risultato

---

## 9. Manuale App: Analisi Strategica

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Analisi Strategica |
| **Sottotitolo** | Dashboard C-Level |
| **Icona** | business-objects-experience |
| **Tipo** | Analytical List Page (ALP) |
| **Servizio OData** | `/odata/v4/orchestrator/` |
| **Entità principale** | `StrategicAnalytics` (aggregation-enabled) |

### 9.1 Scopo

Dashboard strategica per management e C-Level. Fornisce KPI aggregati, trend, analisi rischio e performance fornitori con supporto completo per drill-down e segmentazione.

### 9.2 Dimensioni di Analisi (Raggruppamento)

| Dimensione | Descrizione |
|------------|-------------|
| Società | Company code SAP |
| Fornitore | Nome e numero BP fornitore |
| Data Fattura | Per analisi temporali |
| Stato Elaborazione | Per funnel processing |
| Stato Match | Per analisi abbinamento |
| Tipo Documento SDI | TD01-TD28 |
| Livello Rischio | LOW/MEDIUM/HIGH |
| Stato 3-Way Match | PASSED/FAILED/PARTIAL |
| Stato Duplicati | Per analisi qualità dati |
| Stato Fiscale | Per compliance monitoring |
| Nota di Credito | Si/No |
| Canale Acquisizione | Per analisi canale |

### 9.3 Metriche (Misure Aggregabili)

| Metrica | Aggregazioni | Descrizione |
|---------|-------------|-------------|
| Importo | SUM, MIN, MAX, AVERAGE | Totale fatturato |
| Score Rischio | AVERAGE, MAX | Rischio medio e massimo |
| Scadute | SUM | Conteggio fatture scadute |
| Auto-Matched | SUM | Fatture abbinate automaticamente |
| Touchless | SUM | Fatture elaborate senza intervento |
| 3-Way OK | SUM | Match a 3 vie superato |
| Duplicati | SUM | Fatture con flag duplicato |
| Bloccate Pagamento | SUM | Fatture con blocco pagamento |

### 9.4 Interazione

1. Aprire "Analisi Strategica" dal Launchpad
2. La pagina ALP mostra una **visual filter bar** con grafici interattivi in alto
3. Cliccare su un segmento del grafico per filtrare i dati
4. La tabella sottostante si aggiorna automaticamente
5. Utilizzare il filtro compatto per combinare più dimensioni
6. Espandere/collassare le righe per drill-down gerarchico
7. Esportare i dati in Excel tramite il bottone "Esporta"

---

## 10. Manuale App: Regole & Workflow

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Regole & Workflow |
| **Sottotitolo** | Soglie Finanziarie |
| **Icona** | lead-outdated |
| **Tipo** | Multi-entity ListReport + ObjectPage |
| **Servizio OData** | `/odata/v4/orchestrator/` |

### 10.1 Scopo

Configurazione delle regole di approvazione, tolleranze di matching, regole di allocazione costi e gestione lotti di archiviazione. E l'app di governance per definire il "chi approva cosa".

### 10.2 Entità Gestite

#### 10.2.1 Regole di Approvazione (`ApprovalRules`)

Definiscono la catena di approvazione per le fatture.

**Campi principali:**

| Campo | Descrizione |
|-------|-------------|
| Società | Company code applicabile |
| Importo Da | Soglia inferiore |
| Importo A | Soglia superiore |
| Categoria Fornitore | Filtro per tipo fornitore |
| Categoria Fattura | PO / NON_PO / ALL |
| Approvatore | User ID dell'approvatore assegnato |
| Livello Approvazione | 1, 2, 3... per catene multi-livello |
| Regola Successiva | Riferimento alla regola del livello successivo |
| Giorni Escalation | Giorni prima dell'escalation automatica |
| Attiva | Flag attivazione |

**Workflow di configurazione:**
1. Aprire "Regole & Workflow" dal Launchpad
2. Selezionare "Regole di Approvazione" dalla navigazione
3. Cliccare "Crea" per una nuova regola
4. Compilare: società, range importo, approvatore, livello
5. Per catene multi-livello: creare più regole collegate tramite "Regola Successiva"
6. Attivare la regola con il flag "Attiva"
7. Salvare

**Esempio catena multi-livello:**
- Regola 1: 0-10.000 EUR -> Responsabile Ufficio (livello 1)
- Regola 2: 10.000-50.000 EUR -> Direttore Finanziario (livello 1) -> Regola 3
- Regola 3: (NextRule di Regola 2) -> CEO (livello 2)

#### 10.2.2 Configurazione Processo per Società (`CompanyProcessConfigs`)

Mappa ogni company code a un template di processo e una variante di configurazione.

**Workflow:**
1. Selezionare "Configurazione Processo" dalla navigazione
2. Cliccare "Crea"
3. Selezionare il company code
4. Associare un template di processo
5. Salvare

#### 10.2.3 Template di Processo (`ProcessTemplates`)

Definiscono il flusso di elaborazione a 6 fasi con configurazione step-by-step.

#### 10.2.4 Ruoli di Processo (`ProcessRoles`)

Ruoli **applicativi di processo**, distinti dai ruoli di autorizzazione del §3: sono i destinatari a cui
`ApprovalRule` e `ProcessStepCheck.OverrideApproverRole` assegnano un passo. Il seed
(`db/data/sap.passive.invoice-ProcessRole.csv`) ne contiene **9**:

| Codice | Nome |
|---|---|
| `AP_MATCHING` | Operatore Matching |
| `AP_COMPLIANCE` | Operatore Compliance |
| `POSTING_OFFICER` | Addetto Registrazione |
| `APPROVER_STANDARD` | Approvatore Standard |
| `APPROVER_MANAGER` | Approvatore Manager |
| `APPROVER_TAX` | Approvatore Fiscale |
| `APPROVER_SENIOR` | Approvatore Senior |
| `APPROVER_DIRECTOR` | Direttore Approvatore |
| `APPROVER_CFO` | CFO Approvatore |

> I nomi «Reviewer», «Finance Manager» e «CEO», elencati qui fino al 2026-08-22, non esistono in nessun
> seed né in `xs-security.json`. Ogni `ProcessRole` porta un `BaseRole` che lo lega al ruolo di
> autorizzazione corrispondente.

#### 10.2.5 Regole di Allocazione Costi (`CostAllocationRules`)

Per fatture NON_PO: definiscono le regole di assegnazione automatica a conti CoGe e centri di costo.

**Workflow:**
1. Selezionare "Regole Allocazione Costi"
2. Creare una regola con: società, fornitore/categoria, conto CoGe, centro di costo, percentuale
3. Quando arriva una fattura NON_PO, il sistema propone l'allocazione basandosi su queste regole

#### 10.2.6 Lotti di Archiviazione (`ArchiveLots`)

Gestione batch per la conservazione sostitutiva annuale.

**Workflow:**
1. Selezionare "Lotti Archiviazione"
2. Creare un nuovo lotto per società e anno
3. Il sistema raggruppa le fatture da archiviare
4. Verificare il contenuto del lotto
5. Sottomettere al provider di conservazione
6. Monitorare lo stato fino alla chiusura

---

## 11. Manuale App: Configurazione

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Configurazione |
| **Sottotitolo** | Parametri Sistema |
| **Icona** | action-settings |
| **Tipo** | Multi-entity ListReport + ObjectPage (**60** route / 60 target in `manifest.json`, misurato 2026-08-22) |
| **Servizio OData** | `/odata/v4/orchestrator/` |

### 11.1 Scopo

Configurazione centrale di tutti i parametri di sistema, integrazioni esterne, mappature e code list. E l'app di amministrazione tecnica della suite.

### 11.2 Aree di Configurazione

#### 11.2.1 Parametri di Sistema (`SystemParameters`)

Coppie chiave-valore (`ParamKey` / `ParamValue`) organizzate per categoria. Le categorie sono **24**, non
5 — l'elenco autorevole è `db/data/sap.passive.invoice-ParameterCategories.csv`:

`AI` · `ALERT` · `APPROVAL` · `ARCHIVE` · `AUDIT` · `BP` · `COMPLIANCE` · `DMS` · `DUPLICATE` ·
`EXTRACTION` · `FISCAL` · `GENERALE` · `INBOUND` · `INFRASTRUCTURE` · `INTEGRATION` · `MATCHING` ·
`MESSAGING` · `MONITORING` · `NOTIFICATION` · `RISK` · `SECURITY` · `SLA` · `TECHNICAL` · `WORKFLOW`

(`GENERALE` è il fallback per i parametri non classificati.) Qualche esempio per orientarsi:

| Categoria | Esempi di Parametri |
|-----------|-------------------|
| INTEGRATION | Timeout lettura/scrittura verso S/4 (`INTEGRATION_REMOTE_TIMEOUT_*_MS`), soglie del circuit breaker (`INTEGRATION_CB_*`), whitelist client SAC |
| WORKFLOW | Adapter di approvazione (`WORKFLOW_ADAPTER`), parametri BPA, monitoraggio S/4 Flexible Workflow |
| RISK | Soglie di rischio alto/medio, pesi dello score |
| ARCHIVE | Provider di conservazione, retention e relativa decorrenza (`RETENTION_ANCHOR`) |
| AI | Soglia di confidenza DOX, modello di estrazione |

**Ogni parametro esiste in due forme**: la riga con `CompanyCode = ''` è il **default globale**, valido
per tutte le società; una riga con `CompanyCode` valorizzato è l'override di quella singola società e
vince sul globale. Un parametro con `IsSecret = true` è cifrato a riposo e non compare mai nel bundle di
trasporto (§11.2.6).

**Workflow:**
1. Aprire "Configurazione" dal Launchpad
2. I parametri sono già pre-popolati con valori default
3. Cercare il parametro per nome o categoria
4. Modificare il valore
5. Salvare

#### 11.2.2 Connettori Servizi (`ServiceConnectors`)

Configurazione delle integrazioni con servizi esterni.

**Campi:**

| Campo | Descrizione |
|-------|-------------|
| Nome | Identificativo connettore |
| Tipo Servizio | S4HANA / BTP_SERVICE / EXTERNAL_API / ... |
| URL | Endpoint del servizio |
| Versione OData | V2 / V4 |
| Tipo Autenticazione | OAUTH2 / BASIC / CERTIFICATE / ... |
| Attivo | Flag attivazione |

**Azione speciale:**
- `Test Connessione` - Verifica raggiungibilità e autenticazione del servizio. Ritorna: successo/fallimento, messaggio, entity sets trovati, tempo di risposta in ms.

**Workflow:**
1. Selezionare "Connettori Servizi"
2. Creare o modificare un connettore
3. Compilare URL, tipo auth, credenziali
4. Cliccare "Test Connessione" per verificare
5. Se il test ha successo: attivare il connettore
6. Salvare

#### 11.2.3 Tolleranze di Matching (`MatchingTolerances`)

Configurazione delle soglie di tolleranza per il 3-Way Match per company code.

**Campi:**
- Società, tolleranza quantità (%), tolleranza prezzo (%), tolleranza importo assoluto

#### 11.2.4 Campi Custom (`CustomFieldDefinitions`)

Estensione dinamica del modello dati con campi personalizzati.

#### 11.2.5 Code List (Dati Master)

Tabelle di riferimento per tutti i dropdown dell'applicazione. Ogni code list ha codice, nome e
descrizione in **due** lingue: l'italiano nel file base (è la lingua di default della piattaforma,
`cds.i18n.default_language: 'it'`) e l'inglese nel file `sap.passive.invoice-<CodeList>_texts.csv`. **Non esiste il tedesco**:
`de` non compare in nessuno dei `_texts.csv`.

**Code List disponibili:**
- Stati Elaborazione, Stati Match, Livelli Rischio
- Canali Acquisizione, Canali Inbound
- Categorie Fattura, Categorie Parametri
- Stati Workflow, Stati Eccezione, Severità Eccezione
- Risultati 3-Way Match, Stati Duplicati
- Stati Validazione Fiscale, Stati Archiviazione
- Stati Cattura, Stati Sincronizzazione
- Stati Messaggi Inbound, Stati Lotto Archiviazione

**Workflow per modificare una Code List:**
1. Navigare alla code list desiderata (es. "Stati Elaborazione")
2. Cliccare "Crea" per aggiungere un nuovo valore
3. Inserire codice, nome e descrizione nelle 2 lingue (IT + EN)
4. Salvare
5. Il nuovo valore sarà immediatamente disponibile nei dropdown di tutte le app

#### 11.2.6 Trasporto Configurazione

Scheda **Trasporto**. Sposta la configurazione fra ambienti (SVILUPPO → QA → PRODUZIONE) come file JSON
unico. Contiene tre pannelli operativi — *Esporta Configurazione*, *Importa Configurazione*,
*Risultato Importazione* — più *Storico Trasporti (ultimi 50)*.

> **I due pulsanti del pannello Trasporto operano su scope globale.** Non inviano un codice società, e
> lo scope globale richiede il ruolo **SuperAdmin**: un `Admin` o `AdminConfig` che li usa riceve
> l'errore
>
> ```
> Operazione su scope GLOBAL richiede il ruolo SuperAdmin. Gli Admin devono specificare companyCode della loro società.
> ```
>
> Per un trasporto limitato alla propria società serve invocare le azioni via OData passando
> `companyCode` — vedi [CONFIGURATION_GUIDE.md §11](CONFIGURATION_GUIDE.md#11-trasporto-della-configurazione-exportimport).

**Esportazione:**
1. Compilare il campo *Ambiente sorgente (es. DEV)* — è solo un'etichetta che finisce nel bundle e nel
   nome del file, non seleziona nulla. Default `DEV`.
2. Premere **Esporta Configurazione**: si apre una nuova scheda con il file
   `config-transport-<ambiente>-<data>.json`, da salvare.
3. Il messaggio di conferma riporta quante entità e quante righe sono state esportate.

I valori dei parametri contrassegnati come segreti **non** sono nel file (vengono azzerati per
costruzione) e vanno reimpostati a mano sull'ambiente di destinazione dopo ogni importazione.

**Importazione:**
1. Selezionare il file col campo *Seleziona file bundle JSON…*
2. Premere **Importa Configurazione** e confermare il dialogo *Conferma importazione*.
3. Leggere il pannello **Risultato Importazione**: entità importate, righe importate e — riga
   **`Ignorate:`** — le entità che il sistema ha **deliberatamente non applicato**.

Quella riga è la sola traccia visibile di un caso frequente: se l'importazione non viene eseguita da un
SuperAdmin, il **catalogo dei controlli di governance** (`ProcessStepCheck`) viene ignorato e compare
come

```
Ignorate: ProcessStepCheck (richiede SuperAdmin: catalogo di governance globale)
```

L'esito resta **Importazione completata**: nessun errore, ma le modifiche al catalogo non sono arrivate.
Se il rilascio contiene nuovi controlli o cambi di severità predefinita, va ripetuto con un'utenza
SuperAdmin.

Se invece il bundle tenta di **disabilitare un gate di fase** su una singola società, l'importazione
viene rifiutata per intero (nessuna riga applicata) con il messaggio:

```
Il controllo COST_ALLOCATION_REQUIRED è un gate di fase e non può essere disabilitato per una singola
società: il blocco resterebbe attivo comunque sulle fatture. Per allentarlo, abbassa la severità da
ERRORE ad AVVISO.
```

**Nota sull'avviso di conferma.** L'importazione **non cancella** nulla: aggiorna le righe esistenti e
inserisce quelle mancanti. Una configurazione presente sull'ambiente di destinazione ma assente dal
bundle **resta**, e va rimossa a mano se il rilascio lo richiede.

Il controllo a vuoto (`previewImport`, che elenca in anticipo differenze e motivi di rifiuto **senza
applicare nulla**) non ha un pulsante nell'app: è disponibile solo via OData. Regole complete e sequenza
di rilascio raccomandata in
[CONFIGURATION_GUIDE.md §11](CONFIGURATION_GUIDE.md#11-trasporto-della-configurazione-exportimport).

---

## 12. Manuale App: Operazioni

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Operazioni |
| **Sottotitolo** | Salute & Sincronizzazione |
| **Icona** | activity-2 |
| **Tipo** | ListReport (monitoring) |
| **Servizio OData** | `/odata/v4/orchestrator/` |

### 12.1 Scopo

Monitoraggio in tempo reale dello stato di sincronizzazione con S/4HANA, salute dei connettori, log dei job batch e stato dei messaggi inbound.

### 12.2 Stati di Sincronizzazione (`SyncStates`)

**Colonne:**

| Colonna | Descrizione |
|---------|-------------|
| Società | Company code |
| Ultimo Stato Sync | Successo/Fallito/In corso |
| Ultima Sync | Data e ora |
| Fatture Processate | Conteggio nell'ultima sync |
| Errori | Conteggio errori |
| Durata | Tempo di elaborazione |

### 12.3 Snapshot Billing (`BillingSnapshots`)

Storici dei dati di consumo per la fatturazione della piattaforma.

### 12.4 Contatori Live (`BillingCountersLive`)

Contatori in tempo reale per company code e canale.

### 12.5 Messaggi Inbound (`InboundMessages`)

Log di tutti i messaggi ricevuti dai canali di acquisizione con stato di elaborazione.

### 12.6 Workflow Operativo

1. Aprire "Operazioni" dal Launchpad
2. Verificare lo stato dell'ultima sincronizzazione per ogni società
3. Se una sync è fallita: controllare il conteggio errori e i dettagli
4. Monitorare i contatori live per verificare il flusso in tempo reale
5. Per triggare una sync manuale: utilizzare l'azione `syncInvoices(companyCode)` dal servizio

---

## 13. Manuale App: Approvazioni

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Approvazioni |
| **Sottotitolo** | Coda approver-centric per workflow PENDING |
| **Path** | `/sap.btp.fiori.ui5.passiveinvoiceapprovals/index.html` (l'app si monta sul suo `sap.app.id`, non sul nome cartella) |
| **Tipo** | Worklist |
| **Servizio OData** | `/odata/v4/orchestrator/` |
| **Audience** | Approver, ApproverManager, ApproverTax, ApproverSenior, ApproverDirector, ApproverCFO |

### 13.1 Scopo

Coda dedicata al ruolo Approver (e specializzazioni gerarchiche) che mostra i `InvoiceWorkflowItem`
assegnati all'utente corrente. Riduce il rumore della app `Fatture Passive` (che mostra TUTTE le fatture,
inclusi gli stati non-approver).

> **La inbox filtra `Status = 'IN_APPROVAL'`, e solo quello** (decisione di architettura, audit
> 2026-04-28 round 5). Prima includeva anche `PENDING`, `ESCALATED` e `DELEGATED`, ma i flag `Can*` e gli
> adapter di workflow richiedono `IN_APPROVAL` per agire: quelle righe comparivano «visibili ma senza
> pulsanti». Il contratto runtime è stato convergente nell'altra direzione — delega ed escalation
> **mantengono** `Status = IN_APPROVAL` e cambiano solo `AssignedTo` / `DelegatedFrom` — e `PENDING` non
> è più prodotto né da `requestExceptionOverride` né dalla catena multi-livello.

### 13.2 Entità Filtrate

| Entità | Filtro applicato |
|--------|------------------|
| `InvoiceWorkflowItem` | Variante **Inbox aperta**: `Status = 'IN_APPROVAL'`, righe assegnate all'utente (`AssignedTo`). Altre varianti pronte: *SLA violato*, *Approvazioni di fase aperte*, *Override eccezioni aperti* |
| `Invoices` (READ join) | Header info per row visibility |

> Il campo si chiama **`DelegatedFrom`** (chi ha delegato) e non `DelegatedTo`: `delegateApproval`
> **riassegna `AssignedTo`** al delegato e annota il delegante in `DelegatedFrom`, quindi lo stesso
> filtro su `AssignedTo` copre sia le righe proprie sia quelle delegate. Un filtro su `DelegatedTo`
> non troverebbe nulla — la colonna non esiste.

### 13.3 Azioni Disponibili

| Azione | Effetto |
|--------|---------|
| **approveInvoice** | Approvazione singola, valida soglie ApprovalRule.MaxAmount |
| **rejectInvoice** | Rifiuto + comment obbligatorio, REWORK loop F5→F3 |
| **delegateApproval** | Delega temporanea (con period) ad altro Approver |
| **escalateWorkflow** | Escalation manuale al ApproverManager |
| **approveSelected** | Mass-approve di righe selezionate |

### 13.4 SoD Enforcement

**Mutex Approver vs PostingOfficer**: stesso utente NON può approvare e poi registrare la stessa invoice (eccetto ruolo `OperationalAdmin` esente con auditor sign-off quarterly). Vedi `OIDCAuthStrategy.ts` → `SOD_EXEMPT_ROLES`.

---

## 14. Manuale App: Platform Admin

### Informazioni Generali

| Proprieta | Valore |
|-----------|--------|
| **Titolo** | Platform Admin |
| **Sottotitolo** | Tooling SuperAdmin (cert manager + S3 browser) |
| **Path** | `/passive-invoice-platform/webapp/index.html` |
| **Tipo** | Custom Fiori (multi-section) |
| **Servizio OData** | `/platform-admin` (NON OrchestratorService — service dedicato) |
| **Audience** | SuperAdmin SOLO (service-level `@requires: 'SuperAdmin'`) |
| **Audit** | Ogni azione emette `AuditLogEntry` con `Action='PLATFORM_ADMIN_*'` (SOX-compliant) |

### 14.1 Scopo

App separata per operazioni infrastrutturali che richiedono privilegi cross-company (SuperAdmin). Isolata dal resto della suite per minimizzare la superficie di attacco e per audit forensic dedicato.

### 14.2 Sezione: Certificate Manager

**Funzionalità:**
1. **Upload PEM** — caricamento file `.pem` (X.509 cert + chain) con parsing automatico (issuer, subject, validity, fingerprint SHA-256)
2. **Verifica chain** — controllo che il cert sia firmato dalla CA dichiarata
3. **Test verify** — tentativo di TLS handshake verso un endpoint custom (es. ArchiveLink CS, Conservatore API)
4. **Storage** — encrypted at-rest via `PARAM_ENCRYPTION_KEY`. L'entità si chiama **`Certificate`**
   (`db/schema.cds`), esposta dal servizio come proiezione `Certificates`; `PlatformCertificate` non
   esiste. Azioni disponibili: `uploadCertificate`, `testCertificate` (bound, abilitata solo se il
   certificato ha un `PemContent`), `rotateCertificate`, `runCertificateExpiryCheck`
5. **Quarterly rotation** — runbook `ARCHIVELINK_CERT_ROTATION.md` per cert ArchiveLink, `KYMA_APIRULE_CERT_ROTATION.md` per cert APIRule

### 14.3 Sezione: MinIO / S3 Browser

**Funzionalità:**
1. **Lista bucket** — read-only, scope limitato dai permessi IAM del SA dedicato
2. **Browse oggetti** — listing per prefix con paginazione
3. **Presigned URL** — genera URL firmato (TTL 5min default) per download diretto via browser
4. **Audit** — ogni `LIST_BUCKET` / `GENERATE_PRESIGNED` emette evento `PLATFORM_ADMIN_S3_*`

### 14.4 Limitazioni Intenzionali

- NO write/delete/upload — Platform Admin e solo READ-only sul DMS S3
- NO bulk operations — solo singole interazioni (per ridurre blast radius)
- NO cross-tenant impersonation — service `/platform-admin` rifiuta token con `tenant != system`

---

## 15. Glossario

| Termine | Descrizione |
|---------|-------------|
| **BP** | Business Partner - anagrafica fornitore in S/4HANA |
| **BTP** | SAP Business Technology Platform |
| **CAP** | Cloud Application Programming Model |
| **CDM** | Content Delivery Management (configurazione FLP) |
| **CDS** | Core Data Services (definizione modello dati) |
| **DOX** | SAP Document Information Extraction |
| **FatturaPA** | Formato standard italiano fattura elettronica |
| **FLP** | Fiori Launchpad |
| **GR** | Goods Receipt (entrata merci) |
| **GuidEdocInvoice** | Entità core che mappa GUID e-Document a fattura |
| **NON_PO** | Fattura senza ordine di acquisto |
| **ObjectPage** | Pagina di dettaglio Fiori Elements |
| **OdA** | Ordine di Acquisto (Purchase Order) |
| **PO** | Purchase Order (ordine di acquisto) |
| **SDI** | Sistema di Interscambio (Agenzia delle Entrate) |
| **SES** | Service Entry Sheet (foglio servizi) |
| **Three-Way Match** | Verifica coerenza PO vs Entrata Merci vs Fattura |
| **Touchless** | Elaborazione completamente automatica senza intervento umano |
| **VIM** | Vendor Invoice Management |
