PHP code example of saleh7 / php-zatca-xml

1. Go to this page and download the library: Download saleh7/php-zatca-xml library. Choose the download type require.

2. Extract the ZIP file and open the index.php.

3. Add this code to the index.php.
    
        
<?php
require_once('vendor/autoload.php');

/* Start to develop here. Best regards https://php-download.com/ */

    

saleh7 / php-zatca-xml example snippets


use Saleh7\Zatca\CertificateBuilder;
use Saleh7\Zatca\CertificateBuilderException;

try {
    (new CertificateBuilder())
        ->setOrganizationIdentifier('312345678901233') // The Organization Identifier must be 15 digits, starting andending with 3
        // string $solutionName .. The solution provider name
        // string $model .. The model of the unit the stamp is being generated for
        // string $serialNumber .. # If you have multiple devices each should have a unique serial number
        ->setSerialNumber('Saleh', '1n', 'SME00023')
        ->setCommonName('My Organization') // The common name to be used in the certificate
        ->setCountryName('SA') // The Country name must be Two chars only
        ->setOrganizationName('My Company') // The name of your organization
        ->setOrganizationalUnitName('IT Department') // A subunit in your organizatio
        ->setAddress('Riyadh 1234 Street') // like Riyadh 1234 Street 
        ->setInvoiceType(1100)// # Four digits, each digit acting as a bool. The order is as follows: Standard Invoice, Simplified, future use, future use 
        ->setProduction(false)// true = Production |  false = Testing
        ->setBusinessCategory('Technology') // Your business category like food, real estate, etc
        
        ->generateAndSave('output/certificate.csr', 'output/private.pem');
        
    echo "Certificate and private key saved.\n";
} catch (CertificateBuilderException $e) {
    echo "Error: " . $e->getMessage() . "\n";
    exit(1);
}

use Saleh7\Zatca\ZatcaAPI;
use Saleh7\Zatca\Exceptions\ZatcaApiException;

$zatcaClient = new ZatcaAPI('sandbox');

try {
    $otp = "123123"; // The OTP received from ZATCA
    $certificatePath = __DIR__ . '/output/certificate.csr';
    
    // Load the generated CSR
    $csr = $zatcaClient->loadCSRFromFile($certificatePath);
    
    // Request the compliance certificate from ZATCA
    $complianceResult = $zatcaClient->requestComplianceCertificate($csr, $otp);
    
    // Display the returned certificate and API secret
    echo "Compliance Certificate:\n" . $complianceResult->getCertificate() . "\n";
    echo "API Secret: " . $complianceResult->getSecret() . "\n";
    echo "Request ID: " . $complianceResult->getRequestId() . "\n";

    // Save the certificate details to a JSON file
    $outputFile = __DIR__ . '/output/ZATCA_certificate_data.json';
    $zatcaClient->saveToJson(
        $complianceResult->getCertificate(),
        $complianceResult->getSecret(),
        $complianceResult->getRequestId(),
        $outputFile
    );
    
    echo "Certificate data saved to {$outputFile}\n";

} catch (ZatcaApiException $e) {
    echo "API Error: " . $e->getMessage();
} catch (\Exception $e) {
    echo "Error: " . $e->getMessage();
}

use Saleh7\Zatca\{
    SignatureInformation, UBLDocumentSignatures, ExtensionContent, UBLExtension, UBLExtensions, Signature, 
    InvoiceType, AdditionalDocumentReference, TaxScheme, PartyTaxScheme, Address, LegalEntity, Delivery, 
    Party, PaymentMeans, TaxCategory, AllowanceCharge, TaxSubTotal, TaxTotal, LegalMonetaryTotal, 
    ClassifiedTaxCategory, Item, Price, InvoiceLine, GeneratorInvoice, Invoice, UnitCode, 
    OrderReference, BillingReference, Contract, Attachment
};

// --- Invoice Type ---
$invoiceType = (new InvoiceType())
    ->setInvoice('standard') // 'standard' or 'simplified'
    ->setInvoiceType('invoice') // 'invoice', 'debit', or 'credit', 'prepayment'
    ->setIsThirdParty(false) // Third-party transaction
    ->setIsNominal(false) // Nominal transaction
    ->setIsExportInvoice(false) // Export invoice
    ->setIsSummary(false) // Summary invoice
    ->setIsSelfBilled(false); // Self-billed invoice

// --- Supplier & Customer Information ---
$taxScheme = (new TaxScheme())->setId("VAT");

$partyTaxSchemeSupplier = (new PartyTaxScheme())->setTaxScheme($taxScheme)->setCompanyId('311111111101113');
$partyTaxSchemeCustomer = (new PartyTaxScheme())->setTaxScheme($taxScheme);

$address = (new Address())
    ->setStreetName('Prince Sultan Street')
    ->setBuildingNumber("2322")
    ->setPlotIdentification("2223")
    ->setCitySubdivisionName('Riyadh')
    ->setCityName('Riyadh')
    ->setPostalZone('23333')
    ->setCountry('SA');

$legalEntity = (new LegalEntity())->setRegistrationName('Acme Widget’s LTD');

$supplierCompany = (new Party())
    ->setPartyIdentification("311111111111113")
    ->setPartyIdentificationId("CRN")
    ->setLegalEntity($legalEntity)
    ->setPartyTaxScheme($partyTaxSchemeSupplier)
    ->setPostalAddress($address);

$supplierCustomer = (new Party())
    ->setPartyIdentification("311111111111113")
    ->setPartyIdentificationId("NAT")
    ->setLegalEntity($legalEntity)
    ->setPartyTaxScheme($partyTaxSchemeCustomer)
    ->setPostalAddress($address);

// --- Invoice Items & Pricing ---
$classifiedTax = (new ClassifiedTaxCategory())->setPercent(15)->setTaxScheme($taxScheme);
$productItem = (new Item())->setName('Pencil')->setClassifiedTaxCategory($classifiedTax);
$price = (new Price())->setUnitCode(UnitCode::UNIT)->setPriceAmount(2);

$lineTaxTotal = (new TaxTotal())->setTaxAmount(0.60)->setRoundingAmount(4.60);

$invoiceLine = (new InvoiceLine())
    ->setUnitCode("PCE")
    ->setId(1)
    ->setItem($productItem)
    ->setLineExtensionAmount(4)
    ->setPrice($price)
    ->setTaxTotal($lineTaxTotal)
    ->setInvoicedQuantity(2);

$invoiceLines = [$invoiceLine];

// --- Tax Totals ---
$taxSubTotal = (new TaxSubTotal())->setTaxableAmount(4)->setTaxAmount(0.6)->setTaxCategory($classifiedTax);
$taxTotal = (new TaxTotal())->addTaxSubTotal($taxSubTotal)->setTaxAmount(0.6);

// --- Legal Monetary Total ---
$legalMonetaryTotal = (new LegalMonetaryTotal())
    ->setLineExtensionAmount(4)
    ->setTaxExclusiveAmount(4)
    ->setTaxInclusiveAmount(4.60)
    ->setPrepaidAmount(0)
    ->setPayableAmount(4.60)
    ->setAllowanceTotalAmount(0);

// --- Build the Invoice ---
$invoice = (new Invoice())
    ->setUUID('3cf5ee18-ee25-44ea-a444-2c37ba7f28be')
    ->setId('SME00023')
    ->setIssueDate(new DateTime())
    ->setIssueTime(new DateTime())
    ->setInvoiceType($invoiceType)
    ->setInvoiceCurrencyCode('SAR')
    ->setTaxCurrencyCode('SAR')
    ->setAccountingSupplierParty($supplierCompany)
    ->setAccountingCustomerParty($supplierCustomer)
    ->setTaxTotal($taxTotal)
    ->setLegalMonetaryTotal($legalMonetaryTotal)
    ->setInvoiceLines($invoiceLines);
    // ......
// --- Generate XML ---
try {
    $generatorXml = new GeneratorInvoice();
    $outputXML = $generatorXml->invoice($invoice);
    
    // Save the XML to a file
    $filePath = __DIR__ . '/output/unsigned_invoice.xml';
    file_put_contents($filePath, $outputXML);
    
    echo "Invoice XML saved to: " . $filePath . "\n";

} catch (\Exception $e) {
    echo "An error occurred: " . $e->getMessage() . "\n";
    exit(1);
}

use Saleh7\Zatca\Helpers\Certificate;
use Saleh7\Zatca\InvoiceSigner;

// Load the unsigned invoice XML
$xmlInvoice = file_get_contents(__DIR__ . '/output/unsigned_invoice.xml');

// Load the compliance certificate data from the JSON file
$json_certificate = file_get_contents(__DIR__ . '/output/ZATCA_certificate_data.json');

// Decode the JSON data
$json_data = json_decode($json_certificate, true, 512, JSON_THROW_ON_ERROR);

// Extract certificate details
$certificate = $json_data[0]['certificate'];
$secret = $json_data[0]['secret'];

// Load the private key
$privateKey = file_get_contents(__DIR__ . '/output/private.pem');
$cleanPrivateKey = trim(str_replace(["-----BEGIN PRIVATE KEY-----", "-----END PRIVATE KEY-----"], "", $privateKey));

// Create a Certificate instance
$certificate = new Certificate(
    $certificate,
    $cleanPrivateKey,
    $secret
);

// Sign the invoice
$signedInvoice = InvoiceSigner::signInvoice($xmlInvoice, $certificate);

// Save the signed invoice
InvoiceSigner::signInvoice($xmlInvoice, $certificate)->saveXMLFile('/output/signed_invoice.xml');
bash
composer