TSE-Compliance — Dokumentation für Steuerprüfer¶
Dieses Dokument richtet sich an Steuerprüfer, Finanzbehörden und Steuerberater und beschreibt die technische Umsetzung der TSE-Anbindung im DiKAS-Kassensystem gemäß den geltenden gesetzlichen Anforderungen.
1. Gesetzliche Grundlagen¶
DiKAS erfüllt die Anforderungen folgender Vorschriften:
| Vorschrift | Inhalt |
|---|---|
| § 146a AO | Ordnungsgemäße Kassenführung, Pflicht zur Nutzung einer TSE |
| KassenSichV | Kassensicherungsverordnung — technische Anforderungen an die TSE |
| AEAO zu § 146a AO | Anwendungserlass mit Detailvorgaben zu ProcessTypes, ProcessData, QR-Code |
| DSFinV-K | Digitale Schnittstelle der Finanzverwaltung für Kassensysteme |
| GDPdU / GoBD | Grundsätze zur ordnungsmäßigen Führung und Aufbewahrung von Büchern (digitale Betriebsprüfung) |
2. Signierte Vorgangsarten (ProcessTypes)¶
DiKAS signiert alle kassenrelevanten Vorgänge gemäß AEAO zu § 146a AO — nicht nur Kassenbons. Es werden drei ProcessTypes gemäß DSFinV-K verwendet:
2.1 Kassenbeleg-V1¶
| Eigenschaft | Wert |
|---|---|
| ProcessType | Kassenbeleg-V1 |
| Auslösende Vorgänge | Jede abgeschlossene Zahlung (Direktverkauf, Tischzahlung, Storno) |
| Entities | Receipt (DocumentType: Receipt2) |
ProcessData-Format:
Beispiele:
Beleg^119.00_19.00:19.00 # Ein Steuersatz (19%)
Beleg^50.00_19.00:5.00_7.00:2.00 # Zwei Steuersätze (19% + 7%)
Beleg^0.00_0.00:0.00 # Nullbeleg
Alle Beträge werden mit zwei Dezimalstellen und Punkt als Dezimaltrennzeichen formatiert (Invariant Culture), konform zur DSFinV-K-Spezifikation.
2.2 Bestellung-V1¶
| Eigenschaft | Wert |
|---|---|
| ProcessType | Bestellung-V1 |
| Auslösende Vorgänge | Jede Bestellaufgabe im Tischbetrieb |
| Entities | OpenBon (DocumentType: OpenBon) |
ProcessData-Format:
Beispiel:
Bei Sammelbestellungen (Batch) wird die TSE-Signatur auf dem ersten Bon der Charge gespeichert. Die ProcessData enthält alle Positionen der gesamten Bestellung.
2.3 SonstigerVorgang¶
| Eigenschaft | Wert |
|---|---|
| ProcessType | SonstigerVorgang |
| Auslösende Vorgänge | Schichteröffnung, Schichtschließung, Tagesabschluss, Ausgaben |
| Entities | Exchange, DayClose, Spending |
ProcessData-Format:
Konkrete Vorgangstypen:
| Vorgangstyp | Beschreibung | Beispiel ProcessData |
|---|---|---|
AVSichOpen |
Schichteröffnung | AVSichOpen^Schichteroeffnung^200.00 |
AVSichClose |
Schichtschließung | AVSichClose^Schichtschliessung^350.00 |
AVKassenschnitt |
Tagesabschluss (Z-Bericht) | AVKassenschnitt^Tagesabschluss^1500.00 |
AVBelegabbruch |
Storno-Vorgang | AVBelegabbruch^Storno |
AVSons662 |
Ausgabe/Barentnahme | AVSonstige^Ausgabe^50.00 |
3. TSE-Datenfelder auf Dokumenten¶
Jedes signierte Dokument speichert die folgenden 9 TSE-Felder (implementiert über das Interface ITseDataHolder):
| Feld | Typ | Beschreibung |
|---|---|---|
TseTransactionNumber |
String | Eindeutige Transaktionsnummer der TSE |
TseSignature |
String | Digitale Signatur (Base64-kodiert) |
TseStartTime |
DateTime | Beginn der Signierung (UTC) |
TseEndTime |
DateTime | Ende der Signierung (UTC) |
TseSignatureCounter |
UInt64 | Monoton steigender Signaturzähler |
TseProcessData |
String | Signierte Vorgangsdaten (siehe Abschnitt 2) |
TseProcessType |
String | ProcessType-Bezeichner |
TseSerialNumber |
String | Seriennummer der verwendeten TSE |
TseError |
String | Fehlermeldung bei Signierungsfehler (null bei Erfolg) |
Diese Felder werden auf folgenden Entitäten gespeichert:
- Receipt — Kassenbons (Verkauf, Storno, Retoure)
- OpenBon — Bestellpositionen (Lead-Bon bei Sammelbestellungen)
- Exchange — Schichteröffnungen und -schließungen
- DayClose — Tagesabschlüsse (Z-Berichte)
- Spending — Ausgaben und Barentnahmen
4. QR-Code-Format (DSFinV-K Anhang I)¶
Jeder Kassenbon enthält einen QR-Code mit den TSE-Daten im standardisierten Format gemäß DSFinV-K Anhang I:
V0;{KassenSeriennummer};{ProcessType};{ProcessData};{TransaktionsNr};{SignaturZähler};{StartZeit};{EndZeit};{SigAlgorithmus};{LogZeitformat};{Signatur};{PublicKey}
Konkret:
V0;KASSE-001;Kassenbeleg-V1;Beleg^29.30_19.00:4.68;12345;67890;2026-03-13T18:30:00.000Z;2026-03-13T18:30:01.000Z;ecdsa-plain-SHA256;unixTime;a8f3c2d1e5b7...;PK123...
| Position | Feld | Quelle |
|---|---|---|
| 1 | Version | Immer V0 |
| 2 | Kassen-Seriennummer | CashPointSerialNumber aus BackendConfig |
| 3 | ProcessType | TseProcessType vom Beleg |
| 4 | ProcessData | TseProcessData vom Beleg |
| 5 | Transaktionsnummer | TseTransactionNumber vom Beleg |
| 6 | Signaturzähler | TseSignatureCounter vom Beleg |
| 7 | Startzeit | TseStartTime (ISO 8601, UTC) |
| 8 | Endzeit | TseEndTime (ISO 8601, UTC) |
| 9 | Signaturalgorithmus | SigAlg aus TseConfig (Standard: ecdsa-plain-SHA256) |
| 10 | Log-Zeitformat | LogTimeFormat aus TseConfig (Standard: unixTime) |
| 11 | Signatur | TseSignature vom Beleg |
| 12 | Öffentlicher Schlüssel | PublicKey aus TseConfig |
5. Kassen-Identifikation (ClientId)¶
Die Kassen-Identifikation folgt einer dreistufigen Fallback-Kette:
| Priorität | Quelle | Beschreibung |
|---|---|---|
| 1 | CashPointSerialNumber |
Explizit konfigurierte Kassen-Seriennummer (Lizenz) |
| 2 | BonIdServer |
Bon-Server-Kennung aus BackendConfig |
| 3 | "1" |
Fallback-Standardwert |
Diese ClientId wird bei jeder TSE-Signierung als Kassen-Identifikator übergeben und erscheint im QR-Code als Kassen-Seriennummer.
6. TSE-Konfiguration¶
Die TSE-Konfiguration wird im Dokument configTSE (TseConfig) gespeichert:
| Feld | Beschreibung |
|---|---|
PublicKey |
Öffentlicher Schlüssel der TSE |
Serial |
Seriennummer der TSE |
SigAlg |
Signaturalgorithmus (Standard: ecdsa-plain-SHA256) |
LogTimeFormat |
Zeitformat der TSE-Logs (Standard: unixTime) |
LocalPath |
Lokaler Pfad zur Hardware-TSE |
SetupDate |
Datum der TSE-Inbetriebnahme |
DecomissionDate |
Datum der TSE-Außerbetriebnahme |
TSESerialId |
Interne Serial-ID |
Unterstützte TSE-Anbindungen¶
| Typ | Implementierung | Beschreibung |
|---|---|---|
| Hardware (Swissbit) | SwissbitTseService |
Direkter USB-Zugriff auf Swissbit-TSE |
| Proxy (Netzwerk) | TseProxyService |
TSE über HTTP-Proxy (z. B. Fiskaltrust) |
| Router | TseServiceRouter |
Automatische Weiterleitung: Proxy bevorzugt, Fallback auf Hardware |
7. Ausfallsicherheit und Protokollierung¶
TSE-Ausfallprotokoll (TseOutageLog)¶
Gemäß AEAO zu § 146a AO dokumentiert DiKAS jeden TSE-Ausfall automatisch:
| Feld | Beschreibung |
|---|---|
StartTime |
Beginn des Ausfalls (UTC) |
EndTime |
Ende des Ausfalls (UTC, null wenn noch andauernd) |
Reason |
Ursache (z. B. „TSE not available", „TSE timeout") |
AffectedTransactions |
Anzahl betroffener Transaktionen |
Ablauf bei TSE-Ausfall:
- TSE-Signierung schlägt fehl →
TseError-Feld auf dem Dokument wird gesetzt - Ein neuer
TseOutageLog-Eintrag wird erstellt (mit StartTime und Reason) - Der Kassenvorgang wird nicht blockiert — die Transaktion wird ohne Signatur gespeichert
- Bei der nächsten erfolgreichen Signierung werden alle offenen Ausfall-Einträge geschlossen (EndTime gesetzt)
Timeout: Jede TSE-Signierung hat ein Timeout von 5 Sekunden. Bei Überschreitung wird TseError = "TSE timeout" gesetzt.
Verifizierung bei Prüfung¶
Bei jedem Dokument mit TseError != null liegt ein dokumentierter Signierungsfehler vor. Der zugehörige TseOutageLog-Eintrag belegt den Zeitraum und die Ursache des Ausfalls.
8. Datenexport für die Betriebsprüfung¶
8.1 DSFinV-K Export¶
DiKAS exportiert alle Kassendaten im DSFinV-K-Format (Digitale Schnittstelle der Finanzverwaltung für Kassensysteme):
- Alle vorgeschriebenen CSV-Dateien gemäß DSFinV-K-Spezifikation
- Zeitraumbezogener Export möglich
- Enthält: Einzelaufzeichnungen, Stammdaten, TSE-Daten, Kassenschnitte
8.2 TSE-TAR-Export¶
Direkter Export der TSE-Logdaten als TAR-Archiv:
- Vollexport: Alle gespeicherten Transaktionen der TSE
- Gefilterter Export: Nach Zeitraum (startDate/endDate)
- API-Endpoint:
GET /api/v1/tse/export/tar
8.3 GDPdU Export¶
Für die digitale Betriebsprüfung gemäß GDPdU/GoBD:
- Strukturierte Exportdatei mit allen steuerlich relevanten Daten
- Maschinenlesbar für Prüfsoftware (IDEA, AIS, etc.)
8.4 DATEV Export¶
Für die laufende Buchhaltung beim Steuerberater:
- 7 Export-Modi (Tagesabschluss, ProBon, ProÖffnungstag, WGR, WGR2, NachRechnung, Ausgaben)
- EXTF-Format v13 mit korrekten BU-Schlüsseln (USt 3/2/40, VSt 9/8/40)
- Optional verschlüsselt (AES-256 ZIP) und per E-Mail versendbar
9. Signierungsprozess im Detail¶
9.1 Ablauf einer Signierung¶
Kassenvorgang → TseSigningHelper → ITseService → TSE (Hardware/Proxy)
│ │
│ 1. BackendConfig laden │
│ 2. Prüfen: TSE verfügbar? │
│ 3. ProcessData aufbauen │
│ 4. ClientId auflösen │
│ 5. SignReceiptAsync aufrufen ───────→│
│ 6. Ergebnis auf Entity speichern ←──│
│ 7. OutageLog aktualisieren │
└──────────────────────────────────────┘
9.2 Welche Handler signieren?¶
| Handler | Vorgang | ProcessType |
|---|---|---|
ProcessDirectSaleCommand |
Direktverkauf | Kassenbeleg-V1 |
ProcessTablePaymentCommand |
Tischzahlung | Kassenbeleg-V1 |
VoidReceiptCommand |
Storno | Kassenbeleg-V1 |
CreateOpenBonCommand |
Einzelbestellung | Bestellung-V1 |
CreateOpenBonsBatchCommand |
Sammelbestellung | Bestellung-V1 |
OpenExchangeCommand |
Schichteröffnung | SonstigerVorgang |
CloseExchangeCommand |
Schichtschließung | SonstigerVorgang |
PerformDayCloseCommand |
Tagesabschluss | SonstigerVorgang |
CreateSpendingCommand |
Ausgabe/Barentnahme | SonstigerVorgang |
9.3 Fehlerbehandlung¶
Die TSE-Signierung ist als nicht-blockierend implementiert:
- TSE-Fehler werden im
TseError-Feld dokumentiert, der Vorgang wird trotzdem gespeichert - Ein
try/catchum den gesamten Signierungsprozess verhindert, dass TSE-Probleme den Kassenbetrieb stören - Die
HandleOutageLogAsync-Methode aktualisiert das Ausfallprotokoll nach jeder Signierung (Erfolg oder Fehler)
10. Vollständigkeit der Aufzeichnungen¶
Lückenlose Signierung¶
DiKAS gewährleistet die lückenlose Signierung aller kassenrelevanten Vorgänge durch:
- Zentrale Signierungslogik: Alle Signierungen laufen über
TseSigningHelper— es gibt keinen Weg, einen kassenrelevanten Vorgang ohne TSE-Aufruf abzuschließen - Monotoner Signaturzähler: Der
TseSignatureCounterwird von der TSE verwaltet und steigt monoton. Lücken im Zähler weisen auf Ausfälle hin, die imTseOutageLogdokumentiert sind - Transaktionsnummern: Jede TSE-Transaktion erhält eine eindeutige
TseTransactionNumber - Zeitstempel: Start- und Endzeitpunkt jeder Signierung werden gespeichert
Manipulationsschutz¶
- Signaturalgorithmus: ECDSA mit SHA-256 (ecdsa-plain-SHA256)
- Die TSE-Hardware ist BSI-zertifiziert (Common Criteria)
- Der öffentliche Schlüssel der TSE ist in der TseConfig gespeichert und kann zur Signaturverifikation verwendet werden
- Nachträgliche Änderungen an signierten Dokumenten sind durch die kryptographische Signatur erkennbar
11. Prüfungshinweise für Steuerprüfer¶
Wo finden Sie die TSE-Daten?¶
| Datenquelle | Zugang |
|---|---|
| TSE-Felder auf Belegen | In jedem Receipt/OpenBon/Exchange/DayClose/Spending-Dokument |
| QR-Codes | Auf gedruckten Kassenbons |
| TSE-Ausfallprotokoll | TseOutageLog-Dokumente in der Datenbank |
| TSE-Konfiguration | Dokument configTSE |
| DSFinV-K Export | Admin → Einstellungen → Export → DSFinV-K |
| TSE-TAR Export | Admin → Einstellungen → TSE → Export |
| GDPdU Export | Admin → Einstellungen → Export → GDPdU |
Wie prüfen Sie die Signaturen?¶
- QR-Code scannen: Jeder Bon enthält einen QR-Code im V0-Format (DSFinV-K Anhang I)
- TSE-TAR exportieren: Die TAR-Datei enthält alle TSE-Logdaten und kann mit Prüfwerkzeugen validiert werden
- Signaturzähler prüfen: Der monoton steigende Zähler darf keine unerklärten Lücken aufweisen
- Ausfallprotokoll: Lücken im Signaturzähler müssen durch TseOutageLog-Einträge erklärt sein
- Öffentlicher Schlüssel: Liegt in der TseConfig und kann zur rechnerischen Prüfung einzelner Signaturen verwendet werden
Checkliste für die Kassenprüfung¶
- TSE-Seriennummer stimmt mit dem beim Finanzamt gemeldeten überein
- Signaturzähler ist lückenlos (Lücken durch Ausfall-Protokolle erklärbar)
- ProcessTypes entsprechen den AEAO-Vorgaben (Kassenbeleg-V1, Bestellung-V1, SonstigerVorgang)
- ProcessData-Formate sind DSFinV-K-konform
- QR-Code-Format entspricht DSFinV-K Anhang I (V0-Format)
- Zeitstempel sind plausibel (Start < Ende, chronologisch aufsteigend)
- TSE-Ausfallzeiten sind dokumentiert und nachvollziehbar
- Alle kassenrelevanten Vorgangsarten werden signiert (nicht nur Kassenbons)
- DSFinV-K-Export ist vollständig und maschinenlesbar
- TSE-Zertifikat war im Prüfungszeitraum gültig
12. Technische Eckdaten¶
| Eigenschaft | Wert |
|---|---|
| Signaturalgorithmus | ECDSA mit SHA-256 (ecdsa-plain-SHA256) |
| QR-Code-Format | DSFinV-K Anhang I, Version V0 |
| Zeitformat | ISO 8601, UTC (yyyy-MM-ddTHH |
| Betragsformat | Invariant Culture, 2 Dezimalstellen (z. B. 119.00) |
| TSE-Timeout | 5 Sekunden pro Signierung |
| Unterstützte TSE | Swissbit (USB), Netzwerk-Proxy |
| Ausfallverhalten | Nicht-blockierend, automatische Protokollierung |
| Datenbank | CouchDB oder SQLite/SQL Server (konfigurierbar) |
| API-Basis | .NET 10, Clean Architecture, CQRS mit MediatR |
| Testabdeckung | 17 dedizierte TSE-Tests (Signierung, ProcessData, QR-Code, Fallback) |
Anhang: Zuordnung Vorgangstyp → Dokument → Datenbank¶
| Kassenvorgang | ProcessType | Entity | DocumentType | Datenbank-Kollektion |
|---|---|---|---|---|
| Direktverkauf (bar/Karte) | Kassenbeleg-V1 | Receipt | Receipt2 | receipt2 |
| Tischzahlung | Kassenbeleg-V1 | Receipt | Receipt2 | receipt2 |
| Storno | Kassenbeleg-V1 | Receipt | Receipt2 | receipt2 |
| Bestellung (Tisch) | Bestellung-V1 | OpenBon | OpenBon | openbon |
| Sammelbestellung | Bestellung-V1 | OpenBon | OpenBon | openbon |
| Schichteröffnung | SonstigerVorgang | Exchange | Exchange2 | exchange2 |
| Schichtschließung | SonstigerVorgang | Exchange | Exchange2 | exchange2 |
| Tagesabschluss (Z-Bericht) | SonstigerVorgang | DayClose | DayClose2 | dayclose2 |
| Ausgabe/Barentnahme | SonstigerVorgang | Spending | CashPointSpending | cashpointspending |