BR-KSA-71Simplified summary invoice does not name the buyer
Mutabiq checks Saudi ZATCA Phase 2 e-invoice XML before you submit it: pre-validation against published ZATCA requirements, not an approval by the authority. This page explains one rule, BR-KSA-71.
Five checks a month on the Free plan. The file is checked in memory and is never stored.
The message ZATCA prints
If the Invoice is a simplified invoice type and is a summary invoice (KSA-2, position 1 and 2 = 02, position 6 = 1),then the buyer name must be present.
What Mutabiq reports
One entry for each way this rule can be reported.
Reported as
What kind of value was found — empty, not_15_digits and the like — never the value itself.
Simplified summary invoice does not name the buyer
Reported asname_element_missingthe name element is missing
What is wrong
The buyer party carries no cbc:RegistrationName under any cac:PartyLegalEntity anywhere below it, so the buyer name is absent. SDK 3.4.8 flags the document under BR-KSA-71 as a warning, not a rejection: the finding is reported without failing the document by itself. This rule is the buyer NAME and not the buyer address, whatever its position in the rule list suggests: it reads cac:AccountingCustomerParty/cac:Party//cac:PartyLegalEntity/cbc:RegistrationName, the same business term BR-KSA-42 reads, through a wider path that reaches any cac:PartyLegalEntity below the buyer party however deeply it is nested. Earlier SDK releases (3.0.8) also required the buyer's cac:Country/cbc:IdentificationCode to be exactly SA, and carried a gate with a typo that made it reachable only on a transaction code with a 6 in its sixth position - a code no conforming invoice carries, so the rule could barely ever fire. SDK 3.4.8 drops the country condition and fixes the gate to the transaction code ZATCA's own message describes (KSA-2 beginning 02, position 6 equal to 1), so this rule now fires on an ordinary simplified summary invoice with no buyer name, whatever the buyer's country.
What to check in your ERP
The buyer name itself is what to check: a simplified invoice's buyer block is usually minimal or absent because the customer is a final consumer, so if you do intend to name the buyer, the name belongs in cac:PartyLegalEntity/cbc:RegistrationName and not in cac:PartyName/cbc:Name, which this check does not read.
Simplified summary invoice's buyer name is empty
Reported asname_emptythe name is present but empty
What is wrong
The buyer party carries the cbc:RegistrationName element below it, but every one of them is empty, so the buyer name has no value. SDK 3.4.8 flags the document under BR-KSA-71 exactly as it does a missing name: as a warning, not a rejection, so the finding is reported without failing the document by itself. Any one non-empty name below the buyer party would satisfy the check, so this note means all of them are blank. This rule is the buyer NAME and not the buyer address, whatever its position in the rule list suggests: it reads cac:AccountingCustomerParty/cac:Party//cac:PartyLegalEntity/cbc:RegistrationName, the same business term BR-KSA-42 reads, through a wider path that reaches any cac:PartyLegalEntity below the buyer party however deeply it is nested. It applies to a simplified summary invoice - the invoice transaction code KSA-2 beginning 02 with position 6 equal to 1 - as ZATCA's own message describes. Earlier SDK releases (3.0.8) carried a gate with a typo that made the rule reachable only on a code with a 6 in that position, and also required the buyer's cac:Country/cbc:IdentificationCode to be exactly SA; SDK 3.4.8 corrects the first and drops the second.
What to check in your ERP
The structure is being written and the value is not, which normally means the export emits the buyer legal entity block for every document while the name comes from a field that is empty for a walk-in or cash customer. Either fill the field or stop emitting the block on documents where there is no named buyer.
The clause that runs
Quoted from the validation-rule stylesheet ZATCA publishes, at the file and line named below. The executed guard is what the check runs; the reported test is what it prints when it fails, and the two are not always the same.
Executed guard
not(exists(//cac:AccountingCustomerParty/cac:Party//cac:PartyLegalEntity/cbc:RegistrationName) and normalize-space(//cac:AccountingCustomerParty/cac:Party//cac:PartyLegalEntity/cbc:RegistrationName)!='')
Reported test
not(exists(//cac:AccountingCustomerParty/cac:Party//cac:PartyLegalEntity/cbc:RegistrationName) and //cac:AccountingCustomerParty/cac:Party//cac:PartyLegalEntity/cbc:RegistrationName !='')
As shipped in ZATCA SDK 3.4.8: the copy quoted here is, byte for byte, the file that release ships. The date in the file name is the name ZATCA gives the file; the rules in it are those of SDK 3.4.8.
A worked example
A synthetic document from the measured test corpus that trips this rule, shown where it differs from one that passed. Mutabiq's report names the class of the value, never the value itself.