Troubleshooting
Start here
Holding → Log records every call: the endpoint, the status, how long it took, and — if you have payload logging on — exactly what was sent and what came back. Almost every question below is answered faster by opening the failing document's detail screen and reading the payload than by reasoning about it.
The document is in Holded but I cannot find it
It was filed as a draft. A draft is invisible in Sales → Invoices, on the contact and in search; it exists, but nothing in the interface will show it to you.
Turn on Approve documents on creation. For the ones already filed, find them through Holded's drafts view and approve them there — Holding cannot approve a document after the fact.
“This document is approved in Holded and can no longer be edited”
That is Holded's rule, not Holding's: approval locks a document permanently. To change one, issue a credit note, or delete it in Holded and use Forget on the document detail screen so the order can be sent again.
The totals do not match
The document is flagged, holdedTotal sits next to total on the detail screen, and both are on
the Documents index under With warnings.
The usual cause is the Line subtotal setting: Holded reads a line's subtotal as the price per
unit, and some accounts behave as though it were the line total. If Holded's total is your order
total multiplied by the quantities, flip that setting, delete the document in Holded, Forget
it, and send again.
If it is out by a cent or two, look at the Ajuste line in the payload — an adjustment from another plugin that Holding absorbed rather than dropped.
VAT is wrong on the invoice
Remember what Holding will and will not do: it records what Commerce charged. If the invoice says 21% and it should say 0%, then Commerce charged 21% — Holding's job was to notice, and the warning on the document is it noticing.
Fix the Commerce tax rules, then re-issue. holding/sync/preview <order> prints the classification
and its reasoning, which tells you which rule fired and why.
If the classification is wrong rather than the charge:
- Expected reverse charge, got domestic — the VAT number failed its format check, or VIES rejected it, or VIES could not be reached and your fallback is Charge VAT. The reasoning line says which.
- Expected exempt, got Spanish VAT on a Canarian order — check the postcode is really 35xxx or 38xxx and that excluded territories is on.
- Expected OSS, got home VAT — OSS is off, or no rate is configured for that country.
“No Holded contact could be found or created for this customer”
Either Create contacts is off and Holded has no contact matching the tax id or the email, or
the contact call itself failed — check the log for the contacts request.
Holding matches on the first page of results Holded returns for a filtered query. Holded ignores filter parameters it does not recognise rather than rejecting them, so on a very large contact list a match can be missed and a duplicate created. If that happens, delete the duplicate in Holded and the mapping will heal on the next sync.
Payments are not showing on the invoice
- Check Register payments is on.
- Only successful
purchaseandcapturetransactions count. An authorisation that was never captured is not money received. - A transaction is registered exactly once, ever. If you deleted the payment inside Holded, Holding will not add it again — the row in its own table says the job is done.
The payment is there but filed under the wrong account
Holded's /pay endpoint records the payment method; the bank account is a separate call. Map
both under Payments, or per gateway. If the second call failed you will see a warning in the
log saying the payment was recorded but could not be filed under its bank account.
Every call fails with an authentication error
- The token needs invoicing permissions.
- The API is not available on Holded's free plan.
- Press Test the connection — it reports which header style your token accepted.
- If the key is an env variable, check it resolves: an unset
$HOLDED_API_KEYreads as an empty key and every call fails identically.
Calls stop part-way through a big backfill
Holded meters API use by plan, over a month. Hitting that ceiling is not a rate limit you can wait out for a minute — it is the month's allowance.
Lower Calls per minute, and backfill in batches with --limit. Each document costs roughly
three calls: the contact, the document, the read-back.
Stock differences are reported but never applied
That is the default. Set What a stock read does to apply only if Holded is genuinely the authority for your stock. Applying also needs Commerce 5.3 or later, where stock moved into the inventory system; below that Holding reports and says so rather than pretending.
A document failed and nothing retried it
Retries stop at the Attempts ceiling. php craft holding/sync/retry picks up everything that
failed and has attempts left — put it on cron. Past that ceiling a document waits for a human on
purpose: something that has failed five times is not going to succeed on the sixth without
somebody looking at it.
The order screen panel is missing
It renders through Commerce's own order-edit template hook, and needs the View Holded documents permission. If another plugin's hook on the same screen has an error, Craft may not get as far as Holding's.