Skip to main content New EU e-invoicing mandate from 2027 - Kontier issues XRechnung & ZUGFeRD natively
Developers

The API is the product.

Five calls from an empty organization to the first compliant invoice. One data model for finance, engineering and ops: documented, versioned, replay-safe.

Open the API reference →
REST · v1 OpenAPI 3.0 SDKs TS · Go · Python EU-only · GDPR-native
Quick start

Five calls to the first invoice.

No setup wizard, no console clicking. Everything Kontier can do is an API call. This is the shortest path.

  1. 01
    customer.created

    Create the customer

    customer_type drives the tax treatment. For BUSINESS in the EU the VAT ID is mandatory, and the VIES check runs automatically.

    terminal
    curl -X POST https://api.kontier.eu/v1/customers \  -H "Authorization: Bearer sk_test_..." \  -H "Idempotency-Key: 7f3c9a1e" \  -d '{"name":"Acme GmbH","customer_type":"BUSINESS",       "billing_address":{"country":"DE"},       "tax_identifiers":{"vat":"DE123456789"}}'→ 201 · customer.created · VIES: valid
  2. 02
    product.created

    Define the product

    The billable unit. pricing_model decides how tiers compute later: VOLUME, STAIRCASE or PACKAGE.

    terminal
    curl -X POST https://api.kontier.eu/v1/products \  -H "Idempotency-Key: 2b81d4f0" \  -d '{"name":"API Platform","pricing_model":"STAIRCASE",       "tax_category":"STANDARD"}'→ 201 · product.created
  3. 03
    plan.created

    Version the plan

    The plan bundles products and prices. Every publish mints an integer plan_version, and subscriptions pin it.

    terminal
    curl -X POST https://api.kontier.eu/v1/plans \  -H "Idempotency-Key: 9c02aa17" \  -d '{"name":"Pro"}'# then: POST /v1/plans/{id}/products→ 201 · plan.created · plan_version: 1
  4. 04
    subscription.activated

    Start the subscription

    Without items the subscription inherits the plan-version snapshot. Trial, proration and SEPA mandate included.

    terminal
    curl -X POST https://api.kontier.eu/v1/subscriptions \  -H "Idempotency-Key: e51f7b93" \  -d '{"customer_id":"cus_8f2k","plan_id":"plan_pro",       "billing_interval_unit":"MONTH","currency":"EUR"}'→ 201 · subscription.activated · pinned
  5. 05
    invoice.created

    Send usage, get an invoice

    quantity is a string, so decimals survive the wire. The in-body idempotency_key dedupes the event itself.

    terminal
    curl -X POST https://api.kontier.eu/v1/usage-events \  -H "Idempotency-Key: evt_9a2f" \  -d '{"subscription_id":"sub_44c1","metric_key":"api_calls",       "quantity":"18402","idempotency_key":"evt_9a2f"}'→ 202 · queued → invoice.created · €412.80
Reliability

What the API guarantees.

Commitments, not a feature list: what every response, every error and every webhook is bound to honor.

Webhooks

Signed, at-least-once, replayable.

HMAC-SHA256 over the raw body, secret prefixed whsec_. Six delivery attempts (1m, 5m, 30m, 2h, 12h), dedup on the envelope id. No signing secret means no delivery - fail closed.

X-Webhook-Signature: sha256=5257a86…{ "id": "evt_9a2", "type": "invoice.created", "idempotency_key": "…", "payload": { … } }
Errors

RFC 9457 Problem Details.

Every error is machine-readable: type, title, status, detail, code - plus a request_id for support. No guessing, no regex on error strings.

application/problem+json
Idempotency

Required, not optional.

Idempotency-Key is required on every POST. The key is bound to the SHA-256 of the body: the same key with a different body returns 409. 5xx responses are never cached, so a retry really re-executes.

Idempotency-Key: required
Pagination

Cursor, not offset.

Keyset over (created_at, id), cursor as an opaque token. Stable under parallel inserts - has_more is the authoritative signal, not total_count.

?cursor=…&limit=50 · max 200
Money

Fail closed where it counts.

If the idempotency store falters, money-moving routes (/charge, /refund, /capture, /finalize) return 503 rather than run without dedup. A retry beats a double charge.

503 over a double charge
Versioning

The plan version is pinned.

Subscriptions hold an integer plan_version. Catalogue changes never alter running invoices; switching is an explicit call, never a side effect.

POST /v1/subscriptions/{id}/change-version
OpenAPI

The spec is the contract.

OpenAPI 3.1, generated straight from the code - not maintained on the side. 324 paths, 453 operations, 859 schemas and 114 documented webhook events. Client generation included.

OpenAPI 3.1 · generated from code
E-invoicing

The invoice that passes validation.

XRechnung and ZUGFeRD come out of the same invoice you already produce. No second data path, no export to Excel, no library you have to keep aligned with the KoSIT rules yourself.

From call to valid XML

Generate the document: pick a profile, reference the invoice.

POST /v1/e-invoicing/documents{ "invoice_id": "inv_7c21",  "profile": "XRECHNUNG_3_0_UBL",  "jurisdiction": "DE" }

Fetch the raw XML: exactly what the recipient receives.

GET /v1/e-invoicing/documents/{id}/raw→ 200 · application/xml

Read the findings: every violated rule by id, not "invalid".

GET /v1/e-invoicing/documents/{id}/findings→ [ { "rule": "BR-DE-15", … } ]

What gets validated

Own rule engine

EN 16931, KoSIT BR-DE and PEPPOL BIS run as rules inside the service - no external schematron service that can be down.

Leitweg-ID, actually checked

BR-DE-1 requires the BuyerReference (BT-10). BR-DE-15 checks its shape - this exact pattern:

^[0-9A-Z]{2,12}(-[0-9A-Z]{0,30})?-[0-9]{2}$

Quarantine, not a silent failure

Findings are stored per document. A document that breaks the rules is quarantined instead of quietly going out to a public authority.

17 profiles in the catalogue

  • XRECHNUNG_3_0_UBL
  • XRECHNUNG_3_0_CII
  • EN16931_UBL_2_1
  • EN16931_CII_D16B
  • PEPPOL_BIS_BILLING_3_UBL
  • ZUGFERD_2_COMFORT
  • FACTURX_EN16931
  • ZUGFERD_2_XRECHNUNG
  • +9

Hybrid PDF/A-3 profiles (Factur-X, ZUGFeRD) need the Mustang service; XML-only profiles run without it.

Artifacts are archived with bytes and a hash chain, so the GoBD question "is this still the same invoice" has an answer.

Everything else lives in the reference.

Complete endpoints, schemas, webhook catalogs and examples, readable without signing up, instantly usable with sandbox keys. And anywhere on this site, pressing i reveals each artifact's API path, including right here.

Evaluating the API first?

We write when the API changes: new endpoints, new SDKs, breaking changes announced before they land.

Book a demo

Book a technical demo. 15 minutes with an engineer on your specific pricing model and tax setup.

By submitting you accept our privacy policy.

Prefer email? Reach us at contact@frontieralgorithmics.com

Try Kontier free for 30 days

A 30-day trial - in exchange for your newsletter signup

You subscribe to our newsletter, we send you a personal invite for 30 days of Kontier. No credit card, the trial ends on its own.

After you confirm your email address we send your invite within 48 hours - personally, not automatically.