Playwright Tests / test (pull_request) Has been cancelled
Completes the eRechnung output path: finalized invoices are emitted as a ZUGFeRD/Factur-X EN 16931 hybrid (DATEV) or, when a Leitweg-ID is present, as XRechnung 3.0 for B2G. Both are externally validated as ACCEPTED (0 errors) and PDF/A-3B COMPLIANT against the ProcessWeb eInvoice service. - ERechnungMapper: FdsInvoiceData -> EN 16931 model. Seller master data now from Fuchs:ERechnung:Seller config (VAT id BT-31, Steuernummer BT-32, optional Handelsregister BT-30, IBAN/BIC, contact). Adds payment terms BT-20/BT-9 (BR-CO-25), buyer VAT id, §13b reverse charge, and the service date/period (BT-72 / BG-14) parsed from ProvisionPeriod (BR-DE-TMP-32). B2G -> XRechnung profile with the required electronic addresses/contact. - ERechnungValidator: client for POST /validatepdf (EN 16931 XML + PDF/A-3 in one call). A pure "scenario not matched" with zero errors is not treated as a hard failure; real errors optionally withhold the hybrid (FailOnError). - ERechnungSettings: seller + validation config; wired in Program.cs; ServiceUrl in appsettings. - Online editor: structured German-only dialogs for the recipient address (incl. Leitweg-ID) and the service date/period (single date or range). - Bumps the eRechnungLib submodule to the CII rsm-namespace / PDF-A subtype fix. Fuchs.Tests 514/514, eRechnungLib 97/97. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
145 lines
7.5 KiB
Markdown
145 lines
7.5 KiB
Markdown
# Anforderungen an den eInvoice-Validierungsdienst
|
||
|
||
**Adressat:** Betreiber des Validierungsdienstes `https://api.processweb.de/api/eInvoice`
|
||
**Kontext:** Das Fuchs-Intranet erzeugt Rechnungen als ZUGFeRD/Factur-X- bzw. XRechnung-Hybrid
|
||
(PDF/A-3 mit eingebetteter CII-XML) und ruft nach der Erzeugung `POST /validatepdf` auf, um
|
||
**formale PDF/A-3-Konformität** und **EN 16931-/XRechnung-Regelkonformität** zu prüfen.
|
||
|
||
**Zielbild:** Der Validator soll **maximalen Funktionsumfang** haben — jede in Deutschland/EU
|
||
praktisch vorkommende E-Rechnung (alle gängigen Syntaxen, Profile und Versionen) erkennen,
|
||
korrekt klassifizieren und gegen die passenden Regelwerke prüfen.
|
||
|
||
> **Status 2026-07:** Die ursprüngliche Kernlücke (CII-Dokumente wurden nicht klassifiziert) ist
|
||
> behoben — sowohl EN 16931-ZUGFeRD als auch XRechnung 3.0 (CII) werden inzwischen erkannt und
|
||
> geprüft (`scenarioMatched=true`, angereichertes Response-Schema). Dieses Dokument bleibt als
|
||
> Referenz für den angestrebten **vollen** Funktionsumfang (Abschnitt 4).
|
||
|
||
---
|
||
|
||
## 1. Referenz — was Fuchs emittiert
|
||
|
||
| Profil | Einbettung | GuidelineSpecifiedDocumentContextParameter/ID | Einsatz |
|
||
|---|---|---|---|
|
||
| ZUGFeRD EN 16931 (COMFORT) | `factur-x.xml` | `urn:cen.eu:en16931:2017` | B2B/B2C, DATEV (Standard) |
|
||
| XRechnung 3.0 (CII) | `xrechnung.xml` | `urn:cen.eu:en16931:2017#compliant#urn:xeinkauf.de:kosit:xrechnung_3.0` | B2G (Leitweg-ID vorhanden) |
|
||
|
||
Beide sind PDF/A-3 (veraPDF-COMPLIANT). Profilwahl automatisch: **Leitweg-ID vorhanden →
|
||
XRechnung**, sonst **EN 16931-ZUGFeRD**.
|
||
|
||
## 2. Kern-Anforderungen (umgesetzt, als Regressionsschutz dokumentiert)
|
||
|
||
### R1 — XRechnung 3.0 in CII matchen (B2G)
|
||
- Match-Kriterium (CII): `rsm:CrossIndustryInvoice/rsm:ExchangedDocumentContext/`
|
||
`ram:GuidelineSpecifiedDocumentContextParameter/ram:ID` =
|
||
`urn:cen.eu:en16931:2017#compliant#urn:xeinkauf.de:kosit:xrechnung_3.0`
|
||
- Erwartung: `documentType` gesetzt, `scenarioMatched=true`, EN 16931- **und** XRechnung-Schematron.
|
||
|
||
### R2 — Reines EN 16931 (CII) matchen (ZUGFeRD/DATEV)
|
||
- Match-Kriterium (CII): `…/ram:GuidelineSpecifiedDocumentContextParameter/ram:ID` =
|
||
`urn:cen.eu:en16931:2017` (ohne XRechnung-CIUS-Zusatz).
|
||
- Prüftiefe: **nur** das EN 16931-Kern-Schematron (nicht die XRechnung-CIUS-Regeln).
|
||
|
||
### R3 — Einbettung aus dem Hybrid-PDF robust extrahieren
|
||
`/validatepdf` muss die CII-Rechnungs-XML unabhängig vom Dateinamen aus dem `/AF`-Array ziehen
|
||
(`factur-x.xml`, `xrechnung.xml`, Altname `zugferd-invoice.xml`). Das Match erfolgt über den
|
||
XML-Inhalt/die CustomizationID, nicht über den Dateinamen.
|
||
|
||
> Historischer Hinweis: Solange die drei CII-Wurzelkinder fälschlich im `ram:`- statt
|
||
> `rsm:`-Namespace standen (Fuchs-seitiger Bug, behoben), konnte kein Validator die CustomizationID
|
||
> extrahieren. Der Match muss auf `rsm:ExchangedDocumentContext` greifen.
|
||
|
||
---
|
||
|
||
## 3. (frei)
|
||
|
||
## 4. Maximaler Funktionsumfang
|
||
|
||
### 4.1 Support-Matrix (Syntax × Profil × Version)
|
||
|
||
| Standard / Profil | Syntax | Versionen | Regelwerk |
|
||
|---|---|---|---|
|
||
| **EN 16931** (Kern) | CII, UBL | :2017 (+ Amdt.) | EN16931-Schematron (ConnectingEurope) |
|
||
| **XRechnung** (CIUS) | CII, UBL | 2.0 – 2.3, **3.0.x**, (4.0) | EN16931 + XRechnung-Schematron (KoSIT) |
|
||
| **ZUGFeRD / Factur-X** | CII | 2.0 – **2.4** (Factur-X 1.0/1.07/1.08) | EN16931 (BASIC/COMFORT), EXTENDED |
|
||
| ZUGFeRD-Profile | CII | MINIMUM, BASIC WL, BASIC, EN16931, EXTENDED | profilabhängig |
|
||
| **Peppol BIS Billing 3.0** | CII, UBL | 3.0.x | EN16931 + Peppol-Schematron |
|
||
| Dokumentarten | — | Rechnung (380), Gutschrift (381), Korrektur (384), Storno | UNCL1001 |
|
||
|
||
> Mindest-Priorität: **XRechnung 2.x** und **ZUGFeRD alle 2.x-Profile**; **Peppol BIS 3.0** und
|
||
> **XRechnung 4.0** als Ausbaustufe.
|
||
|
||
### 4.2 Validierungsschichten (je Dokument, getrennt ausgewiesen)
|
||
|
||
1. **Syntax / XSD** — CII (D16B/D22B/D25A) bzw. UBL (2.1/2.5).
|
||
2. **EN 16931-Schematron** — BR-*, BR-CO-*, BR-DEC-*.
|
||
3. **CIUS-Schematron** — XRechnung (BR-DE-*) bzw. Peppol (PEPPOL-*).
|
||
4. **Codelisten** — UNCL/EAS/ISO (Währung, Land, Einheit, USt-Kategorie, Zahlungsmittel).
|
||
5. **Rechen-/Konsistenzprüfung** — Summen, USt-Aufteilung.
|
||
6. **PDF/A** (veraPDF) — Flavour wählbar (`3b` Default; auch `3u`, `2b`, `1b`).
|
||
7. **ZUGFeRD/Factur-X-Container** — `/AF`-Verknüpfung, `/AFRelationship`, Subtype `text/xml`,
|
||
XMP-`fx:*`-Metadaten und **Konsistenz** zwischen XMP-ConformanceLevel und Guideline/CustomizationID.
|
||
|
||
### 4.3 Auto-Erkennung (ohne Vorgabe durch den Aufrufer)
|
||
|
||
- **Syntax** aus dem Wurzelelement (`rsm:CrossIndustryInvoice` → CII; UBL `Invoice`/`CreditNote`).
|
||
- **Profil/Version** aus `GuidelineSpecifiedDocumentContextParameter/ram:ID` (CII) bzw.
|
||
`cbc:CustomizationID` + `cbc:ProfileID` (UBL).
|
||
- **Dokumentart** aus `TypeCode` (BT-3).
|
||
- Strengstes zutreffendes CIUS automatisch wählen; reines EN 16931 nur Kernregeln.
|
||
|
||
### 4.4 Erweiterte API-Endpunkte
|
||
|
||
Bestehend: `verify`, `validate`, `validatepdf`, `validatepdfa`, `doc`, `schema`, `mcp`. Ergänzen:
|
||
|
||
- **`POST /detect`** — nur Klassifikation (Syntax/Profil/Version/Dokumentart).
|
||
- **`POST /validate` mit UBL** — `application/xml` UBL akzeptieren (nicht nur CII).
|
||
- **`POST /validatebatch`** — mehrere Dokumente (multipart oder ZIP).
|
||
- **Report-Formate** über `Accept`/`?format=`: `json` (Default), `svrl`, `html`.
|
||
- **`flavour`-Parameter** auch bei `validatepdf` durchreichen.
|
||
- Weiterhin **HTTP 200** bei fachlicher Ablehnung; echte Transportfehler als 400/415/502/504.
|
||
|
||
### 4.5 Angereichertes Response-Schema
|
||
|
||
```jsonc
|
||
"xml": {
|
||
"syntax": "CII|UBL",
|
||
"standard": "EN16931|XRechnung|ZUGFeRD|Peppol",
|
||
"profile": "EN16931|EXTENDED|XRECHNUNG|BASIC|…",
|
||
"version": "3.0.2",
|
||
"documentType": "XRechnung 3.0 (CII)",
|
||
"customizationId": "urn:…xrechnung_3.0",
|
||
"scenarioMatched": true,
|
||
"documentData": { "invoiceId","issueDate","seller","buyer","leitwegId","totalGross","currency" },
|
||
"layers": [ { "id":"xsd|en16931|cius|codelist|calc", "name","valid","errorCount","warningCount" } ],
|
||
"messages": [ { "level":"error|warning|information","code","rule","message","location","clause","businessTerm" } ]
|
||
}
|
||
```
|
||
|
||
- `level` konsequent aus dem SVRL (`fatal`→error, sonst warning).
|
||
- `location` als XPath **und**, wo möglich, als Business Term (BT-/BG-Nummer).
|
||
- `recommendation` = `accept`, wenn `errorCount=0` (Warnungen erlaubt).
|
||
|
||
### 4.6 Betrieb / Nicht-funktional
|
||
|
||
- **Aktuelle Artefakt-Stände**: KoSIT (XRechnung 2.x/3.0.x/4.0), eInvoicing-EN16931, Peppol,
|
||
veraPDF — mit ausgewiesenen Versionen im Report (`engine`, `scenarioVersion`, `rulesetVersion`).
|
||
- **Health** (`/verify`) meldet geladene Szenario-/Ruleset-Versionen + Zustand jedes Sub-Validators.
|
||
- Robuste Größen-/Timeout-Grenzen dokumentiert; klare 413/504 statt stiller Fehler.
|
||
|
||
## 5. Abnahmekriterien
|
||
|
||
1. **ZUGFeRD EN 16931** (`factur-x.xml`, `urn:cen.eu:en16931:2017`): `xml.scenarioMatched=true`,
|
||
`documentType` ≈ `"EN16931 (CII)"`, `pdfa.isCompliant=true`, bei sauberem Beleg `errorCount=0`.
|
||
2. **XRechnung 3.0** (`xrechnung.xml`, `…xrechnung_3.0`, mit Leitweg-ID): `scenarioMatched=true`,
|
||
`documentType` ≈ `"XRechnung 3.0 (CII)"`, `pdfa.isCompliant=true`.
|
||
3. **Auto-Erkennung** (`POST /detect`): klassifiziert beide korrekt (Syntax/Profil/Version).
|
||
4. **UBL-XRechnung** (Fremdbeleg): wird erkannt und geprüft.
|
||
5. **PDF/A**: bleibt COMPLIANT (Flavour `3b`).
|
||
|
||
## 6. Fuchs-seitiges Verhalten
|
||
|
||
Der Fuchs-Client (`ProcessWebERechnungValidator`) wertet einen reinen **Szenario-Mismatch mit
|
||
`errorCount=0` nicht als harten Fehler** (die Rechnung wird nicht zurückgehalten); echte PDF/A-
|
||
oder XML-Regelfehler dagegen schon (bei `FailOnError=true` wird der Hybrid zurückgehalten →
|
||
Fallback auf Plain-PDF/A).
|