If you sell in Italy: when an invoice is required and when it isn't, which data to collect at checkout, who should number invoices, what happens with returns and rejections — and where almost every integration breaks.
by Nadia Maar ·
In many online stores an invoice is born like this: an order arrives, someone opens the accounting system, retypes the name, lines and amounts, and sends it. It works while there are ten orders a day. At a hundred it's a full-time job that produces full-time errors: a wrong VAT number, a missing recipient code, a credit note forgotten after a return.
In Italy every business invoice travels as an XML file through the Exchange System — the Sistema di Interscambio, or SdI — run by the tax authority. Connecting the store to it is one of the most measurable jobs there is, because it replaces a repetitive task with clear rules. It's also one of the worst done, because the people who build it rarely know the tax rules, and the people who know the rules don't build software. Here is the technical side, with the rules you need to build it properly.
Before connecting anything, it pays to know what has to happen. For a store selling physical goods that get shipped — what Italian rules call indirect e-commerce — the essentials look like this:
| Who buys | What is required |
|---|---|
| A consumer in Italy | No invoice and no receipt, unless the customer asks for an invoice. Takings are recorded; how is something to agree with your accountant. |
| A consumer who asks for an invoice | An e-invoice with their tax code, sent through the SdI. |
| A business with a VAT number | Always an e-invoice, through the SdI, with the customer's recipient code or certified email (PEC). |
| A consumer in another EU country | Above €10,000 a year of EU distance sales, the customer's country VAT applies, usually declared through the One-Stop Shop (OSS). |
This is an article on how to build the integration, not tax advice. Rules change, and your case — digital goods, special schemes, cross-border sales — needs confirming with an accountant before anyone writes a line of code. The software should carry out their instructions, not replace them.
Half of all invoicing problems start at checkout. If the store doesn't ask for the right data at the right time, someone has to chase it by email — and some customers will never reply.
In the onboarding demo the check-digit validation runs inside the form: a wrong number stops there, not at an SdI rejection.
The single most important rule of the whole integration: invoices must have one source of numbering. If the store numbers its own and the accounting system numbers its own, sooner or later two documents will share a number or the sequence will have a gap — and fixing that at year end is an accountant's job, billed like one.
The link between the two must be idempotent: the same order sent twice — it happens, when a connection drops halfway — must produce a single invoice. You get there with a key: the order ID travels with the request, and the invoicing side returns the invoice already issued instead of numbering another.
// One invoice per order, even if the request arrives twice.
export async function invoiceForOrder(order: Order) {
const existing = await db.invoices.byOrder(order.id)
if (existing) return existing // already issued: no duplicates
// A consumer who didn't ask for one: record the takings, no invoice.
if (!order.customer.wantsInvoice && !order.customer.vatNumber) return null
return db.transaction(async tx => {
const number = await tx.numbering.next(yearOf(order.date))
const invoice = await tx.invoices.create({ orderId: order.id, number, lines: order.lines })
await tx.sendQueue.add(invoice.id) // sending happens later, outside the transaction
return invoice
})
}Numbering and saving are atomic: both happen or neither does. Sending isn't — the SdI can reply late, and an invoice that already has a number must not vanish because the network dropped. It goes into a queue, and the queue retries.
The integration doesn't end when the invoice goes out. The situations that test it come later, and need planning up front:
If invoicing is manual today, you don't need to build it all at once. The order that makes most sense, by effort against hours given back:
The integration doesn't have to be written from scratch: the main invoicing packages and many accounting systems expose an interface for receiving documents. The real work is the piece in the middle — who numbers, what gets invoiced, what happens when something goes wrong — and that is what needs designing.
The sum is quick: invoiced orders in a month, times the minutes it takes to retype one, plus the time spent fixing rejections. That number tells you whether the integration is worth it, and how fast it pays back.
The free audit does exactly this sum: we look at how orders and invoices run today, where the hours go, and what automating it would cost. You get a cost and payback estimate — even if you then decide not to go ahead.
No. For goods shipped to consumers you need neither an invoice nor a receipt, unless the customer asks for an invoice; takings are recorded. Businesses with a VAT number always get an e-invoice through the SdI. Your own case should be confirmed with an accountant.
For a business: company name, VAT number, and a seven-character recipient code or certified email (PEC). For a consumer who asks for an invoice: their tax code. It pays to validate the format inside the form, so an error never reaches a rejection.
Only one of them, always the same — usually the accounting or invoicing software. The store records the order and passes the data, and the sequence has no gaps or duplicates.
A rejected file counts as never issued: it has to be corrected and resent quickly — within five days, according to the tax authority's practice, keeping the same number and date. That's why the integration must alert someone the same day.