@risleylima/escpos 0.2.1 → 1.0.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 (107) hide show
  1. package/README.md +94 -766
  2. package/dist/adapter/index.d.ts +29 -0
  3. package/dist/adapter/index.d.ts.map +1 -0
  4. package/dist/adapter/index.js +25 -0
  5. package/dist/adapter/index.js.map +1 -0
  6. package/dist/index.d.ts +14 -0
  7. package/dist/index.d.ts.map +1 -0
  8. package/dist/index.js +25 -0
  9. package/dist/index.js.map +1 -0
  10. package/dist/network-adapter/index.d.ts +24 -0
  11. package/dist/network-adapter/index.d.ts.map +1 -0
  12. package/dist/network-adapter/index.js +263 -0
  13. package/dist/network-adapter/index.js.map +1 -0
  14. package/dist/printer/commands-types.d.ts +37 -0
  15. package/dist/printer/commands-types.d.ts.map +1 -0
  16. package/dist/printer/commands-types.js +63 -0
  17. package/dist/printer/commands-types.js.map +1 -0
  18. package/dist/printer/commands.d.ts +169 -0
  19. package/dist/printer/commands.d.ts.map +1 -0
  20. package/dist/printer/commands.js +192 -0
  21. package/dist/printer/commands.js.map +1 -0
  22. package/dist/printer/image-loader.d.ts +17 -0
  23. package/dist/printer/image-loader.d.ts.map +1 -0
  24. package/dist/printer/image-loader.js +462 -0
  25. package/dist/printer/image-loader.js.map +1 -0
  26. package/dist/printer/image.d.ts +43 -0
  27. package/dist/printer/image.d.ts.map +1 -0
  28. package/dist/printer/image.js +132 -0
  29. package/dist/printer/image.js.map +1 -0
  30. package/dist/printer/index.d.ts +158 -0
  31. package/dist/printer/index.d.ts.map +1 -0
  32. package/dist/printer/index.js +703 -0
  33. package/dist/printer/index.js.map +1 -0
  34. package/dist/printer/profiles/bematech/mp4200th.d.ts +13 -0
  35. package/dist/printer/profiles/bematech/mp4200th.d.ts.map +1 -0
  36. package/dist/printer/profiles/bematech/mp4200th.js +29 -0
  37. package/dist/printer/profiles/bematech/mp4200th.js.map +1 -0
  38. package/dist/printer/profiles/custom/bematech-mp4200th.d.ts +13 -0
  39. package/dist/printer/profiles/custom/bematech-mp4200th.d.ts.map +1 -0
  40. package/dist/printer/profiles/custom/bematech-mp4200th.js +21 -0
  41. package/dist/printer/profiles/custom/bematech-mp4200th.js.map +1 -0
  42. package/dist/printer/profiles/custom/vkp80iii.d.ts +19 -0
  43. package/dist/printer/profiles/custom/vkp80iii.d.ts.map +1 -0
  44. package/dist/printer/profiles/custom/vkp80iii.js +87 -0
  45. package/dist/printer/profiles/custom/vkp80iii.js.map +1 -0
  46. package/dist/printer/profiles/default.d.ts +7 -0
  47. package/dist/printer/profiles/default.d.ts.map +1 -0
  48. package/dist/printer/profiles/default.js +15 -0
  49. package/dist/printer/profiles/default.js.map +1 -0
  50. package/dist/printer/profiles/index.d.ts +41 -0
  51. package/dist/printer/profiles/index.d.ts.map +1 -0
  52. package/dist/printer/profiles/index.js +98 -0
  53. package/dist/printer/profiles/index.js.map +1 -0
  54. package/dist/printer/profiles/merge.d.ts +7 -0
  55. package/dist/printer/profiles/merge.d.ts.map +1 -0
  56. package/dist/printer/profiles/merge.js +58 -0
  57. package/dist/printer/profiles/merge.js.map +1 -0
  58. package/dist/printer/profiles/types.d.ts +99 -0
  59. package/dist/printer/profiles/types.d.ts.map +1 -0
  60. package/dist/printer/profiles/types.js +8 -0
  61. package/dist/printer/profiles/types.js.map +1 -0
  62. package/dist/printer/utils.d.ts +9 -0
  63. package/dist/printer/utils.d.ts.map +1 -0
  64. package/dist/printer/utils.js +54 -0
  65. package/dist/printer/utils.js.map +1 -0
  66. package/dist/serial-adapter/index.d.ts +17 -0
  67. package/dist/serial-adapter/index.d.ts.map +1 -0
  68. package/dist/serial-adapter/index.js +172 -0
  69. package/dist/serial-adapter/index.js.map +1 -0
  70. package/dist/usb-adapter/index.d.ts +20 -0
  71. package/dist/usb-adapter/index.d.ts.map +1 -0
  72. package/dist/usb-adapter/index.js +264 -0
  73. package/dist/usb-adapter/index.js.map +1 -0
  74. package/package.json +42 -15
  75. package/CHANGELOG.md +0 -74
  76. package/docs/COVERAGE_ANALYSIS.md +0 -98
  77. package/docs/DEPENDENCIES_REVIEW.md +0 -127
  78. package/docs/JSDOC_REVIEW.md +0 -122
  79. package/docs/LIBRARY_OVERVIEW.md +0 -383
  80. package/docs/PRE_PUBLISH_CHECKLIST.md +0 -331
  81. package/docs/PUBLIC_API_ANALYSIS.md +0 -223
  82. package/docs/README.md +0 -37
  83. package/docs/SERIALPORT_V13_MIGRATION_COMPLETE.md +0 -127
  84. package/docs/TESTS_IMPLEMENTED.md +0 -129
  85. package/docs/USB_V2_REVIEW.md +0 -148
  86. package/docs/VERIFICATION_RESULTS.md +0 -172
  87. package/docs/VERSIONING.md +0 -102
  88. package/examples/printTest.js +0 -59
  89. package/index.js +0 -7
  90. package/jest.config.js +0 -16
  91. package/src/adapter/index.js +0 -75
  92. package/src/printer/commands.js +0 -199
  93. package/src/printer/image.js +0 -159
  94. package/src/printer/index.js +0 -621
  95. package/src/printer/utils.js +0 -58
  96. package/src/serial-adapter/index.js +0 -198
  97. package/src/usb-adapter/index.js +0 -283
  98. package/tests/README.md +0 -67
  99. package/tests/integration/printer-flow.test.js +0 -128
  100. package/tests/unit/adapters/adapter.test.js +0 -49
  101. package/tests/unit/adapters/serial-adapter.test.js +0 -238
  102. package/tests/unit/adapters/usb-adapter.test.js +0 -319
  103. package/tests/unit/image/image.test.js +0 -157
  104. package/tests/unit/printer/buffer.test.js +0 -60
  105. package/tests/unit/printer/commands.test.js +0 -109
  106. package/tests/unit/printer/printer.test.js +0 -405
  107. package/tests/unit/utils/utils.test.js +0 -96
package/README.md CHANGED
@@ -3,832 +3,160 @@
3
3
  [![npm version](https://img.shields.io/npm/v/@risleylima/escpos.svg)](https://www.npmjs.com/package/@risleylima/escpos)
4
4
  [![Node.js](https://img.shields.io/node/v/@risleylima/escpos.svg)](https://nodejs.org/)
5
5
  [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
6
+ [![Tests](https://img.shields.io/badge/tests-138%20passed-brightgreen.svg)]()
6
7
 
7
- A modern, well-tested Node.js library for generating ESC/POS commands and communicating with thermal printers via USB or Serial ports.
8
+ **The definitive thermal printing library for Node.js.** Industrial-grade robustness, O(n) performance, and a fully agnostic architecture.
8
9
 
9
- ## Features
10
+ ## 🚀 Why choose this library?
10
11
 
11
- - 🖨️ **Full ESC/POS Support**: Complete implementation of ESC/POS commands
12
- - 🔌 **Multiple Adapters**: USB and Serial port support
13
- - 📝 **Fluent API**: Method chaining for easy command composition
14
- - 🖼️ **Image Printing**: Convert and print images on thermal printers
15
- - 📊 **Barcode Generation**: Support for multiple barcode formats (EAN13, EAN8, CODE128, CODE39, etc.)
16
- - 🌐 **Encoding Support**: Multiple character encodings (GB18030, UTF-8, ASCII, etc.)
17
- - 📦 **Modern JavaScript**: Promise-based async/await, ES6+
18
- - ✅ **Well Tested**: 100% test coverage with 145+ tests
19
- - 📚 **Fully Documented**: Complete JSDoc documentation
20
- - 🔄 **Event-Driven**: EventEmitter-based architecture for connection events
12
+ This library was designed to solve common technical bottlenecks found in traditional thermal printing implementations. Our focus is on reliability, performance, and clean architecture.
21
13
 
22
- ## Installation
14
+ ### Technical Advantages
23
15
 
24
- ### Via NPM
16
+ | Feature | Our Modern Approach | Common Legacy Patterns |
17
+ | :--- | :--- | :--- |
18
+ | **Buffer Efficiency** | **O(n)** (Smart chunk accumulation) | O(n²) (Recursive concatenation) |
19
+ | **Event Loop** | **Protected** (Async pixel processing) | Blocked (Synchronous processing) |
20
+ | **State Management** | **Instantiable** (Multi-printer support) | Singletons (Global state limits) |
21
+ | **Protocol Support** | **Modern GS ( k** (QR Functions 165/167/169/180/181) | Legacy ESC Z commands |
22
+ | **Connectivity** | **Fully Agnostic** (Interface-based) | Coupled to specific IO |
25
23
 
26
- ```bash
27
- npm install @risleylima/escpos
28
- ```
29
-
30
- ### Via Yarn
31
-
32
- ```bash
33
- yarn add @risleylima/escpos
34
- ```
35
-
36
- ## Requirements
37
-
38
- - **Node.js**: >= 18.0.0
39
- - **Operating System**: Linux, macOS, or Windows
40
-
41
- ### Platform-Specific Requirements
42
-
43
- #### Linux
44
- - For USB: `libusb` development libraries
45
- ```bash
46
- sudo apt-get install libusb-1.0-0-dev # Debian/Ubuntu
47
- sudo yum install libusb-devel # CentOS/RHEL
48
- ```
49
- - For Serial: Usually built-in, may need permissions
50
- ```bash
51
- sudo usermod -a -G dialout $USER # Add user to dialout group
52
- ```
53
-
54
- #### macOS
55
- - For USB: Usually works out of the box
56
- - For Serial: Usually works out of the box
57
-
58
- #### Windows
59
- - For USB: Usually works out of the box
60
- - For Serial: Usually works out of the box
61
-
62
- ## Quick Start
63
-
64
- ### USB Printer Example
65
-
66
- ```javascript
67
- const { USB, Printer } = require('@risleylima/escpos');
68
-
69
- (async () => {
70
- try {
71
- // Connect to USB printer (VID and PID)
72
- await USB.connect(1046, 20497);
73
- await USB.open();
74
-
75
- // Create printer instance
76
- const printer = new Printer(USB);
77
-
78
- // Print a receipt
79
- printer
80
- .hardware('init')
81
- .align('ct')
82
- .size(2, 2)
83
- .textln('RECEIPT')
84
- .size(1, 1)
85
- .align('lt')
86
- .textln('Item 1: $10.00')
87
- .textln('Item 2: $20.00')
88
- .align('rt')
89
- .textln('Total: $30.00')
90
- .cut(true);
91
-
92
- // Send to printer
93
- await printer.flush();
94
-
95
- // Close connection
96
- await USB.close();
97
- await USB.disconnect();
98
- } catch (error) {
99
- console.error('Error:', error);
100
- }
101
- })();
102
- ```
103
-
104
- ### Serial Printer Example
105
-
106
- ```javascript
107
- const { Serial, Printer } = require('@risleylima/escpos');
108
-
109
- (async () => {
110
- try {
111
- // Connect to serial printer
112
- await Serial.connect('/dev/ttyUSB0');
113
- await Serial.open();
114
-
115
- // Create printer instance
116
- const printer = new Printer(Serial);
117
-
118
- // Print text
119
- printer
120
- .hardware('init')
121
- .textln('Hello, World!')
122
- .cut(true);
123
-
124
- // Send to printer
125
- await printer.flush();
126
-
127
- // Close connection
128
- await Serial.close();
129
- await Serial.disconnect();
130
- } catch (error) {
131
- console.error('Error:', error);
132
- }
133
- })();
134
- ```
135
-
136
- ## API Documentation
137
-
138
- ### Exports
139
-
140
- The library exports the following modules:
141
-
142
- ```javascript
143
- const { USB, Serial, Printer, Adapter, Image } = require('@risleylima/escpos');
144
- ```
145
-
146
- - **`USB`**: USB adapter instance (EventEmitter)
147
- - **`Serial`**: Serial port adapter instance (EventEmitter)
148
- - **`Printer`**: ESC/POS command generator class
149
- - **`Adapter`**: Base adapter class
150
- - **`Image`**: Image processing utilities
151
-
152
- ### USB Adapter
153
-
154
- #### Methods
155
-
156
- ##### `USB.listUSB()`
157
- List all available USB printer devices.
158
-
159
- ```javascript
160
- const devices = await USB.listUSB();
161
- console.log(devices); // Array of USB devices with manufacturer and product info
162
- ```
163
-
164
- ##### `USB.connect(vid, pid)`
165
- Connect to a USB printer by Vendor ID and Product ID.
166
-
167
- ```javascript
168
- await USB.connect(1046, 20497); // Connect to specific device
169
- // OR
170
- await USB.connect(); // Connect to first available printer
171
- ```
172
-
173
- **Events:**
174
- - `connect` - Emitted when device connects
175
- - `detach` - Emitted when device is unplugged
176
-
177
- ##### `USB.open()`
178
- Open the USB device and claim the printer interface.
179
-
180
- ```javascript
181
- await USB.open();
182
- ```
183
-
184
- **Events:**
185
- - `connect` - Emitted when device is opened
186
-
187
- ##### `USB.write(data)`
188
- Write data buffer to the printer.
189
-
190
- ```javascript
191
- await USB.write(Buffer.from('Hello', 'ascii'));
192
- ```
193
-
194
- ##### `USB.close()`
195
- Close the USB device connection.
196
-
197
- ```javascript
198
- await USB.close();
199
- ```
200
-
201
- **Events:**
202
- - `close` - Emitted when device closes
203
-
204
- ##### `USB.disconnect()`
205
- Disconnect from the USB device (calls `close` internally).
206
-
207
- ```javascript
208
- await USB.disconnect();
209
- ```
210
-
211
- **Events:**
212
- - `disconnect` - Emitted when device disconnects
213
-
214
- ### Serial Adapter
215
-
216
- #### Methods
217
-
218
- ##### `Serial.listSerial()`
219
- List all available serial ports.
220
-
221
- ```javascript
222
- const ports = await Serial.listSerial();
223
- console.log(ports); // Array of serial port objects with path, manufacturer, vendorId, productId, etc.
224
- ```
225
-
226
- ##### `Serial.connect(port, options)`
227
- Connect to a serial port printer.
228
-
229
- ```javascript
230
- await Serial.connect('/dev/ttyUSB0');
231
- // OR with options
232
- await Serial.connect('/dev/ttyUSB0', {
233
- baudRate: 9600,
234
- dataBits: 8,
235
- stopBits: 1,
236
- parity: 'none'
237
- });
238
- ```
239
-
240
- **Events:**
241
- - `connect` - Emitted when port connects
242
- - `close` - Emitted when reconnecting (closing previous connection)
243
-
244
- ##### `Serial.open()`
245
- Open the serial port if it's closed.
246
-
247
- ```javascript
248
- await Serial.open();
249
- ```
250
-
251
- ##### `Serial.write(data)`
252
- Write data buffer to the printer.
253
-
254
- ```javascript
255
- await Serial.write(Buffer.from('Hello', 'ascii'));
256
- ```
257
-
258
- ##### `Serial.read()`
259
- Read data from the serial port.
260
-
261
- ```javascript
262
- const data = await Serial.read();
263
- ```
264
-
265
- ##### `Serial.close(timeout)`
266
- Close the serial port connection.
267
-
268
- ```javascript
269
- await Serial.close(); // Default timeout: 50ms
270
- await Serial.close(100); // Custom timeout: 100ms
271
- ```
272
-
273
- **Events:**
274
- - `close` - Emitted when port closes
275
-
276
- ##### `Serial.disconnect(timeout)`
277
- Disconnect from the serial port (calls `close` internally).
278
-
279
- ```javascript
280
- await Serial.disconnect();
281
- ```
282
-
283
- **Events:**
284
- - `disconnect` - Emitted when port disconnects
285
-
286
- ### Printer Class
287
-
288
- #### Constructor
289
-
290
- ```javascript
291
- const printer = new Printer(adapter, options);
292
- ```
293
-
294
- **Parameters:**
295
- - `adapter` (Adapter): USB or Serial adapter instance
296
- - `options` (Object, optional):
297
- - `encoding` (String): Character encoding (default: 'GB18030')
298
- - `width` (Number): Paper width in columns (default: 48)
299
-
300
- #### Text Operations
301
-
302
- ##### `printer.print(content)`
303
- Print raw text without encoding.
304
-
305
- ```javascript
306
- printer.print('Hello');
307
- ```
308
-
309
- ##### `printer.println(content)`
310
- Print text with line break.
311
-
312
- ```javascript
313
- printer.println('Hello');
314
- ```
315
-
316
- ##### `printer.text(content, encoding)`
317
- Print text with encoding.
318
-
319
- ```javascript
320
- printer.text('Hello', 'UTF-8');
321
- ```
322
-
323
- ##### `printer.textln(content, encoding)`
324
- Print text with encoding and line break.
325
-
326
- ```javascript
327
- printer.textln('Hello', 'UTF-8');
328
- ```
329
-
330
- ##### `printer.newLine()`
331
- Send end of line command.
332
-
333
- ```javascript
334
- printer.newLine();
335
- ```
336
-
337
- #### Formatting
338
-
339
- ##### `printer.align(position)`
340
- Set text alignment.
341
-
342
- ```javascript
343
- printer.align('lt'); // Left
344
- printer.align('ct'); // Center
345
- printer.align('rt'); // Right
346
- ```
347
-
348
- ##### `printer.size(width, height)`
349
- Set text size (1-8 for both width and height).
350
-
351
- ```javascript
352
- printer.size(2, 2); // Double width and height
353
- ```
354
-
355
- ##### `printer.style(type)`
356
- Set text style.
357
-
358
- ```javascript
359
- printer.style('B'); // Bold
360
- printer.style('I'); // Italic
361
- printer.style('U'); // Underline
362
- printer.style('NORMAL'); // Normal
363
- ```
364
-
365
- ##### `printer.font(family)`
366
- Set font family.
367
-
368
- ```javascript
369
- printer.font('A'); // Font A (42 columns)
370
- printer.font('B'); // Font B (56 columns)
371
- printer.font('C'); // Font C
372
- ```
373
-
374
- ##### `printer.encode(encoding)`
375
- Set character encoding.
376
-
377
- ```javascript
378
- printer.encode('UTF-8');
379
- printer.encode('GB18030');
380
- ```
24
+ ---
381
25
 
382
- #### Hardware Control
26
+ ## 🛠️ Architectural Pillars
383
27
 
384
- ##### `printer.hardware(command)`
385
- Send hardware commands.
28
+ 1. **Transport Agnostic (IO):** The printer core is pure and communicates through an `AdapterLike` abstraction. Use USB, Serial, or Network interchangeably.
29
+ 2. **Model Agnostic (Profiles):** Handle manufacturer-specific "quirks" (Epson, Elgin, Bematech, Custom) via a robust Profile system.
30
+ 3. **Industrial Reliability:** Built-in mechanisms for `drain` and graceful shutdown to ensure zero data loss.
386
31
 
387
- ```javascript
388
- printer.hardware('init'); // Initialize printer
389
- ```
390
-
391
- ##### `printer.cut(partial, feed)`
392
- Cut paper.
393
-
394
- ```javascript
395
- printer.cut(true); // Partial cut
396
- printer.cut(false); // Full cut
397
- printer.cut(true, 5); // Partial cut with 5 line feeds
398
- ```
32
+ ---
399
33
 
400
- ##### `printer.beep(count, time)`
401
- Beep buzzer.
34
+ ## 📦 Installation
402
35
 
403
- ```javascript
404
- printer.beep(2, 1); // Beep 2 times, 100ms each
36
+ ```bash
37
+ npm install @risleylima/escpos
405
38
  ```
406
39
 
407
- ##### `printer.cashdraw(pin)`
408
- Open cash drawer.
409
-
410
- ```javascript
411
- printer.cashdraw(2); // Pulse pin 2
412
- printer.cashdraw(5); // Pulse pin 5
413
- ```
40
+ ---
414
41
 
415
- #### Barcode
42
+ ## 🧰 Development Setup
416
43
 
417
- ##### `printer.barcode(code, type, options)`
418
- Print barcode.
44
+ - **Official package manager:** `yarn`
45
+ - Use `yarn install` for dependency install in this repository.
46
+ - Use `yarn test`, `yarn test:coverage`, and `yarn build` for local workflows.
419
47
 
420
- ```javascript
421
- // EAN13 barcode
422
- printer.barcode('123456789012', 'EAN13');
423
-
424
- // CODE128 with options
425
- printer.barcode('ABC123', 'CODE128', {
426
- width: 2,
427
- height: 100,
428
- position: 'BLW', // Below: 'OFF', 'ABV', 'BLW', 'BTH'
429
- font: 'A',
430
- includeParity: true
431
- });
48
+ ```bash
49
+ yarn install
50
+ yarn build
51
+ yarn test
432
52
  ```
433
53
 
434
- **Supported Types:**
435
- - `EAN13`, `EAN8`, `UPC-A`, `UPC-E`
436
- - `CODE39`, `CODE93`, `CODE128`
437
- - `ITF`, `NW7`
438
-
439
- #### Image Printing
440
-
441
- ##### `printer.image(image, density)`
442
- Print image in bitmap mode.
443
-
444
- ```javascript
445
- const { Image } = require('@risleylima/escpos');
446
-
447
- // Load image
448
- const image = await Image.load('/path/to/image.png', 'image/png');
449
-
450
- // Print image
451
- printer.image(image, 'd24'); // Density: 'd8', 's8', 'd24', 's24'
452
- ```
54
+ ---
453
55
 
454
- ##### `printer.raster(image, mode)`
455
- Print image in raster mode.
56
+ ## Quick Start
456
57
 
58
+ ### Network (TCP RAW) Example
457
59
  ```javascript
458
- const image = await Image.load('/path/to/image.png', 'image/png');
459
- printer.raster(image, 'normal'); // Mode: 'normal', 'dw', 'dh', 'dwdh'
460
- ```
60
+ import { Network, Printer } from '@risleylima/escpos';
461
61
 
462
- #### Control Methods
62
+ const adapter = new Network();
63
+ await adapter.connect('10.1.1.50', 9100);
64
+ await adapter.open();
463
65
 
464
- ##### `printer.flush()`
465
- Send buffered data to printer.
66
+ const printer = new Printer(adapter);
67
+ printer.textln('Hello World').cut();
466
68
 
467
- ```javascript
468
69
  await printer.flush();
70
+ await adapter.close();
469
71
  ```
470
72
 
471
- ##### `printer.close(options)`
472
- Close connection and flush buffer.
473
-
474
- ```javascript
475
- await printer.close();
476
- ```
477
-
478
- #### Utility Methods
479
-
480
- ##### `printer.drawLine(character)`
481
- Draw a line with specified character.
482
-
483
- ```javascript
484
- printer.drawLine('-'); // Draw line with dashes
485
- printer.drawLine('='); // Draw line with equals
486
- ```
487
-
488
- ##### `printer.feed(n)`
489
- Feed paper n lines.
490
-
491
- ```javascript
492
- printer.feed(3); // Feed 3 lines
493
- ```
494
-
495
- ##### `printer.color(color)`
496
- Set print color (if printer supports it).
497
-
73
+ ### USB Example
498
74
  ```javascript
499
- printer.color(0); // Black
500
- printer.color(1); // Red
501
- ```
75
+ import { USB, Printer } from '@risleylima/escpos';
502
76
 
503
- ##### `printer.setReverseColors(bool)`
504
- Reverse colors (if printer supports it).
77
+ const adapter = new USB();
78
+ await adapter.connect(0x04b8, 0x0202); // VID, PID
79
+ await adapter.open();
505
80
 
506
- ```javascript
507
- printer.setReverseColors(true); // White text on black background
508
- printer.setReverseColors(false); // Normal
509
- ```
510
-
511
- ##### `printer.raw(data)`
512
- Write raw ESC/POS commands.
513
-
514
- ```javascript
515
- // Hex string
516
- printer.raw('1B40'); // Initialize
517
-
518
- // Buffer
519
- printer.raw(Buffer.from('1B40', 'hex'));
520
- ```
81
+ const printer = new Printer(adapter);
82
+ printer.textln('USB Printing').cut();
521
83
 
522
- ## Advanced Examples
523
-
524
- ### Complete Receipt
525
-
526
- ```javascript
527
- const { USB, Printer } = require('@risleylima/escpos');
528
-
529
- (async () => {
530
- await USB.connect(1046, 20497);
531
- await USB.open();
532
-
533
- const printer = new Printer(USB, {
534
- encoding: 'UTF-8',
535
- width: 48
536
- });
537
-
538
- printer
539
- .hardware('init')
540
- .beep(1, 1)
541
- .align('ct')
542
- .size(2, 2)
543
- .textln('MY STORE')
544
- .size(1, 1)
545
- .textln('123 Main Street')
546
- .textln('City, State 12345')
547
- .textln('Phone: (555) 123-4567')
548
- .drawLine()
549
- .align('lt')
550
- .textln('Date: ' + new Date().toLocaleString())
551
- .textln('Receipt #: 001234')
552
- .drawLine()
553
- .textln('Item 1 $10.00')
554
- .textln('Item 2 $20.00')
555
- .textln('Item 3 $15.00')
556
- .drawLine()
557
- .align('rt')
558
- .textln('Subtotal: $45.00')
559
- .textln('Tax: $4.50')
560
- .size(2, 1)
561
- .textln('Total: $49.50')
562
- .size(1, 1)
563
- .drawLine()
564
- .align('ct')
565
- .textln('Thank you for your purchase!')
566
- .feed(3)
567
- .cut(true);
568
-
569
- await printer.flush();
570
- await USB.close();
571
- await USB.disconnect();
572
- })();
84
+ await printer.flush();
85
+ await adapter.close();
573
86
  ```
574
87
 
575
- ### Barcode Example
576
-
577
- ```javascript
578
- const { USB, Printer } = require('@risleylima/escpos');
579
-
580
- (async () => {
581
- await USB.connect(1046, 20497);
582
- await USB.open();
583
-
584
- const printer = new Printer(USB);
585
-
586
- printer
587
- .hardware('init')
588
- .align('ct')
589
- .textln('PRODUCT CODE')
590
- .barcode('123456789012', 'EAN13', {
591
- width: 2,
592
- height: 100,
593
- position: 'BLW',
594
- font: 'A'
595
- })
596
- .feed(2)
597
- .cut(true);
598
-
599
- await printer.flush();
600
- await USB.close();
601
- await USB.disconnect();
602
- })();
603
- ```
88
+ ---
604
89
 
605
- ### Image Printing Example
90
+ ## 📝 Visual Result Preview
606
91
 
607
- ```javascript
608
- const { USB, Printer, Image } = require('@risleylima/escpos');
609
-
610
- (async () => {
611
- await USB.connect(1046, 20497);
612
- await USB.open();
613
-
614
- const printer = new Printer(USB);
615
-
616
- // Load and print image
617
- const image = await Image.load('/path/to/logo.png', 'image/png');
618
-
619
- printer
620
- .hardware('init')
621
- .align('ct')
622
- .image(image, 'd24')
623
- .feed(2)
624
- .textln('Company Logo')
625
- .cut(true);
626
-
627
- await printer.flush();
628
- await USB.close();
629
- await USB.disconnect();
630
- })();
92
+ ```text
93
+ ------------------------------------------------
94
+ MY STORE
95
+ 1024 Engineering Street
96
+ ------------------------------------------------
97
+ Item 001 $ 10.00
98
+ Item 002 $ 20.00
99
+ ------------------------------------------------
100
+ TOTAL $ 30.00
101
+ ------------------------------------------------
102
+ [ MODERN QR CODE HERE ]
103
+ ------------------------------------------------
631
104
  ```
632
105
 
633
- ### Event Handling
106
+ ---
634
107
 
635
- ```javascript
636
- const { USB, Printer } = require('@risleylima/escpos');
637
-
638
- USB.on('connect', (device) => {
639
- console.log('Device connected:', device);
640
- });
641
-
642
- USB.on('disconnect', (device) => {
643
- console.log('Device disconnected:', device);
644
- });
645
-
646
- USB.on('close', (device) => {
647
- console.log('Device closed:', device);
648
- });
649
-
650
- USB.on('detach', () => {
651
- console.log('Device unplugged!');
652
- });
653
-
654
- (async () => {
655
- await USB.connect(1046, 20497);
656
- await USB.open();
657
-
658
- const printer = new Printer(USB);
659
- printer.textln('Hello, World!');
660
- await printer.flush();
661
-
662
- await USB.close();
663
- await USB.disconnect();
664
- })();
665
- ```
108
+ ## 🖼️ Industrial Image Processing
666
109
 
667
- ### Finding USB Printers
110
+ - **Formats:** PNG (Indexed/Gray/RGB), BMP (1/4/8/24-bit), JPEG, GIF, and SVG.
111
+ - **Non-blocking:** Asynchronous decoding with `setImmediate` ensuring your server stays responsive.
668
112
 
669
113
  ```javascript
670
- const { USB } = require('@risleylima/escpos');
671
-
672
- (async () => {
673
- // List all USB printers
674
- const devices = await USB.listUSB();
675
-
676
- console.log('Found printers:');
677
- devices.forEach((device, index) => {
678
- console.log(`${index + 1}. ${device.manufacturer} - ${device.product}`);
679
- console.log(` VID: ${device.deviceDescriptor.idVendor}`);
680
- console.log(` PID: ${device.deviceDescriptor.idProduct}`);
681
- });
682
-
683
- // Connect to first printer
684
- if (devices.length > 0) {
685
- await USB.connect();
686
- await USB.open();
687
- // ... use printer
688
- }
689
- })();
114
+ import { Image } from '@risleylima/escpos';
115
+ const image = await Image.load('./logo.png');
116
+ printer.raster(image);
690
117
  ```
691
118
 
692
- ## Method Chaining
693
-
694
- The Printer class supports method chaining for fluent API:
695
-
696
- ```javascript
697
- printer
698
- .hardware('init')
699
- .align('ct')
700
- .size(2, 2)
701
- .textln('TITLE')
702
- .size(1, 1)
703
- .align('lt')
704
- .textln('Content here')
705
- .cut(true);
706
- ```
119
+ ---
707
120
 
708
- ## Error Handling
121
+ ## 🔍 Status Monitoring
709
122
 
710
- Always wrap printer operations in try-catch blocks:
123
+ Reliable hardware feedback:
711
124
 
712
125
  ```javascript
713
- try {
714
- await USB.connect(1046, 20497);
715
- await USB.open();
716
-
717
- const printer = new Printer(USB);
718
- printer.textln('Hello');
719
- await printer.flush();
720
-
721
- await USB.close();
722
- await USB.disconnect();
723
- } catch (error) {
724
- console.error('Printer error:', error);
725
- // Handle error appropriately
126
+ const status = await printer.getStatus('PAPER');
127
+ if (status[0] & 0x0C) {
128
+ console.log('Alert: Paper low or out of paper!');
726
129
  }
727
130
  ```
728
131
 
729
- ## Testing
730
-
731
- The library includes comprehensive tests:
732
-
733
- ```bash
734
- # Run all tests
735
- npm test
736
-
737
- # Run tests in watch mode
738
- npm run test:watch
739
-
740
- # Run tests with coverage
741
- npm run test:coverage
742
- ```
743
-
744
- **Test Coverage: 100%** ✅
745
- - 145+ tests
746
- - Unit and integration tests
747
- - All edge cases covered
748
-
749
- ## Documentation
750
-
751
- Additional documentation is available in the `docs/` folder:
752
-
753
- - [Library Overview](./docs/LIBRARY_OVERVIEW.md) - Complete library overview
754
- - [JSDoc Review](./docs/JSDOC_REVIEW.md) - JSDoc documentation review
755
- - [Test Coverage](./docs/COVERAGE_ANALYSIS.md) - Test coverage analysis
756
- - [Dependencies Review](./docs/DEPENDENCIES_REVIEW.md) - Dependencies status
757
- - [USB v2 Migration](./docs/USB_V2_MIGRATION.md) - USB library migration guide
758
- - [SerialPort v13 Migration](./docs/SERIALPORT_V13_MIGRATION_COMPLETE.md) - SerialPort migration guide
759
-
760
- ## Contributing
761
-
762
- Contributions are welcome! Please feel free to submit a Pull Request.
763
-
764
- 1. Fork the repository
765
- 2. Create your feature branch (`git checkout -b feature/AmazingFeature`)
766
- 3. Commit your changes (`git commit -m 'Add some AmazingFeature'`)
767
- 4. Push to the branch (`git push origin feature/AmazingFeature`)
768
- 5. Open a Pull Request
769
-
770
- ### Development Setup
771
-
772
- ```bash
773
- # Clone repository
774
- git clone https://github.com/risleylima/escpos.git
775
- cd escpos
776
-
777
- # Install dependencies
778
- npm install
779
- # or
780
- yarn install
781
-
782
- # Run tests
783
- npm test
784
-
785
- # Run tests with coverage
786
- npm run test:coverage
787
- ```
788
-
789
- ## License
790
-
791
- MIT License
132
+ ---
792
133
 
793
- Copyright (c) 2021 Risley Lima risley@rlimainfo.com.br
134
+ ## 🖨️ Profile Support
794
135
 
795
- Permission is hereby granted, free of charge, to any person obtaining a copy
796
- of this software and associated documentation files (the "Software"), to deal
797
- in the Software without restriction, including without limitation the rights
798
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
799
- copies of the Software, and to permit persons to whom the Software is
800
- furnished to do so, subject to the following conditions:
136
+ The library uses profiles to handle model-specific commands:
801
137
 
802
- The above copyright notice and this permission notice shall be included in all
803
- copies or substantial portions of the Software.
138
+ - **'default'**: Standard ESC/POS.
139
+ - **'custom-vkp80iii'**: CUSTOM VKP80III (Uses FS P for advanced cut/eject).
140
+ - **'bematech-mp4200th'**: Bematech MP-4200 TH in ESC/POS mode.
804
141
 
805
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
806
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
807
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
808
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
809
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
810
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
811
- SOFTWARE.
142
+ You can also register model profiles at runtime with `registerProfile(...)`, or use an isolated registry with `createProfileRegistry(...)` for multi-tenant applications.
812
143
 
813
- ## Acknowledgments
144
+ ---
814
145
 
815
- This library is a refactoring/rewrite of [node-escpos](https://github.com/song940/node-escpos) by Lsong, with improvements and modern JavaScript patterns.
146
+ ## ⚙️ Reliability and Safety Notes
816
147
 
817
- ## Support
148
+ - `flush()` is transactional: if adapter write fails, payload is preserved in buffer for retry/recovery.
149
+ - Printer I/O is serialized internally for `flush()`, `close()`, and `getStatus()` to reduce race conditions in concurrent flows.
150
+ - Passing an unknown profile id now fails fast with a descriptive error instead of silently falling back.
818
151
 
819
- - **Issues**: [GitHub Issues](https://github.com/risleylima/escpos/issues)
820
- - **Email**: risley@rlimainfo.com.br
152
+ ---
821
153
 
822
- ## Changelog
154
+ ## ✅ Reliability
823
155
 
824
- ### v0.0.14
825
- - Updated all dependencies to latest versions
826
- - Migrated USB library from v1 to v2 (Promise-based)
827
- - ✅ Migrated SerialPort from v12 to v13 (Promise-based)
828
- - ✅ 100% test coverage (145+ tests)
829
- - ✅ Complete JSDoc documentation
830
- - ✅ Architecture improvements and bug fixes
156
+ - **138 Unit and Integration Tests.**
157
+ - **Strict TypeScript:** Full type safety for the entire ESC/POS command set.
158
+ - **Spec-Validated:** QR Code aligned to ESC/POS GS ( k (Functions 165/167/169/180/181) and industrial connection lifecycles.
831
159
 
832
160
  ---
833
161
 
834
- **Made with ❤️ by [Rlima Info](https://github.com/risleylima)**
162
+ **Built with ❤️ for mission-critical systems.**