Idempotency: prevenire gli invii duplicati

Idempotency nella PSB API di eConnect: come prevenire gli invii duplicati con l'header X-EConnect-DocumentId.

Nell'invio di fatture e altri documenti tramite un'API esiste sempre il rischio di invii duplicati. Un timeout di rete, un riavvio dell'applicazione o un errore imprevisto possono far sì che non si sia certi se un documento sia stato effettivamente elaborato. Senza protezione, si potrebbe inviare nuovamente lo stesso documento, con fatture doppie come conseguenza.

La PSB API offre un meccanismo di idempotency integrato che risolve questo problema. Inviando un documentId univoco con ogni upload, la PSB riconosce i tentativi duplicati e impedisce che lo stesso documento venga elaborato due volte.

Come funziona

Il meccanismo di idempotency si basa sull'header HTTP X-EConnect-DocumentId. Nell'invio di un documento si aggiunge questo header con un valore univoco che identifica il documento.

POST /api/v1/{partyId}/salesInvoice/send HTTP/1.1
Host: psb.econnect.eu
Authorization: Bearer {token}
Content-Type: application/xml
X-EConnect-DocumentId: 550e8400-e29b-41d4-a716-446655440000

<?xml version="1.0" encoding="UTF-8"?>
<Invoice xmlns="urn:oasis:names:specification:ubl:schema:xsd:Invoice-2">
  ...
</Invoice>

La PSB elabora il documento e salva il documentId. Se si invia nuovamente la stessa richiesta (ad esempio con un retry dopo un timeout), la PSB riconosce che il documentId esiste già e restituisce una risposta 409 Conflict invece di elaborare nuovamente il documento.

HTTP/1.1 409 Conflict

Quel 409 non è un messaggio di errore nel senso tradizionale. È una conferma che il documento è stato già elaborato con successo in precedenza. L'applicazione può contrassegnare la richiesta come completata in sicurezza.

Requisiti per il documentId

Il documentId inviato nell'header X-EConnect-DocumentId deve soddisfare alcune condizioni:

RequisitoDescrizioneMinimo 6 caratteriValori più corti vengono rifiutatiNessun carattere specialeCaratteri come @ e _ non sono consentitiUnivoco per documentoOgni documento deve avere un proprio documentId

Importante: non utilizzi mai il numero di fattura come documentId. Un numero di fattura può essere riutilizzato per una nota di credito o una fattura corretta, il che porta a conflitti. Utilizzi invece un UUID/GUID generato per ogni tentativo di invio.

Un UUID è la scelta raccomandata. È garantito univoco e ampiamente supportato in tutti i linguaggi di programmazione.

Goed:   550e8400-e29b-41d4-a716-446655440000  (UUID)
Goed:   DOC2026030800142                       (eigen reeks, mits uniek)
Fout:   INV-2026-001                           (factuurnummer, niet gebruiken)
Fout:   ab@cd                                  (speciale tekens)
Fout:   abc                                    (te kort)
Implementare la logica di retry

L'idempotency diventa particolarmente utile in combinazione con la logica di retry. Se una chiamata API fallisce a causa di un errore di rete o di un errore server 5xx, si desidera ritentare la richiesta senza il rischio di elaborazione duplicata.

L'approccio raccomandato funziona come segue:

  1. Generare un documentId univoco (UUID) prima di inviare la richiesta.
  2. Inviare il documento con l'header X-EConnect-DocumentId.
  3. Se si riceve un 200 OK: il documento è stato elaborato, completato.
  4. Se si riceve un 409 Conflict: il documento era già stato elaborato in un tentativo precedente, completato.
  5. Se si riceve un errore 5xx o un timeout: attendere e ripetere la richiesta con lo stesso documentId.
  6. Se si riceve un errore 4xx (diverso da 409): c'è un problema con la richiesta stessa. Il retry non ha senso, l'errore deve essere risolto.

Suggerimento: utilizzi l'exponential backoff per i retry. Cominci con un breve tempo di attesa (ad esempio 1 secondo) e lo raddoppi ad ogni tentativo successivo, fino a un massimo di ad esempio 60 secondi. La PSB stessa applica una politica di retry di massimo 8 tentativi nell'arco di circa 35 ore per errori 5xx.

Quali endpoint supportano l'idempotency?

L'header X-EConnect-DocumentId è supportato su tutti gli endpoint con cui si caricano documenti nella PSB. I principali sono:

EndpointFunzionePOST /api/v1/{partyId}/salesInvoice/sendInvio fattura di venditaPOST /api/v1/{partyId}/generic/sendInvio documento generico (self-billing, despatch advice)POST /api/v1/{partyId}/purchaseOrder/sendInvio ordine

Per gli endpoint di ricezione (download di documenti) l'idempotency non è applicabile: il download di un documento è per natura idempotente, poiché non modifica dati.

L'idempotency è un meccanismo semplice con un grande effetto. Inviando costantemente un X-EConnect-DocumentId con ogni upload di documento, ci si protegge contro gli invii duplicati. In combinazione con la logica di retry e l'exponential backoff, si costruisce un'integrazione robusta resistente a problemi di rete e errori temporanei del server.

In breve Invii con ogni upload di documento l'header X-EConnect-DocumentId con un UUID univoco. In caso di retry, la PSB restituisce 409 Conflict se il documento è già stato elaborato. Non utilizzi mai il numero di fattura come documentId.

Consulti la documentazione API completa