@kreiseck/kasseneck-api 0.9.4 → 0.11.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (50) hide show
  1. package/CHANGELOG.md +118 -0
  2. package/README.md +41 -0
  3. package/dist/cjs/payments/hobex-hps/index.d.ts +2 -2
  4. package/dist/cjs/payments/hobex-hps/index.js +36 -1
  5. package/dist/cjs/payments/hobex-hps/outcome.d.ts +20 -1
  6. package/dist/cjs/payments/hobex-hps/outcome.js +11 -0
  7. package/dist/cjs/payments/hobex-hps/payments.d.ts +19 -0
  8. package/dist/cjs/payments/hobex-hps/payments.js +160 -33
  9. package/dist/cjs/payments/hobex-hps/transaction-response.d.ts +180 -31
  10. package/dist/cjs/payments/hobex-hps/transaction-response.js +308 -88
  11. package/dist/cjs/payments/index.d.ts +1 -1
  12. package/dist/cjs/payments/index.js +8 -1
  13. package/dist/cjs/printing/escpos.d.ts +85 -1
  14. package/dist/cjs/printing/escpos.js +140 -4
  15. package/dist/cjs/printing/index.d.ts +2 -1
  16. package/dist/cjs/printing/index.js +13 -1
  17. package/dist/cjs/printing/qr-groesse.d.ts +122 -0
  18. package/dist/cjs/printing/qr-groesse.js +126 -0
  19. package/dist/cjs/receipt/epos.d.ts +42 -1
  20. package/dist/cjs/receipt/epos.js +66 -5
  21. package/dist/cjs/receipt/index.d.ts +2 -2
  22. package/dist/cjs/receipt/index.js +3 -1
  23. package/dist/cjs/receipt/layout-escpos.d.ts +50 -2
  24. package/dist/cjs/receipt/layout-escpos.js +59 -2
  25. package/dist/esm/payments/hobex-hps/index.d.ts +2 -2
  26. package/dist/esm/payments/hobex-hps/index.js +2 -2
  27. package/dist/esm/payments/hobex-hps/outcome.d.ts +20 -1
  28. package/dist/esm/payments/hobex-hps/outcome.js +10 -0
  29. package/dist/esm/payments/hobex-hps/payments.d.ts +19 -0
  30. package/dist/esm/payments/hobex-hps/payments.js +161 -34
  31. package/dist/esm/payments/hobex-hps/transaction-response.d.ts +180 -31
  32. package/dist/esm/payments/hobex-hps/transaction-response.js +302 -87
  33. package/dist/esm/payments/index.d.ts +1 -1
  34. package/dist/esm/payments/index.js +1 -1
  35. package/dist/esm/printing/escpos.d.ts +85 -1
  36. package/dist/esm/printing/escpos.js +138 -4
  37. package/dist/esm/printing/index.d.ts +2 -1
  38. package/dist/esm/printing/index.js +2 -1
  39. package/dist/esm/printing/qr-groesse.d.ts +122 -0
  40. package/dist/esm/printing/qr-groesse.js +120 -0
  41. package/dist/esm/receipt/epos.d.ts +42 -1
  42. package/dist/esm/receipt/epos.js +65 -5
  43. package/dist/esm/receipt/index.d.ts +2 -2
  44. package/dist/esm/receipt/index.js +2 -2
  45. package/dist/esm/receipt/layout-escpos.d.ts +50 -2
  46. package/dist/esm/receipt/layout-escpos.js +59 -3
  47. package/fixtures/hobex-hps-codes.json +365 -15
  48. package/fixtures/kasse-texte.json +1 -1
  49. package/fixtures/oberflaeche.json +1 -1
  50. package/package.json +1 -1
@@ -5,7 +5,7 @@
5
5
  * ein, es reicht den Terminal-Rumpf roh durch — die Einordnung passiert hier.
6
6
  *
7
7
  * **Zwilling:** `kasseneck_api/lib/src/hobex_hps/transaction_response.dart`.
8
- * Beide Seiten pinnen dieselbe Codetabelle, siehe `HPS_MEASURED_CODES` unten
8
+ * Beide Seiten pinnen dieselbe Codetabelle, siehe `HPS_CODES` unten
9
9
  * und `fixtures/hobex-hps-codes.json`.
10
10
  *
11
11
  * **`responseCode !== '0'` ist NICHT die Pruefung auf eine Ablehnung.** Genau
@@ -18,7 +18,7 @@
18
18
  *
19
19
  * [isConclusive] ist die einzige Stelle, an der ein Code zu einem Ausgang
20
20
  * wird — und sie ist eine ECHTE Positivliste: nur ein Code, dessen Bedeutung
21
- * GEMESSEN und in [HPS_MEASURED_CODES] benannt ist, zaehlt. Jeder andere —
21
+ * feststeht und in [HPS_CODES] benannt ist, zaehlt. Jeder andere —
22
22
  * auch ein neuer, heute noch unbekannter Code — ist eine Wissensluecke, siehe
23
23
  * [isUnknownCode]. Am 27.08.2026 hat der Dart-Zwilling gemessen, warum die
24
24
  * Gegenrichtung ("jeder Code ausser 9027 ist schluessig") gefaehrlich ist: ein
@@ -26,98 +26,217 @@
26
26
  * schluessig und haette eine Zahlung, unter der tatsaechlich Geld geflossen
27
27
  * sein kann, als `declined` gemeldet.
28
28
  */
29
+ /** Der Satz fuer den Bediener je Grund, deutsch. */
30
+ export const HPS_REASON_HINTS = {
31
+ approved: 'Vom Terminal genehmigt.',
32
+ aborted: 'Der Vorgang wurde abgebrochen. Es wurde kein Geld bewegt.',
33
+ noCard: 'Es wurde keine Karte vorgehalten. Es wurde kein Geld bewegt — '
34
+ + 'bitte erneut versuchen.',
35
+ cardReadFailed: 'Die Karte konnte nicht gelesen werden. Es wurde kein Geld bewegt — '
36
+ + 'bitte erneut versuchen, notfalls die Karte stecken statt auflegen.',
37
+ cardDeclined: 'Die Karte wurde vom Terminal abgelehnt. Es wurde kein Geld bewegt '
38
+ + '— bitte eine andere Karte oder Zahlungsart verwenden.',
39
+ wrongPin: 'Die PIN war falsch. Es wurde kein Geld bewegt — bitte erneut '
40
+ + 'versuchen.',
41
+ amountInvalid: 'Das Terminal nimmt diesen Betrag nicht an. Es wurde kein Geld '
42
+ + 'bewegt.',
43
+ tipNotSelected: 'Das Trinkgeld wurde nicht rechtzeitig gewählt. Es wurde kein Geld '
44
+ + 'bewegt — bitte erneut versuchen.',
45
+ terminalBusy: 'Das Terminal ist noch mit einem anderen Vorgang beschäftigt. Es '
46
+ + 'wurde kein Geld bewegt — kurz warten und erneut versuchen.',
47
+ terminalBlocked: 'Das Terminal ist gesperrt. Es wurde kein Geld bewegt — bitte hobex '
48
+ + 'kontaktieren.',
49
+ terminalSetup: 'Das Terminal ist nicht richtig eingerichtet. Es wurde kein Geld '
50
+ + 'bewegt — bitte die Terminal-ID in den Einstellungen prüfen, sonst '
51
+ + 'hobex kontaktieren.',
52
+ terminalFault: 'Das Terminal meldet eine Störung. Es wurde kein Geld bewegt — '
53
+ + 'bitte das Terminal neu starten und erneut versuchen.',
54
+ requestRejected: 'Das Terminal hat die Anfrage abgewiesen. Es wurde kein Geld bewegt '
55
+ + '— tritt das wieder auf, bitte den Support kontaktieren.',
56
+ invalidTransaction: 'Das Terminal kennt die ursprüngliche Zahlung nicht. Es wurde kein '
57
+ + 'Geld bewegt.',
58
+ refundPassword: 'Das Passwort für die Gutschrift war falsch oder wurde nicht '
59
+ + 'eingegeben. Es wurde nichts ausgezahlt.',
60
+ refundDisabled: 'Gutschriften sind an diesem Terminal abgeschaltet. Es wurde nichts '
61
+ + 'ausgezahlt — bitte hobex kontaktieren.',
62
+ hostTimeoutReversed: 'hobex hat nicht rechtzeitig geantwortet, das Terminal hat den '
63
+ + 'Vorgang selbst storniert. Es wird kein Geld bewegt — bitte erneut '
64
+ + 'versuchen.',
65
+ hostFault: 'Die Verbindung zwischen Terminal und hobex ist gestört. Ob die '
66
+ + 'Karte belastet wurde, weiß das Terminal nicht — bitte nicht erneut '
67
+ + 'kassieren, bevor es geklärt ist.',
68
+ internalError: 'Das Terminal meldet einen internen Fehler. Ob die Karte belastet '
69
+ + 'wurde, ist unklar — bitte nicht erneut kassieren, bevor es geklärt '
70
+ + 'ist.',
71
+ canceled: 'Die Zahlung ist aufgehoben.',
72
+ notAbortable: 'Der Vorgang ist bereits abgeschlossen und lässt sich nicht mehr '
73
+ + 'abbrechen.',
74
+ noStatement: 'Das Terminal hat zu diesem Vorgang keine Auskunft.',
75
+ technicalError: 'Das Terminal meldet einen technischen Fehler; über den Vorgang '
76
+ + 'sagt das nichts.',
77
+ unknown: 'Das Terminal nennt einen Code, dessen Bedeutung nicht bekannt ist.',
78
+ };
29
79
  /**
30
- * Die gemessene Codetabelle — Vertrag mit dem Dart-Zwilling, siehe
31
- * `fixtures/hobex-hps-codes.json`. Gemessen an einem hobex-HPS (TID 3600335,
32
- * HPS 1.10.0, Firmware 7.3.6, 26.–28.08.2026).
80
+ * Die beiden Gruende hinter einem Code mit `effect: 'hostUncertain'`: ob Geld
81
+ * geflossen ist, weiss das Terminal nicht.
82
+ */
83
+ export function isHostUncertainReason(reason) {
84
+ return reason === 'hostFault' || reason === 'internalError';
85
+ }
86
+ function code(c, title, meaning, effect, reason, source, rejectsRequest = false) {
87
+ return { code: c, title, meaning, conclusive: effect === 'conclusive', effect, reason, source, rejectsRequest };
88
+ }
89
+ /**
90
+ * Die vollstaendige Codetabelle — Vertrag mit dem Dart-Zwilling
91
+ * (`HpsCodes.all` in `lib/src/hobex_hps/response_codes.dart`), ausgegeben als
92
+ * `fixtures/hobex-hps-codes.json`.
93
+ *
94
+ * Zwei Quellen: GEMESSEN an hobex-HPS-Geraeten (TID 3600335, HPS 1.10.0,
95
+ * Firmware 7.3.6, 26.–28.08.2026; TID 3556988 im Betrieb) und die
96
+ * Antwortcodeliste von hobex (erhalten 11.09.2026). Die Regel bleibt: nur ein
97
+ * Code mit feststehender Bedeutung schreibt einen Ausgang fest -- die Liste des
98
+ * Herstellers ist eine solche Feststellung, kein Raten aus der Codefamilie.
99
+ *
100
+ * Eingeordnet wird danach, WO im Ablauf ein dokumentierter Code entsteht:
101
+ * - vor dem Host (Anfrage, Karte, EMV-Kernel, Eingaben, Geraetezustand) ->
102
+ * `conclusive`, also `declined`;
103
+ * - `100029`, Zeitueberschreitung zum Host MIT auto-reversal -> ebenfalls
104
+ * `declined`, das Terminal storniert laut hobex selbst;
105
+ * - beim oder nach dem Host OHNE auto-reversal, dazu der Sammelcode `100999`
106
+ * -> `hostUncertain`.
33
107
  *
34
- * Reihenfolge ist die im Messprotokoll (`doc/kartenzahlung.md` im
35
- * Dart-Zwilling) — numerisch aufsteigend zu sortieren wuerde beim Diff
36
- * gegen die Vertragsdatei nichts gewinnen und macht Aenderungen schwerer
37
- * nachzuverfolgen.
108
+ * Reihenfolge: zuerst die gemessenen wie im Messprotokoll, dann die
109
+ * dokumentierten aufsteigend -- identisch mit dem Dart-Zwilling.
38
110
  */
39
- export const HPS_MEASURED_CODES = [
40
- { code: '0', meaning: 'genehmigt', conclusive: true },
41
- {
42
- code: '9002',
43
- meaning: 'ungueltiger Vorgang -- das Terminal hat den Vorgang selbst als '
44
- + 'unzulaessig verworfen, bevor irgendetwas in Bewegung kam',
45
- conclusive: true,
46
- },
47
- {
48
- code: '9011',
49
- meaning: "aufgehoben (\"Transaction Canceled\") -- der Vorgang unter dieser Kennung wurde storniert",
50
- conclusive: true,
51
- },
52
- {
53
- code: '9027',
54
- meaning: 'keine Aussage -- steht gleichermassen fuer "nie gesehen", '
55
- + '"laeuft gerade", "Karte nicht aufgelegt" und "abgebrochen"',
56
- conclusive: false,
57
- },
58
- {
59
- code: '9900',
60
- meaning: '"Technical Error Database" -- gemessen im Zusammenhang mit '
61
- + 'einer nicht rein numerischen Kennung; keine Aussage ueber den Vorgang selbst',
62
- conclusive: false,
63
- },
64
- {
65
- code: '9003',
66
- meaning: '"Invalid Amount" -- der Betrag wird abgewiesen, BEVOR eine Karte '
67
- + 'verlangt wird (28.08.2026: 99999,99 EUR, Antwort nach 15,7 s ohne '
68
- + 'Kartenaufforderung); nichts belastet',
69
- conclusive: true,
70
- },
71
- { code: '100002', meaning: 'abgebrochen ("Aborted")', conclusive: true },
72
- { code: '100003', meaning: 'Karte nicht aufgelegt ("Card not present")', conclusive: true },
73
- { code: '100010', meaning: 'nicht mehr abbrechbar -- der Vorgang ist bereits abgeschlossen', conclusive: true },
74
- {
75
- code: '100019',
76
- meaning: '"Amount is not in a valid range" -- Betrag ausserhalb des '
77
- + 'zulaessigen Bereichs, gemessen mit negativem Betrag; Abweisung vor '
78
- + 'dem Kartenfluss, nichts belastet',
79
- conclusive: true,
80
- },
81
- {
82
- code: '100108',
83
- meaning: '"Invalid TID" -- die Terminal-Kennung gibt es an diesem Geraet '
84
- + 'nicht; der Vorgang wird abgewiesen, bevor etwas geschieht',
85
- conclusive: true,
86
- },
87
- {
88
- code: '55',
89
- meaning: '"PIN falsch" -- Host-Ablehnung wegen falscher PIN, die erste '
90
- + 'gemessene Host-Ablehnung ueberhaupt (02.09.2026 im Betrieb, TID '
91
- + '3556988, HPS 1.11.4, Firmware 2.3.9): die Zahlung antwortete direkt '
92
- + 'damit, die Statusabfrage danach elfmal in Folge ebenso -- eine '
93
- + 'Host-Ablehnung bleibt am Terminal abrufbar; nichts belastet',
94
- conclusive: true,
95
- },
111
+ export const HPS_CODES = [
112
+ code('0', 'Authorized', 'genehmigt', 'conclusive', 'approved', 'measuredAndDocumented'),
113
+ code('9002', 'Invalid Transaction', 'ungueltiger Vorgang -- das Terminal hat den Vorgang selbst als '
114
+ + 'unzulaessig verworfen, bevor irgendetwas in Bewegung kam', 'conclusive', 'invalidTransaction', 'measured', true),
115
+ code('9011', 'Transaction Canceled', 'aufgehoben ("Transaction Canceled") -- der Vorgang unter dieser '
116
+ + 'Kennung wurde storniert', 'conclusive', 'canceled', 'measured'),
117
+ code('9027', 'Original Tx not found', 'keine Aussage -- steht gleichermassen fuer "nie gesehen", "laeuft '
118
+ + 'gerade", "Karte nicht aufgelegt" und "abgebrochen"', 'noStatement', 'noStatement', 'measured'),
119
+ code('9900', 'Technical Error Database', '"Technical Error Database" -- gemessen im Zusammenhang mit einer '
120
+ + 'nicht rein numerischen Kennung; keine Aussage ueber den Vorgang '
121
+ + 'selbst', 'noStatement', 'technicalError', 'measured'),
122
+ code('9003', 'Invalid Amount', '"Invalid Amount" -- der Betrag wird abgewiesen, BEVOR eine Karte '
123
+ + 'verlangt wird (28.08.2026: 99999,99 EUR, Antwort nach 15,7 s ohne '
124
+ + 'Kartenaufforderung); nichts belastet', 'conclusive', 'amountInvalid', 'measured'),
125
+ code('100002', 'Aborted', 'abgebrochen ("Aborted") -- ueber die Kasse oder am Terminal; '
126
+ + 'nichts belastet', 'conclusive', 'aborted', 'measuredAndDocumented'),
127
+ code('100003', 'Card not present', 'Karte nicht aufgelegt ("Card not present") -- innerhalb der Frist '
128
+ + '(gemessen rund 60 s) keine Karte; nichts belastet', 'conclusive', 'noCard', 'measuredAndDocumented'),
129
+ code('100010', 'Unable to abort transaction', 'nicht mehr abbrechbar -- der Vorgang ist bereits abgeschlossen', 'conclusive', 'notAbortable', 'measuredAndDocumented', true),
130
+ code('100019', 'Amount is not in a valid range', '"Amount is not in a valid range" -- Betrag ausserhalb des '
131
+ + 'zulaessigen Bereichs, gemessen mit negativem Betrag; Abweisung vor '
132
+ + 'dem Kartenfluss, nichts belastet', 'conclusive', 'amountInvalid', 'measuredAndDocumented'),
133
+ code('100108', 'Invalid TID', '"Invalid TID" -- die Terminal-Kennung gibt es an diesem Geraet '
134
+ + 'nicht; der Vorgang wird abgewiesen, bevor etwas geschieht', 'conclusive', 'terminalSetup', 'measured', true),
135
+ code('55', 'PIN falsch', '"PIN falsch" -- Host-Ablehnung wegen falscher PIN, die erste '
136
+ + 'gemessene Host-Ablehnung ueberhaupt (02.09.2026 im Betrieb, TID '
137
+ + '3556988, HPS 1.11.4, Firmware 2.3.9): die Zahlung antwortete '
138
+ + 'direkt damit, die Statusabfrage danach elfmal in Folge ebenso -- '
139
+ + 'eine Host-Ablehnung bleibt am Terminal abrufbar; nichts belastet', 'conclusive', 'wrongPin', 'measured'),
140
+ // ---- ab hier: Antwortcodeliste von hobex, erhalten 11.09.2026 ----
141
+ code('100001', 'Bad Request', 'fehlerhafte Anfrage der Kasse ("Bad Request") -- Abweisung vor dem '
142
+ + 'Kartenfluss; nichts belastet', 'conclusive', 'requestRejected', 'documented', true),
143
+ code('100004', 'Card read failed', 'Karte nicht lesbar ("Card read failed") -- Fehler beim Umgang mit '
144
+ + 'der Karte, vor jeder Autorisierung; im Betrieb (TID 3556988, '
145
+ + '28.08.2026) danach dauerhaft 9027; nichts belastet', 'conclusive', 'cardReadFailed', 'documented'),
146
+ code('100005', 'App select failed', 'Anwendungsauswahl gescheitert ("App select failed") -- die Karte '
147
+ + 'bietet keine passende Anwendung, vor jeder Autorisierung; im '
148
+ + 'Betrieb danach dauerhaft 9027; nichts belastet', 'conclusive', 'cardReadFailed', 'documented'),
149
+ code('100006', 'Communication with TecsXml failed', 'keine Verbindung zum hobex-Host ("Communication with TecsXml '
150
+ + 'failed") -- das Terminal storniert NICHT selbst; ob beim Host '
151
+ + 'etwas angekommen ist, weiss das Terminal nicht', 'hostUncertain', 'hostFault', 'documented'),
152
+ code('100007', 'Processing of TecsXml step failed', 'Schritt beim hobex-Host gescheitert ("Processing of TecsXml step '
153
+ + 'failed") -- das Terminal storniert NICHT selbst; ob beim Host '
154
+ + 'belastet wurde, weiss das Terminal nicht', 'hostUncertain', 'hostFault', 'documented'),
155
+ code('100008', 'Invalid TID', 'Terminal-Kennung passt nicht ("Invalid TID") -- die TID der '
156
+ + 'Anfrage ist nicht die eingerichtete; Abweisung vor dem '
157
+ + 'Kartenfluss, nichts belastet (am Geraet gemessen wurde dafuer '
158
+ + '100108)', 'conclusive', 'terminalSetup', 'documented', true),
159
+ code('100009', 'Invalid Tx Type', 'Vorgangstyp unbekannt oder nicht moeglich ("Invalid Tx Type") -- '
160
+ + 'Abweisung vor dem Kartenfluss; nichts belastet', 'conclusive', 'requestRejected', 'documented', true),
161
+ code('100011', 'Not Found', 'nicht gefunden ("Not Found") -- das Terminal kennt den Vorgang '
162
+ + 'nicht; keine Aussage ueber den Vorgang, anders als 9027 aber nie '
163
+ + 'gemessen und deshalb ohne dessen Schlussregel', 'noStatement', 'noStatement', 'documented'),
164
+ code('100012', 'Max retries exceeded', 'zu viele Kartenversuche ("Max retries exceeded") -- die Karte '
165
+ + 'wurde mehrfach (Vorgabe 3) erfolglos vorgehalten; nichts belastet', 'conclusive', 'cardReadFailed', 'documented'),
166
+ code('100013', 'Diagnosis failed', 'Diagnose gescheitert ("Diagnosis failed") -- das Terminal konnte '
167
+ + 'die Daten des EMV-Kernels nicht lesen; kein Kartenfluss, nichts '
168
+ + 'belastet', 'conclusive', 'terminalFault', 'documented', true),
169
+ code('100014', 'Card information wasn\'t entered', 'Kartendaten nicht eingegeben ("Card information wasn\'t entered") '
170
+ + '-- die MOTO-Eingabe kam nicht innerhalb der Frist; nichts belastet', 'conclusive', 'noCard', 'documented'),
171
+ code('100015', 'Card declined', 'Karte vom EMV-Kernel abgelehnt ("Card declined") -- Ablehnung im '
172
+ + 'Terminal, vor jeder Autorisierung beim Host; im Betrieb danach '
173
+ + 'dauerhaft 9027; nichts belastet', 'conclusive', 'cardDeclined', 'documented'),
174
+ code('100017', 'Card Not Supported', 'Karte nicht unterstuetzt ("Card Not Supported") -- der EMV-Kernel '
175
+ + 'kennt die Karte nicht; nichts belastet', 'conclusive', 'cardDeclined', 'documented'),
176
+ code('100018', 'Scep enrollment failed', 'Zertifikatsanmeldung gescheitert ("Scep enrollment failed") -- '
177
+ + 'falscher Code oder keine Verbindung; das Terminal kann den Host '
178
+ + 'nicht ansprechen, nichts belastet', 'conclusive', 'terminalSetup', 'documented', true),
179
+ code('100020', 'Refund password is invalid', 'Passwort fuer die Gutschrift falsch ("Refund password is invalid") '
180
+ + '-- die Gutschrift wird nicht ausgefuehrt, nichts ausgezahlt', 'conclusive', 'refundPassword', 'documented'),
181
+ code('100021', 'Failed to enter the password', 'Passwort nicht eingegeben ("Failed to enter the password") -- '
182
+ + 'nicht innerhalb der Frist; nichts ausgefuehrt', 'conclusive', 'refundPassword', 'documented'),
183
+ code('100022', 'Terminal is blocked', 'Terminal gesperrt ("Terminal is blocked") -- das Geraet ist nicht '
184
+ + 'IN_OPERATION; nichts belastet', 'conclusive', 'terminalBlocked', 'documented', true),
185
+ code('100023', 'Invalid message type', 'ungueltige Antwort des hobex-Hosts ("Invalid message type") -- '
186
+ + 'Nachricht und Antwortcode in den UserData ungueltig; ob beim Host '
187
+ + 'belastet wurde, weiss das Terminal nicht', 'hostUncertain', 'hostFault', 'documented'),
188
+ code('100024', 'Transaction completion has failed', 'Abschluss des Online-Vorgangs gescheitert ("Transaction completion '
189
+ + 'has failed") -- NACH der Anfrage beim Host; ob belastet bleibt, '
190
+ + 'weiss das Terminal nicht', 'hostUncertain', 'hostFault', 'documented'),
191
+ code('100025', 'Refund transactions are disabled', 'Gutschriften abgeschaltet ("Refund transactions are disabled") -- '
192
+ + 'in der Geraeteeinstellung; nichts ausgezahlt', 'conclusive', 'refundDisabled', 'documented'),
193
+ code('100026', 'Transaction was declined.', 'Host-Antwort passt nicht zur Karte ("Transaction was declined.") '
194
+ + '-- Chip-Daten fuer eine Karte ohne Chip; das Terminal lehnt ab, ob '
195
+ + 'der Host zuvor belastet hat, ist offen', 'hostUncertain', 'hostFault', 'documented'),
196
+ code('100027', 'Unsupported UserData in TecsXml Response', 'unbekannte Daten in der Antwort des hobex-Hosts ("Unsupported '
197
+ + 'UserData in TecsXml Response") -- ob beim Host belastet wurde, '
198
+ + 'weiss das Terminal nicht', 'hostUncertain', 'hostFault', 'documented'),
199
+ code('100028', 'Tip selection process has failed.', 'Trinkgeld nicht gewaehlt ("Tip selection process has failed.") -- '
200
+ + 'nicht innerhalb der Frist; nichts belastet', 'conclusive', 'tipNotSelected', 'documented'),
201
+ code('100029', 'Communication with TecsXml timeout', 'Zeitueberschreitung zum hobex-Host ("Communication with TecsXml '
202
+ + 'timeout") -- das Terminal storniert den Vorgang SELBST '
203
+ + '(auto-reversal); nichts belastet', 'conclusive', 'hostTimeoutReversed', 'documented'),
204
+ code('100998', 'Terminal is busy', 'Terminal beschaeftigt ("Terminal is busy") -- ein anderer Vorgang '
205
+ + 'laeuft oder das Geraet ist nicht bereit; die Anfrage wurde nicht '
206
+ + 'angenommen, nichts belastet', 'conclusive', 'terminalBusy', 'documented', true),
207
+ code('100999', 'Internal Error', 'interner Fehler des Terminals ("Internal Error") -- Sammelcode '
208
+ + 'fuer jeden sonst nicht benannten Fehler, an jeder Stelle des '
209
+ + 'Ablaufs moeglich; ob belastet wurde, ist offen', 'hostUncertain', 'internalError', 'documented'),
96
210
  ];
211
+ /**
212
+ * @deprecated Seit 0.10.0 [HPS_CODES] -- die Tabelle fuehrt nicht mehr nur
213
+ * gemessene Codes. Gleicher Inhalt, bleibt fuer bestehende Aufrufer.
214
+ */
215
+ export const HPS_MEASURED_CODES = HPS_CODES;
97
216
  /** `responseCode` einer genehmigten Zahlung. */
98
217
  export const APPROVED_CODE = '0';
99
- /** Siehe [HPS_MEASURED_CODES]: ungueltiger Vorgang, nichts passiert. */
218
+ /** Siehe [HPS_CODES]: ungueltiger Vorgang, nichts passiert. */
100
219
  export const INVALID_TRANSACTION_CODE = '9002';
101
- /** Siehe [HPS_MEASURED_CODES]: aufgehoben. */
220
+ /** Siehe [HPS_CODES]: aufgehoben. */
102
221
  export const TRANSACTION_CANCELED_CODE = '9011';
103
- /** Siehe [HPS_MEASURED_CODES]: keine Aussage. */
222
+ /** Siehe [HPS_CODES]: keine Aussage. */
104
223
  export const NO_STATEMENT_CODE = '9027';
105
- /** Siehe [HPS_MEASURED_CODES]: Kennung nicht numerisch, keine Aussage. */
224
+ /** Siehe [HPS_CODES]: Kennung nicht numerisch, keine Aussage. */
106
225
  export const TECHNICAL_ERROR_CODE = '9900';
107
- /** Siehe [HPS_MEASURED_CODES]: abgebrochen. */
226
+ /** Siehe [HPS_CODES]: abgebrochen. */
108
227
  export const ABORTED_CODE = '100002';
109
- /** Siehe [HPS_MEASURED_CODES]: Karte nicht aufgelegt. */
228
+ /** Siehe [HPS_CODES]: Karte nicht aufgelegt. */
110
229
  export const CARD_NOT_PRESENT_CODE = '100003';
111
- /** Siehe [HPS_MEASURED_CODES]: nicht mehr abbrechbar. */
230
+ /** Siehe [HPS_CODES]: nicht mehr abbrechbar. */
112
231
  export const NOT_ABORTABLE_CODE = '100010';
113
- /** Siehe [HPS_MEASURED_CODES]: Betrag abgewiesen, vor dem Kartenfluss. */
232
+ /** Siehe [HPS_CODES]: Betrag abgewiesen, vor dem Kartenfluss. */
114
233
  export const INVALID_AMOUNT_CODE = '9003';
115
- /** Siehe [HPS_MEASURED_CODES]: Betrag ausserhalb des zulaessigen Bereichs. */
234
+ /** Siehe [HPS_CODES]: Betrag ausserhalb des zulaessigen Bereichs. */
116
235
  export const AMOUNT_OUT_OF_RANGE_CODE = '100019';
117
- /** Siehe [HPS_MEASURED_CODES]: Terminal-Kennung unbekannt. */
236
+ /** Siehe [HPS_CODES]: Terminal-Kennung unbekannt. */
118
237
  export const INVALID_TID_CODE = '100108';
119
238
  /**
120
- * Siehe [HPS_MEASURED_CODES]: Host-Ablehnung, falsche PIN -- nichts belastet.
239
+ * Siehe [HPS_CODES]: Host-Ablehnung, falsche PIN -- nichts belastet.
121
240
  *
122
241
  * Zweistellig, weil ein Antwortcode des HOSTS (ISO 8583, 55 = "Incorrect
123
242
  * PIN"), kein `9xxx`-Terminalcode und kein `100xxx`-Code der HPS-Anwendung.
@@ -128,6 +247,61 @@ export const INVALID_TID_CODE = '100108';
128
247
  * dann nicht 9027 antwortet, sondern mit dem Code selbst.
129
248
  */
130
249
  export const WRONG_PIN_CODE = '55';
250
+ // ---- Antwortcodeliste von hobex, erhalten 11.09.2026 ----
251
+ // Bedeutung, Wirkung und Grund stehen in [HPS_CODES]; hier nur die Namen,
252
+ // gleichlautend mit dem Dart-Zwilling (`TransactionResponse.*Code`).
253
+ /** `100001` "Bad Request" -- nichts belastet. */
254
+ export const BAD_REQUEST_CODE = '100001';
255
+ /** `100004` "Card read failed" -- nichts belastet. Im Betrieb am 28.08.2026 gesehen. */
256
+ export const CARD_READ_FAILED_CODE = '100004';
257
+ /** `100005` "App select failed" -- nichts belastet. Im Betrieb am 28.08.2026 gesehen. */
258
+ export const APP_SELECT_FAILED_CODE = '100005';
259
+ /** `100006` "Communication with TecsXml failed" (No auto-reversal) -- ungewiss. */
260
+ export const HOST_COMMUNICATION_FAILED_CODE = '100006';
261
+ /** `100007` "Processing of TecsXml step failed" (No auto-reversal) -- ungewiss. */
262
+ export const HOST_STEP_FAILED_CODE = '100007';
263
+ /** `100008` "Invalid TID" laut hobex; gemessen wurde [INVALID_TID_CODE]. */
264
+ export const INVALID_TID_DOCUMENTED_CODE = '100008';
265
+ /** `100009` "Invalid Tx Type" -- nichts belastet. */
266
+ export const INVALID_TX_TYPE_CODE = '100009';
267
+ /** `100011` "Not Found" -- keine Aussage, aber ohne die Zwei-9027-Regel. */
268
+ export const NOT_FOUND_CODE = '100011';
269
+ /** `100012` "Max retries exceeded" -- nichts belastet. */
270
+ export const MAX_RETRIES_EXCEEDED_CODE = '100012';
271
+ /** `100013` "Diagnosis failed" -- nichts belastet. */
272
+ export const DIAGNOSIS_FAILED_CODE = '100013';
273
+ /** `100014` "Card information wasn't entered" (MOTO) -- nichts belastet. */
274
+ export const CARD_INFO_NOT_ENTERED_CODE = '100014';
275
+ /** `100015` "Card declined" (EMV-Kernel) -- nichts belastet. Im Betrieb am 28. und 31.08.2026 gesehen. */
276
+ export const CARD_DECLINED_CODE = '100015';
277
+ /** `100017` "Card Not Supported" -- nichts belastet. */
278
+ export const CARD_NOT_SUPPORTED_CODE = '100017';
279
+ /** `100018` "Scep enrollment failed" -- nichts belastet. */
280
+ export const SCEP_ENROLLMENT_FAILED_CODE = '100018';
281
+ /** `100020` "Refund password is invalid" -- nichts ausgezahlt. */
282
+ export const REFUND_PASSWORD_INVALID_CODE = '100020';
283
+ /** `100021` "Failed to enter the password" -- nichts ausgezahlt. */
284
+ export const PASSWORD_NOT_ENTERED_CODE = '100021';
285
+ /** `100022` "Terminal is blocked" -- nichts belastet. */
286
+ export const TERMINAL_BLOCKED_CODE = '100022';
287
+ /** `100023` "Invalid message type" -- ungewiss. */
288
+ export const INVALID_MESSAGE_TYPE_CODE = '100023';
289
+ /** `100024` "Transaction completion has failed" -- ungewiss. */
290
+ export const COMPLETION_FAILED_CODE = '100024';
291
+ /** `100025` "Refund transactions are disabled" -- nichts ausgezahlt. */
292
+ export const REFUND_DISABLED_CODE = '100025';
293
+ /** `100026` "Transaction was declined." (Chip-Daten fuer eine Karte ohne Chip) -- ungewiss. */
294
+ export const CHIP_DATA_MISMATCH_CODE = '100026';
295
+ /** `100027` "Unsupported UserData in TecsXml Response" -- ungewiss. */
296
+ export const UNSUPPORTED_USER_DATA_CODE = '100027';
297
+ /** `100028` "Tip selection process has failed." -- nichts belastet. */
298
+ export const TIP_SELECTION_FAILED_CODE = '100028';
299
+ /** `100029` "Communication with TecsXml timeout" (auto-reversal) -- nichts belastet. */
300
+ export const HOST_TIMEOUT_REVERSED_CODE = '100029';
301
+ /** `100998` "Terminal is busy" -- nichts belastet; gemessen als HTTP [TERMINAL_BUSY_HTTP_STATUS]. */
302
+ export const TERMINAL_BUSY_CODE = '100998';
303
+ /** `100999` "Internal Error" -- Sammelcode, ungewiss. */
304
+ export const INTERNAL_ERROR_CODE = '100999';
131
305
  /**
132
306
  * HTTP `409` ("Terminal is busy"): das Terminal serialisiert und weist eine
133
307
  * zweite Anfrage ab, waehrend eine erste noch laeuft. Am 27.08.2026 gemessen:
@@ -135,13 +309,26 @@ export const WRONG_PIN_CODE = '55';
135
309
  * Spur (die Statusabfrage auf seine Kennung liefert weiterhin
136
310
  * [NO_STATEMENT_CODE]).
137
311
  *
138
- * Bewusst KEIN Eintrag in [HPS_MEASURED_CODES]: es ist ein HTTP-Status, kein
312
+ * Bewusst KEIN Eintrag in [HPS_CODES]: es ist ein HTTP-Status, kein
139
313
  * `responseCode` — er entsteht, bevor ueberhaupt ein Antwortrumpf gelesen
140
314
  * wird. Siehe `errors.ts` (`HpsConnectTerminalError.isTerminalBusy`) fuer die
141
315
  * getrennte Auswertung.
142
316
  */
143
317
  export const TERMINAL_BUSY_HTTP_STATUS = 409;
144
- const KNOWN_OUTCOME_CODES = new Set(HPS_MEASURED_CODES.filter((c) => c.conclusive).map((c) => c.code));
318
+ const CODE_BY_ID = new Map(HPS_CODES.map((c) => [c.code, c]));
319
+ /** Der Eintrag zu [code] in [HPS_CODES], oder `undefined`, wenn seine Bedeutung nicht feststeht. */
320
+ export function hpsCodeInfo(code) {
321
+ return code === undefined ? undefined : CODE_BY_ID.get(code);
322
+ }
323
+ /**
324
+ * Der Grund zu [code] -- `'unknown'` fuer einen Code ausserhalb der Tabelle,
325
+ * `undefined` ohne Code.
326
+ */
327
+ export function hpsCodeReason(code) {
328
+ if (code === undefined)
329
+ return undefined;
330
+ return hpsCodeInfo(code)?.reason ?? 'unknown';
331
+ }
145
332
  /**
146
333
  * Liest eine Terminal-Antwort aus dem `hps`-Feld der Connect-Huelle.
147
334
  *
@@ -217,7 +404,13 @@ export function isInProgress(res) {
217
404
  export function isNotAbortable(res) {
218
405
  return res.responseCode === NOT_ABORTABLE_CODE;
219
406
  }
220
- /** `true`, wenn das Terminal zu dieser Kennung keine Auskunft gibt (9027). */
407
+ /**
408
+ * `true`, wenn das Terminal zu dieser Kennung keine Auskunft gibt (9027).
409
+ *
410
+ * Bewusst NUR `9027`, nicht auch [NOT_FOUND_CODE] (`100011`): auf `9027` ruht
411
+ * die Zwei-9027-Regel in `payments.ts`, und die ist fuer genau diesen Code
412
+ * gemessen. `100011` ist dokumentiert, aber nie gesehen.
413
+ */
221
414
  export function isNoStatement(res) {
222
415
  return res.responseCode === NO_STATEMENT_CODE;
223
416
  }
@@ -238,17 +431,39 @@ export function isCanceled(res) {
238
431
  }
239
432
  /**
240
433
  * `true`, wenn diese Antwort ueberhaupt eine Aussage ueber den Ausgang
241
- * traegt — ein Ergebniscode, der in [HPS_MEASURED_CODES] als `conclusive`
242
- * gefuehrt wird. Die einzige Stelle, an der ein Code zu einem Ausgang wird.
434
+ * traegt — ein Ergebniscode, der in [HPS_CODES] als `conclusive` gefuehrt
435
+ * wird. Die einzige Stelle, an der ein Code zu einem Ausgang wird.
243
436
  */
244
437
  export function isConclusive(res) {
245
- return res.responseCode !== undefined && KNOWN_OUTCOME_CODES.has(res.responseCode);
438
+ return hpsCodeInfo(res.responseCode)?.conclusive ?? false;
439
+ }
440
+ /**
441
+ * Wie [isConclusive], aber fuer die Antwort auf eine STATUSABFRAGE: ein Code,
442
+ * der die Anfrage selbst abweist (`rejectsRequest`, etwa `100022` "Terminal is
443
+ * blocked" oder `100108` "Invalid TID"), sagt dort nichts ueber den gesuchten
444
+ * Vorgang. Als `declined` gelesen, hiesse ein gesperrtes Terminal "die Zahlung
445
+ * ist nicht belastet".
446
+ */
447
+ export function isConclusiveAsStatus(res) {
448
+ const info = hpsCodeInfo(res.responseCode);
449
+ return info !== undefined && info.conclusive && !info.rejectsRequest;
450
+ }
451
+ /**
452
+ * `true`, wenn der Code einen Ausgang meldet, den das Terminal selbst nicht
453
+ * kennt: der hobex-Host war beteiligt, und das Terminal storniert nicht von
454
+ * sich aus (`effect: 'hostUncertain'`). Ein spaeteres `9027` auf die
455
+ * Statusabfrage heisst dann NICHT "nichts belastet" -- es spiegelt nur den
456
+ * Speicher des Terminals, nicht den des Hosts.
457
+ */
458
+ export function isHostUncertain(res) {
459
+ return hpsCodeInfo(res.responseCode)?.effect === 'hostUncertain';
246
460
  }
247
461
  /**
248
- * `true`, wenn ein Ergebniscode VORHANDEN ist, aber weder schluessig noch
249
- * eine der beiden gemessenen Wissensluecken ([isNoStatement],
250
- * [isTechnicalError]) — ein Code, den dieses Modell schlicht nicht kennt.
462
+ * `true`, wenn ein Ergebniscode VORHANDEN ist, dessen Bedeutung aber nicht
463
+ * feststeht -- er fehlt in [HPS_CODES]. Ein Code, den dieses Modell schlicht
464
+ * nicht kennt; anders als [isNoStatement], [isTechnicalError] und
465
+ * [isHostUncertain], die eine Wissensluecke ueber den VORGANG benennen.
251
466
  */
252
467
  export function isUnknownCode(res) {
253
- return res.responseCode !== undefined && !isConclusive(res) && !isNoStatement(res) && !isTechnicalError(res);
468
+ return res.responseCode !== undefined && hpsCodeInfo(res.responseCode) === undefined;
254
469
  }
@@ -42,4 +42,4 @@
42
42
  export { StripeLinkMode, type StripeLinkModeKey } from '../enums/index.js';
43
43
  export { type CreateStripeLinkOptions, type StripeCaptureResult, createStripeLink, stripeCaptureIntent, } from './stripe.js';
44
44
  export { type HobexPayOptions, type HobexRefundOptions, type HobexTransactionIdOptions, hobexPay, hobexRefund, newHobexTransactionId, } from './hobex.js';
45
- export { type CardPaymentOutcome, type HpsConnectClient, type HpsConnectClientOptions, type HpsConnectFetch, type HpsConnectFetchResponse, type HpsConnectPaymentOptions, type HpsConnectTarget, type HpsConnectTransactionOptions, type HpsMeasuredCode, type HpsPaymentEvent, type HpsPaymentEventKind, type HpsPaymentObserver, type HpsPaymentOptions, type HpsPayments, type HpsPaymentResult, type HpsPaymentsOptions, type HpsTransactionIdGeneratorOptions, type HpsTransactionResponse, ABORTED_CODE, APPROVED_CODE, CARD_NOT_PRESENT_CODE, createHpsConnectClient, createHpsPayments, createHpsTransactionIdGenerator, HPS_MEASURED_CODES, HpsClarifyTimeoutError, HpsConnectException, HpsConnectTerminalError, HpsConnectTransportError, HpsPreflightError, HpsTransactionIdError, INVALID_TRANSACTION_CODE, isApproved, isConclusive, isInProgress, isNoStatement, isNotAbortable, isTechnicalError, isUnknownCode, isValidHpsTransactionId, mayRetrySafely, MAX_TRANSACTION_ID_LENGTH, newHpsTransactionId, NOT_ABORTABLE_CODE, NO_STATEMENT_CODE, parseHpsTransactionResponse, PREFLIGHT_CONNECT_CODES, TECHNICAL_ERROR_CODE, TERMINAL_BUSY_HTTP_STATUS, TRANSACTION_CANCELED_CODE, } from './hobex-hps/index.js';
45
+ export { type CardPaymentOutcome, type HpsConnectClient, type HpsConnectClientOptions, type HpsConnectFetch, type HpsConnectFetchResponse, type HpsConnectPaymentOptions, type HpsConnectTarget, type HpsConnectTransactionOptions, type HpsCode, type HpsCodeEffect, type HpsCodeReason, type HpsCodeSource, type HpsMeasuredCode, type HpsPaymentEvent, type HpsPaymentEventKind, type HpsPaymentObserver, type HpsPaymentOptions, type HpsPayments, type HpsPaymentResult, type HpsPaymentsOptions, type HpsTransactionIdGeneratorOptions, type HpsTransactionResponse, ABORTED_CODE, APPROVED_CODE, CARD_NOT_PRESENT_CODE, createHpsConnectClient, createHpsPayments, createHpsTransactionIdGenerator, HPS_CODES, HPS_MEASURED_CODES, HPS_REASON_HINTS, hpsCodeInfo, hpsCodeReason, HpsClarifyTimeoutError, HpsConnectException, HpsConnectTerminalError, HpsConnectTransportError, HpsPreflightError, HpsTransactionIdError, INVALID_TRANSACTION_CODE, isApproved, isConclusive, isConclusiveAsStatus, isHostUncertain, isHostUncertainResult, isInProgress, isNoStatement, isNotAbortable, isTechnicalError, isUnknownCode, isValidHpsTransactionId, mayRetrySafely, MAX_TRANSACTION_ID_LENGTH, newHpsTransactionId, NOT_ABORTABLE_CODE, NO_STATEMENT_CODE, parseHpsTransactionResponse, PREFLIGHT_CONNECT_CODES, TECHNICAL_ERROR_CODE, TERMINAL_BUSY_HTTP_STATUS, TRANSACTION_CANCELED_CODE, } from './hobex-hps/index.js';
@@ -42,4 +42,4 @@
42
42
  export { StripeLinkMode } from '../enums/index.js';
43
43
  export { createStripeLink, stripeCaptureIntent, } from './stripe.js';
44
44
  export { hobexPay, hobexRefund, newHobexTransactionId, } from './hobex.js';
45
- export { ABORTED_CODE, APPROVED_CODE, CARD_NOT_PRESENT_CODE, createHpsConnectClient, createHpsPayments, createHpsTransactionIdGenerator, HPS_MEASURED_CODES, HpsClarifyTimeoutError, HpsConnectException, HpsConnectTerminalError, HpsConnectTransportError, HpsPreflightError, HpsTransactionIdError, INVALID_TRANSACTION_CODE, isApproved, isConclusive, isInProgress, isNoStatement, isNotAbortable, isTechnicalError, isUnknownCode, isValidHpsTransactionId, mayRetrySafely, MAX_TRANSACTION_ID_LENGTH, newHpsTransactionId, NOT_ABORTABLE_CODE, NO_STATEMENT_CODE, parseHpsTransactionResponse, PREFLIGHT_CONNECT_CODES, TECHNICAL_ERROR_CODE, TERMINAL_BUSY_HTTP_STATUS, TRANSACTION_CANCELED_CODE, } from './hobex-hps/index.js';
45
+ export { ABORTED_CODE, APPROVED_CODE, CARD_NOT_PRESENT_CODE, createHpsConnectClient, createHpsPayments, createHpsTransactionIdGenerator, HPS_CODES, HPS_MEASURED_CODES, HPS_REASON_HINTS, hpsCodeInfo, hpsCodeReason, HpsClarifyTimeoutError, HpsConnectException, HpsConnectTerminalError, HpsConnectTransportError, HpsPreflightError, HpsTransactionIdError, INVALID_TRANSACTION_CODE, isApproved, isConclusive, isConclusiveAsStatus, isHostUncertain, isHostUncertainResult, isInProgress, isNoStatement, isNotAbortable, isTechnicalError, isUnknownCode, isValidHpsTransactionId, mayRetrySafely, MAX_TRANSACTION_ID_LENGTH, newHpsTransactionId, NOT_ABORTABLE_CODE, NO_STATEMENT_CODE, parseHpsTransactionResponse, PREFLIGHT_CONNECT_CODES, TECHNICAL_ERROR_CODE, TERMINAL_BUSY_HTTP_STATUS, TRANSACTION_CANCELED_CODE, } from './hobex-hps/index.js';
@@ -27,6 +27,7 @@
27
27
  * Nicht enthalten (bewusst): Rasterbilder/Logos, Capability-Profile einzelner
28
28
  * Druckermodelle, Kassenlade, 1D-Barcodes.
29
29
  */
30
+ import { type QrModulGroesse } from './qr-groesse.js';
30
31
  /** Papierbreite der Bonrolle. */
31
32
  export type PosPaperSize = 'mm58' | 'mm80';
32
33
  /** Ausrichtung einer Textzeile bzw. innerhalb einer Spalte. */
@@ -43,6 +44,14 @@ export type PosTextSize = 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8;
43
44
  export type QrSize = 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8;
44
45
  /** Fehlerkorrekturstufe des QR-Codes. */
45
46
  export type QrCorrection = 'L' | 'M' | 'Q' | 'H';
47
+ /**
48
+ * Fertig gerechnetes QR-Raster, quadratisch, `true` = schwarzes Modul —
49
+ * **ohne** Ruhezone, die setzt der Drucker-Weg selbst.
50
+ *
51
+ * Dieses Paket rastert bewusst nicht selbst (keine Bildverarbeitung, siehe
52
+ * Kopf dieser Datei); wer den Bildweg braucht, bringt sein eigenes Raster mit.
53
+ */
54
+ export type QrMatrix = readonly (readonly boolean[])[];
46
55
  /** Textstil. Fehlende Felder gelten als Vorgabewert (nicht als "unveraendert"). */
47
56
  export interface PosStyles {
48
57
  bold?: boolean;
@@ -88,8 +97,26 @@ export interface EscPosHrOptions {
88
97
  }
89
98
  export interface EscPosQrOptions {
90
99
  align?: PosAlign;
100
+ /**
101
+ * Feste Modulgroesse in Druckpunkten. Gesetzt schaltet sie die Rechnung ab —
102
+ * fuer Aufrufer, die genau wissen, was ihr Geraet kann. Ohne sie entscheidet
103
+ * die Regel in `qr-groesse.ts`.
104
+ */
91
105
  size?: QrSize;
92
106
  correction?: QrCorrection;
107
+ /** Deckel fuer die gerechnete Modulgroesse; wirkungslos neben `size`. */
108
+ groesse?: QrModulGroesse;
109
+ /** Modell 1 des Symbols ausdruecklich waehlen — siehe `qrCodeBytes`. */
110
+ modell1?: boolean;
111
+ }
112
+ export interface EscPosQrRasterOptions {
113
+ align?: PosAlign;
114
+ /** Feste Punkte je Modul; ohne Angabe gerechnet (mindestens 1). */
115
+ punkteJeModul?: number;
116
+ /** Deckel fuer die gerechnete Groesse. */
117
+ groesse?: QrModulGroesse;
118
+ /** Ruhezone je Seite in Modulen; Vorgabe `QR_RUHEZONE_MODULE` (4). */
119
+ ruhezoneModule?: number;
93
120
  }
94
121
  /** Interner Stilzustand — immer vollstaendig, nie teilbefuellt. */
95
122
  interface AktuelleStile {
@@ -111,6 +138,25 @@ interface AktuelleStile {
111
138
  export interface EscPosDocument {
112
139
  readonly paperSize: PosPaperSize;
113
140
  readonly spaceBetweenRows: number;
141
+ /**
142
+ * Der Beleg ging ohne QR hinaus — `null`, solange alles in Ordnung ist.
143
+ * Gesetzt, wenn das Symbol auch mit der Ausnahmegroesse nicht auf das Papier
144
+ * passt und kein Bildweg mitgegeben wurde. Auf einer oesterreichischen Kassa
145
+ * ist der QR die maschinenlesbare Signatur: das muss der Aufrufer erfahren,
146
+ * ohne den Bytestrom zu durchsuchen.
147
+ */
148
+ qrFehler: string | null;
149
+ /**
150
+ * Der QR steht auf dem Papier, aber nicht so wie eingestellt — `null`,
151
+ * solange nichts abgewichen ist. Zwei Faelle, beide mit Grund im Text: das
152
+ * Symbol war fuer den nativen Befehl zu breit und ging als Bild hinaus, oder
153
+ * es passte nur unter der Mindest-Modulgroesse.
154
+ *
155
+ * Getrennt von `qrFehler`, weil die Handlung eine andere ist: dort heisst es
156
+ * "Beleg ohne QR, nachdrucken oder elektronisch ausgeben", hier "gedruckt,
157
+ * aber der eingestellte Weg taugt fuer dieses Geraet nicht".
158
+ */
159
+ qrAusweich: string | null;
114
160
  /** intern: bisher erzeugte Bytes */
115
161
  readonly bytes: number[];
116
162
  /** intern: global gesetzte Codepage (ueberlebt `escPosReset`) */
@@ -213,7 +259,45 @@ export declare function escPosRow(doc: EscPosDocument, columns: readonly PosColu
213
259
  export declare function qrCodeBytes(text: string, options?: {
214
260
  size?: QrSize;
215
261
  correction?: QrCorrection;
262
+ modell1?: boolean;
216
263
  }): Uint8Array;
217
- /** Setzt die Ausrichtung und haengt den nativen QR-Befehl an. */
264
+ /**
265
+ * Setzt die Ausrichtung und haengt den nativen QR-Befehl an — mit
266
+ * **gerechneter** Modulgroesse, sofern `options.size` sie nicht festlegt.
267
+ *
268
+ * Ohne `size` entscheidet die Regel aus `qr-groesse.ts`: so gross wie
269
+ * moeglich, gedeckelt durch `options.groesse` (Vorgabe `auto` = der
270
+ * Bestandswert 4 dieses Pakets). Passt das Symbol auch mit der
271
+ * Ausnahmegroesse nicht aufs Papier, geht **kein** QR-Befehl hinaus und
272
+ * `doc.qrFehler` sagt warum: der Drucker schneidet ein zu breites Symbol
273
+ * nicht ab, er laesst es weg — ein Befehl, von dem man weiss, dass er nichts
274
+ * druckt, taeuschte nur einen Ausdruck vor. Den Bildweg kennt diese Ebene
275
+ * nicht; den faehrt `escPosQrRaster` bzw. der Belegweg in `layout-escpos.ts`.
276
+ *
277
+ * Eine leere Nutzlast geht unveraendert durch (fester Bestandsweg, keine
278
+ * Rechnung): sie ist ein Datenfehler, kein Papierfehler, und der Aufrufer
279
+ * behandelt sie ohnehin schon.
280
+ */
218
281
  export declare function escPosQrCode(doc: EscPosDocument, text: string, options?: EscPosQrOptions): void;
282
+ /**
283
+ * Der Bildweg: ein fertiges QR-Raster als Rasterbild (`GS v 0`) — der
284
+ * Notausgang, wenn der native Befehl das Symbol nicht auf das Papier bringt.
285
+ *
286
+ * Ein Pflichtbeleg ohne QR ist der schlechteste aller Ausgaenge; als Bild
287
+ * geht jedes Symbol hinaus, weil die Punkte je Modul hier bis auf 1 fallen
288
+ * duerfen. Dafuer ist das Bild langsamer und auf manchen Geraeten blasser.
289
+ *
290
+ * Das Raster selbst kommt vom Aufrufer (siehe `QrMatrix`): dieses Paket
291
+ * rechnet keine QR-Codes und verarbeitet keine Bilder.
292
+ */
293
+ export declare function escPosQrRaster(doc: EscPosDocument, matrix: QrMatrix, options?: EscPosQrRasterOptions): void;
294
+ /**
295
+ * Punkte je Modul, mit denen `escPosQrRaster` ein Raster dieser Groesse auf
296
+ * dieses Papier bringt — dieselbe Rechnung, nur ohne Untergrenze 3: ein Bild
297
+ * darf bis auf einen Punkt je Modul schrumpfen und passt darum immer.
298
+ */
299
+ export declare function qrRasterPunkte(paperSize: PosPaperSize, moduleAnzahl: number, options?: {
300
+ groesse?: QrModulGroesse;
301
+ ruhezoneModule?: number;
302
+ }): number;
219
303
  export {};