Appearance
Integration Service — ZATCA E-Invoicing
The Integration service implements Saudi Arabia's mandatory e-invoicing requirements as defined by ZATCA (Zakat, Tax and Customs Authority — هيئة الزكاة والضريبة والجمارك).
Overview
| Property | Value |
|---|---|
| Service | Integration.Apis |
| CAE placement | Private CAE |
| Source | Platforms/Src/InfrastructureServices/Integration/ |
| NuGet packages | Microtec.Zatca.Integration, Microtec.Zatca.Infrastructure |
| Regulatory body | ZATCA (Saudi Arabia) |
| Standard | UBL 2.1 XML, CSID certificates |
What is ZATCA?
ZATCA is the Saudi government authority responsible for tax collection and customs. As part of Vision 2030, ZATCA mandated a phased e-invoicing (Fatoorah / فاتورة) programme:
| Phase | Scope | Effective |
|---|---|---|
| Phase 1 — Generation | Taxpayers must generate and store structured electronic invoices (offline) | December 2021 |
| Phase 2 — Integration | Invoices must be cryptographically signed and submitted to ZATCA in real time | Rolled out from January 2023 by taxpayer tier |
Microtec ERP supports both phases.
Architecture
The Integration service acts as the dedicated ZATCA adapter. The ERP sales module calls it via the internal public API client (IIntegrationPublicApi) rather than calling ZATCA directly.
NuGet Packages
| Package | Responsibility |
|---|---|
Microtec.Zatca.Integration | ZATCA HTTP client, request/response models, UBL XML builders |
Microtec.Zatca.Infrastructure | Certificate management, cryptographic signing, storage adapters |
Both packages are published to the private Azure DevOps NuGet feed.
IZatcaService Interface
csharp
public interface IZatcaService
{
/// <summary>
/// Onboard a new device (cryptographic unit) with ZATCA.
/// Returns the Compliance CSID (CCSID).
/// </summary>
Task<OnboardingResult> OnboardDeviceAsync(
OnboardingRequest request,
CancellationToken ct = default);
/// <summary>
/// Submit an invoice for clearance (B2B, > SAR 1,000).
/// ZATCA validates and returns a cleared UUID.
/// </summary>
Task<ClearanceResult> ClearInvoiceAsync(
ZatcaInvoice invoice,
CancellationToken ct = default);
/// <summary>
/// Report an invoice to ZATCA (B2C, simplified invoices).
/// Does not require prior clearance.
/// </summary>
Task<ReportingResult> ReportInvoiceAsync(
ZatcaInvoice invoice,
CancellationToken ct = default);
/// <summary>
/// Check the compliance status of an existing CSID.
/// </summary>
Task<ComplianceStatus> CheckComplianceAsync(
string csid,
CancellationToken ct = default);
}Device Onboarding Flow
Before submitting invoices, each tenant must register a cryptographic stamp identity (CSID) with ZATCA:
The OTP is a one-time password obtained by the tenant admin from the ZATCA Fatoorah portal.
Invoice Submission Flow
Phase 2 — Clearance (B2B invoices above SAR 1,000)
Phase 2 — Reporting (B2C simplified invoices)
Same flow as clearance, but uses the /invoices/reporting ZATCA endpoint instead. No real-time validation response — ZATCA batch-validates reported invoices asynchronously.
Invoice Statuses
| Status | Meaning |
|---|---|
Draft | Invoice created in ERP but not yet submitted |
Pending | Submitted to ZATCA, awaiting response |
Cleared | ZATCA confirmed clearance (B2B) |
Reported | ZATCA confirmed receipt (B2C simplified) |
Rejected | ZATCA returned validation errors |
Error | Submission failed (network, certificate, or system error) |
Configuration
json
// appsettings.json (Integration.Apis)
{
"Zatca": {
"BaseUrl": "https://gw-fatoorah.zatca.gov.sa/e-invoicing/developer-portal",
"Environment": "Sandbox",
"ApiVersion": "V2"
}
}| Key | Values | Description |
|---|---|---|
Zatca:Environment | Sandbox, Production | Selects ZATCA endpoint |
Zatca:BaseUrl | URL | Override the base URL (used for sandbox/staging) |
Zatca:ApiVersion | V2 | ZATCA API version |
Sandbox vs Production
Always use Sandbox in dev/stage environments. Production CSIDs are tied to the tenant's ZATCA account and will be revoked if misused.
Error Handling
ZATCA returns structured XML validation errors. These are mapped to the standard ApiResponse envelope:
json
{
"success": false,
"messageCode": 3006,
"message": "ZATCA validation failed: [BT-5] Invoice date cannot be in the future",
"data": {
"zatcaErrors": [
{ "code": "BT-5", "message": "Invoice date cannot be in the future" }
]
}
}Common ZATCA error categories:
| ZATCA Error Category | Typical Cause |
|---|---|
BT-* | Invoice field validation (amount, date, VAT number) |
BG-* | Invoice group validation (missing sections) |
CertificateExpired | PCSID has expired — re-onboard required |
DuplicateInvoice | Same invoice UUID submitted twice |
Related Resources
- ZATCA Fatoorah developer portal:
https://zatca.gov.sa/en/E-Invoicing - UBL 2.1 specification used by ZATCA:
https://docs.oasis-open.org/ubl/os-UBL-2.1/ - Internal service:
Platforms/Src/InfrastructureServices/Integration/ - NuGet source:
Platforms/Src/InfrastructureServices/Zatca/