@alizadefaig/pos-server 1.2.28 → 1.2.31
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.
- package/app/core/Context.js +4 -1
- package/app/core/auth/scope.js +15 -2
- package/app/core/index.js +16 -0
- package/app/core/models/Order.js +60 -4
- package/app/core/models/OrderProduct.js +5 -0
- package/app/core/repositories/ProductRelations.js +4 -4
- package/app/core/resources/OrderResource.js +1 -0
- package/app/core/resources/TeamResource.js +7 -1
- package/app/core/services/AuthService.js +60 -8
- package/app/core/services/InitService.js +23 -4
- package/app/core/services/OrderProductService.js +6 -0
- package/app/core/services/OrderService.js +8 -3
- package/app/core/services/PrintService.js +16 -4
- package/app/core/services/ReportService.js +87 -55
- package/app/core/support/teamSettings.js +10 -1
- package/app/core/support/terminalAccess.js +93 -0
- package/app/core/support/unlock.js +9 -1
- package/app/db/migrations/013_terminal_bindings.sql +5 -0
- package/app/netstats.js +98 -0
- package/app/sync/config.js +1 -1
- package/app/sync/discovery.js +201 -38
- package/app/sync/index.js +40 -29
- package/package.json +1 -1
- package/routes/desktop/api/offline.js +1 -1
- package/routes/desktop/api/printers.js +33 -11
- package/routes/desktop/local.js +1 -1
- package/routes/server/api/platform.js +1 -1
- package/server.js +4 -0
|
@@ -16,18 +16,40 @@ const appConfig = getConfig();
|
|
|
16
16
|
let PROXY_TARGET = appConfig.apiUrl || 'http://localhost:8000';
|
|
17
17
|
const getUsbPrinters = async () => {
|
|
18
18
|
let result = [];
|
|
19
|
-
|
|
19
|
+
let usbDevices = [];
|
|
20
|
+
try {
|
|
21
|
+
usbDevices = escpos.USB.findPrinter();
|
|
22
|
+
} catch (e) {
|
|
23
|
+
console.warn('[printers] usb scan failed:', e.message);
|
|
24
|
+
return result;
|
|
25
|
+
}
|
|
20
26
|
for (const usbDevice of usbDevices) {
|
|
21
|
-
usbDevice.
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
27
|
+
const {idVendor, idProduct, iProduct} = usbDevice.deviceDescriptor;
|
|
28
|
+
const printer = {type: 'USB', name: null, vendor_id: idVendor, product_id: idProduct};
|
|
29
|
+
// На Windows libusb открывает только устройство на драйвере WinUSB. Принтер на родном
|
|
30
|
+
// драйвере (usbprint.sys / драйвер производителя) даёт LIBUSB_ERROR_NOT_SUPPORTED —
|
|
31
|
+
// раньше это исключение роняло весь скан в 500, и не было видно даже LAN-принтеров.
|
|
32
|
+
let opened = false;
|
|
33
|
+
try {
|
|
34
|
+
usbDevice.open();
|
|
35
|
+
opened = true;
|
|
36
|
+
printer.name = await getStringDescriptor(usbDevice, iProduct);
|
|
37
|
+
} catch (e) {
|
|
38
|
+
printer.error = e.message;
|
|
39
|
+
console.warn(`[printers] usb ${idVendor}:${idProduct} not opened:`, e.message);
|
|
40
|
+
} finally {
|
|
41
|
+
if (opened) {
|
|
42
|
+
try {
|
|
43
|
+
usbDevice.close();
|
|
44
|
+
} catch (e) {
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
if (!printer.name) {
|
|
49
|
+
const hex = (n) => Number(n).toString(16).padStart(4, '0');
|
|
50
|
+
printer.name = `USB ${hex(idVendor)}:${hex(idProduct)}`;
|
|
51
|
+
}
|
|
52
|
+
result.push(printer);
|
|
31
53
|
}
|
|
32
54
|
|
|
33
55
|
return result;
|
package/routes/desktop/local.js
CHANGED
|
@@ -61,7 +61,7 @@ router.get('/local/status', (req, res) => {
|
|
|
61
61
|
|
|
62
62
|
// Ведомый ищет мастера (app/sync/discovery.js): подписанный ответ на nonce, без ключа зала.
|
|
63
63
|
router.get('/local/whoami', (req, res) => {
|
|
64
|
-
const answer = isSyncEnabled() ? sync.whoami(req.query.nonce) : null;
|
|
64
|
+
const answer = isSyncEnabled() ? sync.whoami(req.query.nonce, String(req.socket.remoteAddress || '').replace(/^::ffff:/, '')) : null;
|
|
65
65
|
if (!answer) {
|
|
66
66
|
return res.status(404).json({success: false});
|
|
67
67
|
}
|
|
@@ -17,7 +17,7 @@ const init = (services) => new InitService(services);
|
|
|
17
17
|
|
|
18
18
|
registerOfflineRoutes(router, '/api', {
|
|
19
19
|
/** AuthController::init. `user` в ответ не входит: токен кладётся в модель и не выводится. */
|
|
20
|
-
'app.init': [CLOUD_READ, async (services) => init(services).init()],
|
|
20
|
+
'app.init': [CLOUD_READ, async (services, params, extra) => init(services).init(extra)],
|
|
21
21
|
|
|
22
22
|
/** ProductController::get / OrderProductController::get — оба ProductService::allProducts. */
|
|
23
23
|
'products.get': [CLOUD_READ, async (services) => init(services).products(services.context.teamId)],
|
package/server.js
CHANGED
|
@@ -13,6 +13,7 @@ const {internalGuard, originGuard} = require("./app/security");
|
|
|
13
13
|
const {isSyncEnabled} = require("./app/sync/config");
|
|
14
14
|
const multer = require('multer');
|
|
15
15
|
const {getLogger} = require("./app/logger/Log");
|
|
16
|
+
const netstats = require("./app/netstats");
|
|
16
17
|
|
|
17
18
|
|
|
18
19
|
|
|
@@ -69,6 +70,8 @@ const bodyParsers = [
|
|
|
69
70
|
express.urlencoded({extended: true, limit: BODY_LIMIT}),
|
|
70
71
|
upload.any(),
|
|
71
72
|
];
|
|
73
|
+
// Запросы из зала (не loopback) и их исход — для диагностики кассы (/local/status.net).
|
|
74
|
+
app.use(netstats.middleware);
|
|
72
75
|
// Мастер раздаёт фронт телефонам зала (LAN_FRONT): страница и её файлы открыты без ключа и
|
|
73
76
|
// токена — данных в них нет, а API за ними проверяется ниже. No-op без флага.
|
|
74
77
|
app.use(require('./app/sync/lanFront').middleware());
|
|
@@ -178,6 +181,7 @@ const runExpress = (conf = null) => {
|
|
|
178
181
|
|
|
179
182
|
// ==== Start Listen ====
|
|
180
183
|
const hostname = appConfig.host || 'localhost';
|
|
184
|
+
netstats.attach(server, {host: hostname, port});
|
|
181
185
|
server.listen(port, hostname, async () => {
|
|
182
186
|
if (hostname === 'localhost') {
|
|
183
187
|
console.log(`Server started on ${hostname} http://${hostname}:${port}`);
|