mm_os 2.7.7 → 2.7.9

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.
@@ -1,620 +0,0 @@
1
- /**
2
- * 查询个人记录
3
- * @param {String} clientid 客户端ID
4
- * @param {Object} param
5
- */
6
- exports.get_log = function(clientid, param) {
7
- return this.push("get_suc_record", clientid, param);
8
- }
9
-
10
- /**
11
- * 考勤打卡(无)
12
- * @param {String} clientid 客户端ID
13
- * @param {Object} uuid 用户唯一标识
14
- * @param {String} avatar base64头像
15
- * @param {Number} longtime 超时回馈
16
- */
17
- exports.sign_in = function(clientid, uuid, avatar) {
18
- // return this.push("PullRecordOnlyPic", clientid, {
19
- // "personID": uuid,
20
- // "picinfo": avatar
21
- // });
22
- }
23
-
24
- /**
25
- * 下发二维码(无)
26
- * @param {String} clientid
27
- * @param {Object} param
28
- * @param {Number} longtime 超时回馈
29
- */
30
- exports.push_qrcode = function(clientid, param) {
31
- // return this.push("ShowQRCode", clientid, param);
32
- }
33
-
34
- /**
35
- * 以图搜人(无)
36
- * @param {String} clientid 客户端ID
37
- * @param {Object} avatar 人脸照片
38
- * @param {Number} longtime 超时回馈
39
- */
40
- exports.get_member_pic = function(clientid, avatar) {
41
- // return this.push("GetPictureSearch", clientid, {
42
- // "facesluiceId": clientid,
43
- // "MaxSimilarity": 80,
44
- // "MaxNum": 1,
45
- // "picinfo": avatar
46
- // });
47
- }
48
-
49
- /**
50
- * 远程开门
51
- * @param {String} clientid 客户端ID
52
- * @param {String} uuid 用户唯一标识
53
- * @param {Boolean} pass 是否可通行 true为是
54
- * @param {String} tip 提示
55
- */
56
- exports.unlock = async function(clientid, uuid = '0', pass = false, tip = '没有访问权限') {
57
- var res = await this.push("gpio control", clientid, {
58
- // 0不开门,1开门
59
- "ctrl_type": pass ? "on" : "off"
60
- });
61
- if (!res) {
62
- return "请求超时!"
63
- }
64
- if (res.message !== "ACK") {
65
- return res.code;
66
- }
67
- return
68
- }
69
-
70
- /**
71
- * 删除成员
72
- * @param {String} clientid 客户端ID
73
- * @param {String} uuid 用户唯一标识
74
- * @param {Number} longtime 超时回馈
75
- */
76
- exports.delete_member = async function(clientid, uuid) {
77
- var res = await this.push("delete_face", clientid, {
78
- "per_id": uuid,
79
- "type": 0
80
- });
81
- if (!res) {
82
- return "请求超时!"
83
- }
84
- if (res.message !== "ACK") {
85
- return res.code;
86
- }
87
- return
88
- }
89
-
90
- exports.sleep = async function(longtime, param) {
91
- return new Promise((resolve, reject) => {
92
- setTimeout(() => {
93
- resolve(param);
94
- }, longtime);
95
- });
96
- }
97
-
98
- /**
99
- * 批量删除成员
100
- * @param {String} clientid 客户端ID
101
- * @param {Object} arr 成员列表
102
- * @param {Number} longtime 超时回馈
103
- */
104
- exports.delete_member_batch = async function(clientid, arr, longtime) {
105
- if (!this.drives[clientid]) {
106
- this.drives[clientid] = {};
107
- }
108
- if (this.drives[clientid].pushing) {
109
- return {
110
- detail: "busy"
111
- }
112
- }
113
- this.drives[clientid].pushing = 1;
114
- this.drives[clientid].mode = "update";
115
-
116
- var result;
117
- var error = 0;
118
- var success = 0;
119
- var error_info = [];
120
- var success_info = [];
121
-
122
- var now = new Date().toStr("yyyy-MM-dd hh:mm:ss");
123
- for (var i = 0; i < arr.length; i++) {
124
- var customId = arr[i];
125
- var res = await this.push("delete_face", clientid, {
126
- "per_id": customId,
127
- "type": 0
128
- }, 10000);
129
- if (!res) {
130
- await this.sleep(60000);
131
- res = await this.push("delete_face", clientid, {
132
- "per_id": customId,
133
- "type": 0
134
- }, 10000);
135
- }
136
- if (!res) {
137
- error_info.push({
138
- customId,
139
- errcode: -1,
140
- time_create: now
141
- });
142
- } else if (res.message == "ACK") {
143
- success++;
144
- success_info.push({
145
- customId,
146
- time_create: now
147
- });
148
- } else {
149
- error++;
150
- // 407 人脸像素太大(大于 1072)
151
- // 408 图片格式错误
152
- // 410 获取到的特征数据为空
153
- // 412 相似人脸禁止录入
154
- // 419 缓存初始化中
155
- // 420 图片长度小于 112
156
- error_info.push({
157
- customId,
158
- errcode: res.code.toString(),
159
- time_create: now
160
- });
161
- }
162
- }
163
- this.drives[clientid].pushing = 0;
164
- this.drives[clientid].mode = "";
165
-
166
- return {
167
- error,
168
- success,
169
- error_info,
170
- success_info,
171
- result: 'ok'
172
- };
173
- }
174
-
175
- /**
176
- * 重启设备
177
- * @param {String} clientid 设备sn
178
- */
179
- exports.reboot_device = async function(clientid) {
180
- var res = await this.push("reboot_cam", clientid, {});
181
- if (!res) {
182
- return "请求超时!"
183
- }
184
- if (res.message !== "ACK") {
185
- return res.code;
186
- }
187
- }
188
-
189
- /**
190
- * 设置设备时间
191
- * @param {String} clientid 设备sn
192
- * @param {String} datetime 日期时间
193
- */
194
- exports.set_device_time = async function(clientid, datetime) {
195
- var res = await this.push("ss_set_timing", clientid, {
196
- "body": {
197
- "datetime": datetime
198
- }
199
- });
200
- if (!res) {
201
- return "请求超时!"
202
- }
203
-
204
- if (res.message !== "ACK") {
205
- return res.code;
206
- }
207
- }
208
-
209
- /**
210
- * 恢复出厂设置
211
- * @param {String} clientid 设备sn
212
- * @param {Boolean} record 是否恢复控制记录,true为恢复
213
- * @param {Boolean} member 是否恢复成员,true为恢复
214
- * @param {Boolean} log 是否恢复请求日志,true为恢复
215
- */
216
- exports.reset_device = function(clientid, record = true, member = false, log = true) {
217
- if (record) {
218
- // 清空记录
219
- this.push("delete_record", clientid, {});
220
- }
221
-
222
- if (member) {
223
- // 删除所有成员
224
- this.push("delete_face", clientid, {
225
- type: 4
226
- });
227
- }
228
- }
229
-
230
- /**
231
- * 查询下发进度(未完成)
232
- * @param {String} clientid 设备sn
233
- */
234
- exports.get_progress = async function(clientid) {
235
- if (!this.drives[clientid]) {
236
- this.drives[clientid] = {};
237
- }
238
- return this.drives[clientid].pushing || 0;
239
- }
240
-
241
- /**
242
- * 转换进入的消息
243
- * @param {Object} push_topic
244
- * @param {Object} msg
245
- * @param {Object} topic
246
- */
247
- exports.convert_in = function(push_topic, msg, topic) {
248
- var cg = this.config;
249
- var method = msg[cg.method];
250
- if (push_topic.indexOf("heartbeat") !== -1) {
251
- method = "mqtt_heartbeat";
252
- } else if (push_topic.indexOf("face/response") !== -1) {
253
- method = "push_face";
254
- }
255
- var json = {
256
- clientid: "",
257
- id: msg[cg.msgid] || this.get_msgid(method, 'client'),
258
- method
259
- };
260
- if (msg[cg.params]) {
261
- json.params = msg[cg.params];
262
- }
263
- if (msg[cg.result]) {
264
- json.result = {
265
- code: msg.code,
266
- message: msg[cg.result]
267
- };
268
- }
269
- if (!json.params && !json.result) {
270
- json.result = msg;
271
- }
272
- json.clientid = this.get_clientid(push_topic, json.params || json.result || {}, msg, topic).toLocaleUpperCase();
273
- return json;
274
- }
275
-
276
- // exports.main = function(push_topic, params, msg, topic, index) {
277
- // console.log(push_topic, params, msg, topic, index);
278
- // }
279
-
280
- /**
281
- * 转换消息并推送
282
- */
283
- exports.push = function(method, clientid, params, longtime = 0) {
284
- var cg = this.config;
285
- var msg = {};
286
- msg.client_id = clientid;
287
- msg[cg.msgid] = this.get_msgid(method);
288
- msg[cg.method] = method;
289
- Object.assign(msg, params);
290
- return this.pushS(clientid, msg);
291
- }
292
-
293
- /**
294
- * 考勤补卡(无)
295
- * @param {String} clientid 设备sn
296
- * @param {Object} param 其他信息
297
- * @param {Number} longtime 超时回馈
298
- */
299
- exports.replacement = function(clientid, param, longtime = 0) {
300
- // return this.push("PullRecordOnlyName", clientid, param, longtime);
301
- }
302
-
303
- /**
304
- * 查询人员名单
305
- * @param {String} clientid 客户端ID
306
- * @param {Number} longtime 超时回馈
307
- */
308
- exports.get_member = async function(clientid, uuid, name) {
309
- var qy = {};
310
- if (uuid) {
311
- qy.uuid = uuid;
312
- }
313
- if (name) {
314
- qy.name = name;
315
- }
316
- var res = await this.push("query_face", qy);
317
- if (!res) {
318
- return "请求超时!"
319
- }
320
- if (res.code) {
321
- return res.pers_id;
322
- }
323
- return []
324
- }
325
-
326
- /**
327
- * 查询人员名单
328
- * @param {String} clientid 客户端ID
329
- * @param {String} uuid 用户唯一标识
330
- */
331
- exports.get_member_one = async function(clientid, uuid) {
332
- var list = await get_member(clientid, uuid);
333
- if (list.length) {
334
- return list[0]
335
- }
336
- return null;
337
- }
338
-
339
- /**
340
- * 成员模型
341
- * @param {Object} m 原始的成员
342
- */
343
- exports.member_model_out = function(m) {
344
- var obj = {
345
- "per_id": m.customId,
346
- "per_name": m.name,
347
- "idcardNum": m.nfc || '',
348
- "img_url": this.fullUrl(m.avatar),
349
- "idcardper": m.idcard,
350
- "auth_type": 0,
351
- // 1 待审核 | 2 已拒绝 | 3 已通过 | 4 黑名单 , 设备0为白名单,2为黑名单
352
- "per_type": m.state == 4 ? 2 : 0,
353
- "usr_type": m.gm,
354
- "gender": m.sex == 1 ? '男' : '女'
355
- }
356
-
357
- if (typeof(m.time_valid_start) == "object") {
358
- obj.s_time = m.time_valid_start.stamp();
359
- } else {
360
- obj.s_time = m.time_valid_start.toTime().stamp();
361
- }
362
- if (typeof(m.time_valid_end) == "object") {
363
- obj.e_time = m.time_valid_end.stamp();
364
- } else {
365
- obj.e_time = m.time_valid_end.toTime().stamp();
366
- }
367
- return obj
368
- }
369
-
370
- /**
371
- * 下发人员名单
372
- * @param {String} clientid 设备ID
373
- * @param {Object} user 人员信息
374
- */
375
- exports.update_member = async function(clientid, user) {
376
- var member = this.member_model_out(user);
377
- var res = await this.push("update_face_ex", clientid, member);
378
- if (!res) {
379
- return "请求超时!"
380
- }
381
- if (res.message !== "ACK") {
382
- return res.code;
383
- }
384
- return
385
- }
386
-
387
- /**
388
- * 批量下发人员名单(模拟) 设备本身没有批量下发,因此需要自己设计一个来模拟
389
- * @param {String} clientid 客户端ID
390
- * @param {Array} list 人员名单
391
- * @param {Number} longtime 超时回馈
392
- */
393
- exports.update_member_batch = async function(clientid, list, longtime = 0) {
394
- if (!this.drives[clientid]) {
395
- this.drives[clientid] = {};
396
- }
397
- if (this.drives[clientid].pushing) {
398
- return {
399
- detail: "busy"
400
- }
401
- }
402
- this.drives[clientid].pushing = 1;
403
- this.drives[clientid].mode = "delete";
404
-
405
- var result;
406
- var error = 0;
407
- var success = 0;
408
- var error_info = [];
409
- var success_info = [];
410
-
411
- var now = new Date().toStr("yyyy-MM-dd hh:mm:ss");
412
- for (var i = 0; i < list.length; i++) {
413
- var user = list[i];
414
- var res = await this.push("update_face_ex", clientid, this.member_model_out(user), 10000);
415
- if (!res) {
416
- await this.sleep(60000);
417
- res = await this.push("update_face_ex", clientid, this.member_model_out(user), 10000);
418
- }
419
- if (!res) {
420
- error_info.push({
421
- customId: user.customId,
422
- errcode: -1,
423
- time_create: now
424
- });
425
- } else if (res.message == "ACK") {
426
- success++;
427
- success_info.push({
428
- customId: user.customId,
429
- time_create: now
430
- });
431
- } else {
432
- error++;
433
- // 407 人脸像素太大(大于 1072)
434
- // 408 图片格式错误
435
- // 410 获取到的特征数据为空
436
- // 412 相似人脸禁止录入
437
- // 419 缓存初始化中
438
- // 420 图片长度小于 112
439
- error_info.push({
440
- customId: user.customId,
441
- errcode: res.code.toString(),
442
- time_create: now
443
- });
444
- }
445
- }
446
- this.drives[clientid].pushing = 0;
447
- this.drives[clientid].mode = "";
448
-
449
- return {
450
- error,
451
- success,
452
- error_info,
453
- success_info,
454
- result: 'ok'
455
- };
456
- }
457
-
458
- /**
459
- * 播放语音
460
- * @param {String} clientid 客户端ID
461
- * @param {Number} type 语音类型 1为没有权限,2为鉴权失败,3为鉴权成功
462
- */
463
- exports.play_audio = async function(clientid, type = 3) {
464
- var body = {};
465
- switch (type) {
466
- case 1:
467
- // 权限过期
468
- body.file_name = "deadline.wav"
469
- break;
470
- case 2:
471
- // 鉴权失败
472
- body.file_name = "failure.wav"
473
- break;
474
- case 3:
475
- // 鉴权成功
476
- body.file_name = "success.wav"
477
- break;
478
- default:
479
- break;
480
- }
481
- body.type = 0;
482
- var res = await this.push("trylisten_wav", clientid, {
483
- body
484
- });
485
-
486
- if (!res) {
487
- return "请求超时!"
488
- }
489
- if (res.message !== "ACK") {
490
- return res.code;
491
- }
492
- return
493
- }
494
-
495
- /**
496
- * 设置扫描二维码模式
497
- * @param {String} clientid 客户端ID
498
- * @param {Number} mode 模式
499
- */
500
- exports.set_qrcode_mode = async function(clientid, mode = 1) {
501
- var res = await this.push("set_qrcode_mode", clientid, {
502
- body: {
503
- "enable": 0,
504
- mode
505
- }
506
- });
507
- if (!res) {
508
- return "请求超时!"
509
- }
510
- if (res.message !== "ACK") {
511
- return res.code;
512
- }
513
- return
514
- }
515
-
516
- /**
517
- * 发送灯光
518
- * @param {String} clientid 客户端ID
519
- * @param {Number} color 颜色选项
520
- */
521
- exports.send_led = async function(clientid, color = 1) {
522
- var res = await this.push("set_led_color_test", clientid, {
523
- "body": {
524
- color
525
- }
526
- });
527
- if (!res) {
528
- return "请求超时!"
529
- }
530
- if (res.message !== "ACK") {
531
- return res.code;
532
- }
533
- return
534
- }
535
-
536
-
537
- /**
538
- * 初始化函数, 用于定义开放给前端的函数
539
- */
540
- exports.init = function() {
541
- var m = this.methods;
542
- var _this = this;
543
-
544
- m["mqtt_heartbeat"] = function(clientid, params) {
545
- if (!_this.drives[clientid]) {
546
- _this.drives[clientid] = {};
547
- }
548
- _this.drives[clientid].online = 1;
549
- _this.drives[clientid].time_last = new Date().getTime();
550
- // console.log("心跳", clientid, _this.drives[clientid]);
551
- }
552
-
553
- /**
554
- * 在线通知
555
- * @param {String} clientid 设备sn
556
- * @param {Object} param 其他信息
557
- */
558
- m["mqtt_online"] = async function(clientid, params) {
559
- _this.update_online(clientid, 1);
560
- _this.set_qrcode_mode(clientid);
561
- console.log("上线", clientid, _this.drives[clientid]);
562
- };
563
-
564
- m["push_face"] = async function(clientid, params, msg, id) {
565
- var type = 1;
566
- var action;
567
- switch (msg.type) {
568
- case "face_result":
569
- type = 1;
570
- break;
571
- case "wgin_read":
572
- type = 4;
573
- break;
574
- default:
575
- break;
576
- }
577
- var log = {
578
- customId: params.per_id,
579
- name: params.name,
580
- idcard: params.idcard,
581
- clientid,
582
- // (1刷脸验证|2远程开门|3智码开门|4刷卡验证)
583
- type,
584
- // 1白名单|2黑名单
585
- person_type: params.matchRole || params.role || 0,
586
- record_type: 1,
587
- action,
588
- nfc: params.wg_num,
589
- // usec / ext_sec
590
- time: params.ext_sec.toTime().toStr("yyyy-MM-dd hh:mm:ss"),
591
- avatar: params.img_data,
592
- sex: params.gender == '男' ? 1 : 2
593
- }
594
- $.server.exec_log(clientid, log);
595
- }
596
-
597
- m["send_qr_msg"] = async function(clientid, params, msg, id) {
598
- var qrcode = params.data;
599
- var {
600
- uuid,
601
- pass,
602
- tip,
603
- device
604
- } = await $.server.exec_qrcode(clientid, qrcode);
605
- if (device && device.online) {
606
- await _this.unlock(clientid, uuid, pass, tip);
607
- }
608
- if (tip) {
609
- if (tip.indexOf("过期") !== -1 || tip.indexOf("超限") !== -1) {
610
- _this.play_audio(clientid, 1);
611
- _this.send_led(clientid);
612
- } else if (tip.indexOf("通行") !== -1) {
613
- // _this.play_audio(clientid, 3);
614
- } else {
615
- _this.play_audio(clientid, 2);
616
- _this.send_led(clientid);
617
- }
618
- }
619
- }
620
- };
@@ -1,36 +0,0 @@
1
- {
2
- // 名称, 由中英文和下“_”组成, 用于修改或卸载 例如: demo
3
- "name": "ZS",
4
- // mqtt 服务标题
5
- "title": "新设备",
6
- // mqtt 服务介绍
7
- "description": "",
8
- // 状态 0未启用,1启用
9
- "state": 1,
10
- // 订阅的主题
11
- "topic": ["face/+/response", "face/response", "qr/response", "online/response", "heartbeat/response"],
12
- // 主题回复
13
- "topic_receive": ["face/${clientid}/request", "face/request"],
14
- // 给客户端推送的主题
15
- "topic_push": "face/${clientid}/request",
16
- // 接收方式
17
- "qos": 1,
18
- // 推送方式
19
- "qos_push": 0,
20
- // 保持接收
21
- "retain": true,
22
- // 调用的脚本
23
- "func_file": "./index.js",
24
- // 客户端ID
25
- "clientid": "sn",
26
- // 消息ID
27
- "msgid": "cmd_id",
28
- // 请求方法
29
- "method": "cmd",
30
- // 参数
31
- "params": "body",
32
- // 结果
33
- "result": "reply",
34
- // 回复方法
35
- "method_receive": "${method}"
36
- }
@@ -1,41 +0,0 @@
1
- {
2
- // 路由路径
3
- "path": "/api/test",
4
- // 名称, 用于动态增删改API配置
5
- "name": "demo_test",
6
- // 标题, 用于开发文档显示
7
- "title": "示例接口",
8
- // 描述, 用于介绍该路由的作用
9
- "description": "描述接口使用方法",
10
- // 函数文件, 用于驱动脚本, 实现业务
11
- "func_file": "./index.js",
12
- // 请求方法, 选填 GET, POST, ALL。 ALL指同时支持GET/POST
13
- "method": "ALL",
14
- // 开放域, 如果域未开放, 则只有特定的协议头才能访问该API, 同时API文档不接见
15
- "scope": true,
16
- // 缓存时长, 单位: 分钟。使用缓存后, 二次访问API直接从缓存读取, 不重复执行业务脚本
17
- "cache": 0,
18
- // 是否启用
19
- "state": 1,
20
- // 是否客户端缓存, 使用客户端则不再访问服务器, 直接从浏览器中拿; 使用服务端缓存则会访问服务器
21
- "client_cache": false,
22
- // SQL配置路径, 用于将请求参数拼接成SQL, 实现比较复杂的查询
23
- "sql_path": "./sql.json",
24
- // 参数配置路径, 用于校验API请求参数是否正确, 同时显示在API文档中
25
- "param_path": "./param.json",
26
- /* 授权协议 */
27
- "oauth": {
28
- // 是否需要登录, true表示需要登录才能访问该接口
29
- "signIn": false,
30
- // 会员权限级别, 如果小于该值, 则无法访问, 0为不限制
31
- "vip": 0,
32
- // 管理员权限级别, 如果小于该值, 则无法访问, 0为不限制
33
- "gm": 0,
34
- // 商户/第三方权限级别, 如果小于该值, 则无法访问, 0为不限制
35
- "mc": 0,
36
- // 用户组, 允许访问该接口的普通用户群体, 传ID数组,例如: [1,5]
37
- "user_group": [],
38
- // 管理组, 允许访问该接口的管理员群体, 传ID数组,例如: [1,5]
39
- "user_admin": []
40
- }
41
- }