Init
This commit is contained in:
5
.gitignore
vendored
Normal file
5
.gitignore
vendored
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
.git
|
||||||
|
node_modules
|
||||||
|
build
|
||||||
|
*.tgz
|
||||||
|
.DS_Store
|
||||||
21
LICENSE
Normal file
21
LICENSE
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
MIT License
|
||||||
|
|
||||||
|
Copyright (c) 2021-2024 bropat <patrick.broetto@gmail.com>
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
||||||
927
README.md
927
README.md
@ -0,0 +1,927 @@
|
|||||||
|
# eufy-security-client
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
[](https://www.npmjs.com/package/eufy-security-client)
|
||||||
|
[](https://www.npmjs.com/package/eufy-security-client)
|
||||||
|
[](https://www.npmjs.com/package/eufy-security-client)
|
||||||
|
[](https://www.npmjs.com/package/eufy-security-client)
|
||||||
|
[](https://libraries.io/npm/eufy-security-client)
|
||||||
|
[](https://snyk.io/test/github/bropat/eufy-security-client)
|
||||||
|
|
||||||
|
[](https://nodei.co/npm/eufy-security-client/)
|
||||||
|
|
||||||
|
Join us on Discord:
|
||||||
|
|
||||||
|
<a target="_blank" href="https://discord.gg/5wjQ2asb64"><img src="https://dcbadge.limes.pink/api/server/5wjQ2asb64" alt="" /></a>
|
||||||
|
|
||||||
|
The development of this shared library was inspired by the work of the following people:
|
||||||
|
|
||||||
|
* FuzzyMistborn (<https://github.com/FuzzyMistborn/python-eufy-security>)
|
||||||
|
* keshavdv (<https://github.com/keshavdv/python-eufy-security>)
|
||||||
|
* JanLoebel (<https://github.com/JanLoebel/eufy-node-client>)
|
||||||
|
|
||||||
|
Credits go to them as well.
|
||||||
|
|
||||||
|
If you appreciate my work and progress and want to support me, you can do it here:
|
||||||
|
|
||||||
|
[](https://ko-fi.com/E1E332Q6Z)
|
||||||
|
[](https://www.paypal.me/pbroetto)
|
||||||
|
|
||||||
|
**This project is not affiliated with Anker and Eufy (Eufy Security). It is a personal project that is maintained in spare time.**
|
||||||
|
|
||||||
|
## Description
|
||||||
|
|
||||||
|
This shared library allows to control [Eufy security devices](https://us.eufylife.com/collections/security) by connecting to the Eufy cloud servers and local/remote stations over p2p.
|
||||||
|
|
||||||
|
You need to provide your Cloud login credentials.
|
||||||
|
|
||||||
|
One client instance will show all devices from one Eufy Cloud account and allows to control them.
|
||||||
|
|
||||||
|
## Features
|
||||||
|
|
||||||
|
* Connects to Eufy cloud (supports 2fa)
|
||||||
|
* Connects to station/devices using p2p communication (supported: local and remote connectivity)
|
||||||
|
* Supports receiving push notification (unified push messages interface)
|
||||||
|
* Basic P2P implementation that supports also commands not already implemented
|
||||||
|
* Get info and parameters from stations/devices over https and/or p2p
|
||||||
|
* P2P functionality already implemented:
|
||||||
|
* Station:
|
||||||
|
* Change guard mode
|
||||||
|
* Reboot station
|
||||||
|
* Devices:
|
||||||
|
* Start livestream (local/remote p2p or rtmp over cloud)
|
||||||
|
* Stop livestream (local/remote p2p or rtmp over cloud)
|
||||||
|
* Enable/disable device
|
||||||
|
* Enable/disable auto night vision (only camera products)
|
||||||
|
* Enable/disable led (only camera 2 products, indoor cameras, floodlight camera, solo cameras and doorbells)
|
||||||
|
* Enable/disable anti-theft detection (only camera 2 products)
|
||||||
|
* Enable/disable motion detection
|
||||||
|
* Enable/disable pet detection (only indoor cameras)
|
||||||
|
* Enable/disable sound detection (only indoor cameras)
|
||||||
|
* Enable/disable RTSP stream (only camera2 products, indoor cameras and solo cameras)
|
||||||
|
* Change video watermark setting (only camera products)
|
||||||
|
* Start/cancel download video
|
||||||
|
* Quick response (only doorbells)
|
||||||
|
* Lock/unlock (only smart lock products)
|
||||||
|
* And many more, check it out...
|
||||||
|
|
||||||
|
## Documentation
|
||||||
|
|
||||||
|
Look [here](https://bropat.github.io/eufy-security-client/).
|
||||||
|
|
||||||
|
*As an example, you can look at the following projects: [ioBroker.eufy-security](https://github.com/bropat/ioBroker.eufy-security), [eufy-security-ws](https://github.com/bropat/eufy-security-ws), [eufy_security](https://github.com/fuatakgun/eufy_security)*
|
||||||
|
|
||||||
|
## Quick Start
|
||||||
|
|
||||||
|
Install via npm:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
npm install eufy-security-client
|
||||||
|
```
|
||||||
|
|
||||||
|
Then import and use in TypeScript:
|
||||||
|
|
||||||
|
```typescript
|
||||||
|
import { EufySecurity } from "eufy-security-client";
|
||||||
|
// ...existing code...
|
||||||
|
const eufyClient = new EufySecurity();
|
||||||
|
// ...existing code...
|
||||||
|
```
|
||||||
|
|
||||||
|
## Known working devices
|
||||||
|
|
||||||
|
For a list of supported devices, please see [here](https://bropat.github.io/eufy-security-client/#/supported_devices).
|
||||||
|
|
||||||
|
If more devices work (or also not) please report them by opening a GitHub issue.
|
||||||
|
|
||||||
|
## How to report issues and feature requests
|
||||||
|
|
||||||
|
Please use GitHub issues for this.
|
||||||
|
|
||||||
|
## Deployment
|
||||||
|
|
||||||
|
Instructions aimed at maintainers for deploying a new version: [Deployment](docs/deployment.md)
|
||||||
|
|
||||||
|
## Changelog
|
||||||
|
|
||||||
|
### 3.2.0 (2025-04-02)
|
||||||
|
|
||||||
|
* (martijnpoppen) FIX: Indoor Cam P&T sw update 2.3.1.2 on/off #604
|
||||||
|
* (SmolSoftBoi) Add error handling for MQTT proto file loading and improve logging #584
|
||||||
|
* (ChayoteJarocho) Add missing entry for Wall Cam 81A0 battery #570
|
||||||
|
* (jarodwilson) NEW: add SoloCam E30 (T8171) & FloodLight E30 (T8426) #583
|
||||||
|
* (martijnpoppen) FIX: enableEmbeddedPKCS1Support #595
|
||||||
|
* (NicolaiVdS & martijnpoppen) NEW: Battery doorbell C30 & C31 #600
|
||||||
|
* (martijnpoppen) NEW: add support for Indoor Cam C210 (T8419) & C220 (T8W11C) #596
|
||||||
|
* (martijnpoppen) NEW: add support for Eufycam S3 Pro - T8162 #594
|
||||||
|
* (martijnpoppen) NEW: Add Device Alarm to multiple camera #602
|
||||||
|
|
||||||
|
### 3.1.1 (2024-09-28)
|
||||||
|
|
||||||
|
* (bropat) Added RTSP support for Indoor Cam S350 (T8416)
|
||||||
|
* (bropat) Fixed draining issues for some battery powered devices (instead of #544)
|
||||||
|
* (bropat) Fixed standalone support for Indoor Cam S350 (T8416; #550)
|
||||||
|
* (bropat) Fixed issue with encryption type level 2
|
||||||
|
* (bropat) Fixed issue #502 (untested)
|
||||||
|
* (bropat) Fixed issue #539
|
||||||
|
* (bropat) Fixed issue #547
|
||||||
|
* (PhilippEngler) FIX: hasCommand for DevicePresetPosition, DeviceSavePresetPosition and DeviceDeletePresetPosition (#551)
|
||||||
|
* (PhilippEngler) added preset commands T8170 (#552)
|
||||||
|
|
||||||
|
### 3.1.0 (2024-08-27)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Change** Requires node version >= 20.0.0
|
||||||
|
* (martijnpoppen) NEW: add deviceConfig with simultaneousDetections option (#494)
|
||||||
|
* (PhilippEngler) added StationTimeZoneProperty (#472)
|
||||||
|
* (martijnpoppen) FIX: HB3 Doorbell Known Face detection not coming trough and Doorbell Ringing (#495)
|
||||||
|
* (bropat/lenoxys) Added ability to disable automatic cloud polling (#533)
|
||||||
|
* (bropat/PhilippEngler) Added ability to choose listening port of p2p station communication (#473)
|
||||||
|
* (bropat) Added vehicleDetected property to Floodlight Cam E340 (T8425)
|
||||||
|
* (bropat) Implemented runaway limit during parsing of p2p message data (infinite loop detection)
|
||||||
|
* (bropat) Added new EufySecurity options enableEmbeddedPKCS1Support (possible workaround for issue #487)
|
||||||
|
* (bropat) Added more logging about the initiation of P2P connections
|
||||||
|
* (bropat) Added more authentication log for info level
|
||||||
|
* (bropat) Improved livestream handling
|
||||||
|
* (PhilippEngler) update T8416 support (#535)
|
||||||
|
* (PhilippEngler) update T8170 support (#536)
|
||||||
|
* (bassrock) fix(bool): convert numeric to boolean (#523)
|
||||||
|
* (bropat) Fixed issue #482
|
||||||
|
* (bropat) Fixed an unhandled case that led to a infinite loop when parsing p2p messages
|
||||||
|
* (bropat) Fixed possible incorrect initiation of a P2P reconnection
|
||||||
|
* (bropat) Fixed some more property parsing
|
||||||
|
* (bropat) Possible fix for some locks missing some metadata
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 3.0.0 (2024-03-03)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Change** New modular logging implementation
|
||||||
|
* (bropat) Added support for Video Smart Lock S330 (T8530; #220)
|
||||||
|
* (bropat) Added support for Smart Lock C210 (T8502; #291)
|
||||||
|
* (bropat) Added support for Smart Lock C220 (T8506; #377 #356)
|
||||||
|
* (bropat) Added support for Smart Lock S230 (T8510P; #458)
|
||||||
|
* (bropat) Added support for Smart Lock S231 (T8520P; untested)
|
||||||
|
* (bropat) Added support for Retrofit Smart Lock E110 (T8503; #208)
|
||||||
|
* (bropat) Added support for Retrofit Smart Lock E130 (T8504; untested)
|
||||||
|
* (bropat) Added support for Smart Drop S300 (T8790; #261 #364)
|
||||||
|
* (bropat/martijnpoppen) Added support for Video Doorbell E340 (T8214; #406)
|
||||||
|
* (martijnpoppen) Added support for MiniBase Chime (T8023)
|
||||||
|
* (bropat/martijnpoppen) Added support for eufyCam E330 (Professional; T8600; #408)
|
||||||
|
* (bropat/martijnpoppen) Added support for Solar Wall Light Cam S120 (T84A0; #409)
|
||||||
|
* (bropat/martijnpoppen) Added support for SoloCam S340 (T8170; #410)
|
||||||
|
* (bropat) Added support for Indoor Cam S350 (T8416; #398)
|
||||||
|
* (bropat) Added support for Floodlight Cam E340 (T8425; #388)
|
||||||
|
* (bropat) Added support for SoloCam C210 (T8B00; #369)
|
||||||
|
* (bropat) Outdated, no longer functioning cloud livestream has been removed
|
||||||
|
* (bropat) Improved cloud device lookup
|
||||||
|
* (bropat) Implemented new image gathering from p2p initiated by push notifications
|
||||||
|
* (bropat) Implemented new p2p parameter format
|
||||||
|
* (bropat) Implemented calibrate command for Floodlight T8423 (#280)
|
||||||
|
* (martijnpoppen) OPT: persistentData via config instead of JSON file (#416)
|
||||||
|
* (PhilippEngler) changed description of state of DualCamWatchViewMode (#402)
|
||||||
|
* (PhilippEngler) Added support for storage info on HomeBase 3 (#405)
|
||||||
|
* (bropat) Added default values for some properties
|
||||||
|
* (bropat) Lowered p2p keepalive interval for battery saving devices
|
||||||
|
* (bropat) Added name of the person who locked/unlocked the lock
|
||||||
|
* (bropat) Added origin who locked/unlocked the lock
|
||||||
|
* (bropat) Changed to simultaneous triggering of different detection types by receiving of a single type of push notification
|
||||||
|
* (PhilippEngler) Updated device types (#478)
|
||||||
|
* (PhilippEngler) Add DeviceNotificationIntervalTimeProperty to indoor cams (#471)
|
||||||
|
* (PhilippEngler) Added storage info fpr S100 (#412)
|
||||||
|
* (martijnpoppen) FIX: vehicle detection S340 (#475)
|
||||||
|
* (PhilippEngler) Make StationStorageInfoProperties readonly (#474)
|
||||||
|
* (PhilippEngler) Solve TypeError in handleMsg (#469)
|
||||||
|
* (PhilippEngler) Fixed description of state of DualCamWatchViewMode (#402)
|
||||||
|
* (martijnpoppen) FIX: Eufy e330 remove battery (#445)
|
||||||
|
* (bropat) Fixed issue #380
|
||||||
|
* (bropat) Fixed issue #323
|
||||||
|
* (bropat) Fixed issue #452
|
||||||
|
* (bropat) Fixed decode of parameters
|
||||||
|
* (bropat) Fixed: not all types of motion detection can be deactivated at the same time (fallback to last value)
|
||||||
|
* (bropat) Fixed issue that caused long running p2p livestreams to be interrupted (#431)
|
||||||
|
* (bropat/PhilippEngler) Fixed possible double api connect event (#439)
|
||||||
|
* (bropat) Fixed possible issue with loading persistent data for cloud api
|
||||||
|
* (bropat) Fixed api internal session invalidation
|
||||||
|
* (bropat) Fixed update processing and persistent data consistency
|
||||||
|
* (bropat) Fixed persistent data saving
|
||||||
|
* (bropat) Fixed push notification in connection with HomeBase 3
|
||||||
|
|
||||||
|
### 2.9.1 (2023-11-04)
|
||||||
|
|
||||||
|
* (bropat) Fixed data decryption for p2p command responses
|
||||||
|
|
||||||
|
### 2.9.0 (2023-11-04)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Change** Requires node version >= 18.0.0
|
||||||
|
* (bropat) Added support for SmartTrack Link (T87B0; #385) and SmartTrack Card (T87B2; untested)
|
||||||
|
* (bropat/martijnpoppen) NEW: add support for S220 (T8134; #353)
|
||||||
|
* (bropat) Implemented data decryption for p2p command responses
|
||||||
|
* (bropat) Migrated API getCiphers method to v2 endpoint
|
||||||
|
* (bropat) Migrated API getInvites method to v2 endpoint
|
||||||
|
* (bropat) Migrated to Buffer.subarray from deprecated Buffer.slice method
|
||||||
|
* (bropat) Migrated to new sdcard info gathering over p2p (#373)
|
||||||
|
* (bropat) Fixed parsing of push notification for sensor open status (#372)
|
||||||
|
* (bropat) Fixed API getHouseInviteList method (removed encryption)
|
||||||
|
* (bropat) Fixed device type for lock T8506
|
||||||
|
* (PhilippEngler) Fixed StatusLed property for doorbell dual (#374)
|
||||||
|
* (bropat) Updated docs with new device names
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 2.8.1 (2023-08-31)
|
||||||
|
|
||||||
|
* (bropat) Automatic detection of supported P2P encryption (none, type1, type2)
|
||||||
|
* (bropat) Fixed regression introduced with activating p2p encryption for all devices (some older devices do not support it!)
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 2.8.0 (2023-08-20)
|
||||||
|
|
||||||
|
* (bropat) Implemented p2p data encryption for all supported commands
|
||||||
|
* (bropat) Improved updating of properties taking into account the priority/quality of the value source (http, p2p, push, mqtt)
|
||||||
|
* (bropat) API request throttling optimised
|
||||||
|
* (bropat) Fixed updating of the image property
|
||||||
|
|
||||||
|
### 2.7.1 (2023-08-08)
|
||||||
|
|
||||||
|
* (bropat) Fixed regression introduced by commit 7471fbf (Fixed possible MaxListenersExceededWarning)
|
||||||
|
* (bropat) Fixed issue not loading p2p properties over p2p connection for stations (HB2 and HB3)
|
||||||
|
|
||||||
|
### 2.7.0 (2023-08-01)
|
||||||
|
|
||||||
|
* (bropat) Added support for Wired Wall Light Cam S100 (T84A1; #318)
|
||||||
|
* (bropat) Added support for Garage-Control Cam (T8452; #219)
|
||||||
|
* (bropat) Implemented entry sensor status update over p2p connection
|
||||||
|
* (bropat) Improved cloud device lookup
|
||||||
|
* (bropat) Improved error handling
|
||||||
|
* (bropat/witold-gren) Added missing station command support for 4G LTE Starlight (T8151; #333)
|
||||||
|
* (bropat/witold-gren) Added missing push notification support for 4G LTE Starlight (T8151; #333)
|
||||||
|
* (bropat/witold-gren) Fixed issue handling push notification alarm events (#333)
|
||||||
|
* (bropat) Fixed image property not updating correctly
|
||||||
|
* (bropat) Fixed issue of executing the download image command only if supported
|
||||||
|
* (PhilippEngler) fix DeviceChargingStatus for eufyCam3 (#330)
|
||||||
|
* (PhilippEngler) handle incomplete JSON for parameter (#347)
|
||||||
|
* (bropat) Initiate p2p connection for supported devices only
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 2.6.2 (2023-05-16)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue waiting for device/station loading event in some cases
|
||||||
|
* (martijnpoppen) FIX: doorbell push not parsed when connected to HB3 #325
|
||||||
|
|
||||||
|
### 2.6.1 (2023-05-13)
|
||||||
|
|
||||||
|
* (bropat) Fixed an issue that caused the event "livestream started" to be emit twice
|
||||||
|
* (bropat) Added some missing properties (package detection) for doorbell solo (T8203)
|
||||||
|
* (bropat) Migrated from dependency protobuf-typescript to protobufjs
|
||||||
|
|
||||||
|
### 2.6.0 (2023-05-12)
|
||||||
|
|
||||||
|
* (bropat) Implemented access to local event history (database on station)
|
||||||
|
* (bropat) Implemented download of first picture from local database for supported devices
|
||||||
|
* (martijnpoppen) FIX: HB3 notifications - (exclude sensors) #324
|
||||||
|
|
||||||
|
### 2.5.1 (2023-05-07)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue in downloading `cover_path` picture for supported devices
|
||||||
|
|
||||||
|
### 2.5.0 (2023-05-07)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Change** `picture_url` property is now hidden and was replaced by `picture` property for supported devices
|
||||||
|
* (bropat) Implemented new push notification picture gathering and decryption
|
||||||
|
* (bropat) Fixed sdcard info gathering for devices without sdcard inserted
|
||||||
|
|
||||||
|
### 2.4.4 (2023-04-21)
|
||||||
|
|
||||||
|
* (bropat) Implemented feature request #313
|
||||||
|
* (bropat) Fixed issue #316
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 2.4.3 (2023-04-11)
|
||||||
|
|
||||||
|
* (martijnpoppen) FIX: HB3 connected sensors not reporting (#314)
|
||||||
|
* (PhilippEngler) Fix problem when the P2PDID number is starting with zeros
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 2.4.2 (2023-02-23)
|
||||||
|
|
||||||
|
* (bropat) Improved local discovery of stations over p2p
|
||||||
|
* (bropat) Fixed issue in API communication when no stations and devices are found
|
||||||
|
|
||||||
|
### 2.4.1 (2023-02-19)
|
||||||
|
|
||||||
|
* (bropat) Added support for configuring a suggested IP address for a station
|
||||||
|
* (bropat) Fixed json parse issue with null-terminated strings
|
||||||
|
* (bropat) Fixed p2p keepalive issue
|
||||||
|
* (bropat/martijnpoppen) Fixed Invalid Property personDetected error for some floodlight cams
|
||||||
|
* (PhilippEngler) Finished implementation of getStorageInfo
|
||||||
|
* (bropat) Removed dependency mediainfo.js
|
||||||
|
|
||||||
|
### 2.4.0 (2022-12-24)
|
||||||
|
|
||||||
|
* (bropat) Implemented new encrypted cloud API communication (v2)
|
||||||
|
* (bropat) Added support for 4G LTE Starlight camera (T8150; #209; #231)
|
||||||
|
* (bropat) Implemented client-side termination of the stream (live/download; #258)
|
||||||
|
* (bropat) Fixed issue #271
|
||||||
|
* (bropat) Fixed issue #283
|
||||||
|
* (bropat) Fixed issue #287
|
||||||
|
* (martijnpoppen) FIX: webAPi stream request (#275)
|
||||||
|
* (martijnpoppen) FIX: support V2 for getPassportProfile (V1 deprecated; #282)
|
||||||
|
* (martijnpoppen) FIX: always encrypt login with server key. (#285)
|
||||||
|
* (PhilippEngler) update _getEvents for v2 (#286)
|
||||||
|
* (bropat) Fixed wrong variable names in pull request (#286)
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 2.3.0 (2022-11-26)
|
||||||
|
|
||||||
|
* (bropat) Added support for Wired Doorbell (T8200X)
|
||||||
|
* (bropat) Added new property `snoozeStartTime`, `snoozeHomebase`, `snoozeChime` and `snoozeMotion` to supported devices
|
||||||
|
* (bropat) Added debug information for analysed audio and video codecs at start of livestream
|
||||||
|
* (bropat/martijnpoppen) Added new command `stationChime` for supported stations
|
||||||
|
* (bropat) Implemented fallback for configured empty string for setting `trustedDeviceName`
|
||||||
|
* (bropat) Implemented missing Homebase 3 notification events
|
||||||
|
* (bropat) Fixed unknown video codec issue
|
||||||
|
* (bropat) Fixed issue #240
|
||||||
|
* (smitty078) Fixed issue #251
|
||||||
|
* (thieren) Fixed issue #256 (#255)
|
||||||
|
* (tyware) Fixed issue #257
|
||||||
|
* (bropat) Fixed issue #258
|
||||||
|
* (PhilippEngler) Change DeviceChargingStatusProperty value for eufyCam 3c (#254)
|
||||||
|
* (PhilippEngler) Fixed doubled property labels (#253)
|
||||||
|
* (martijnpoppen) FIX: keypad wifiSignalLevel property error (#245)
|
||||||
|
* (martijnpoppen) FIX: issue when params are not available for rawDevice/rawStation (#246)
|
||||||
|
|
||||||
|
### 2.2.3 (2022-11-12)
|
||||||
|
|
||||||
|
* (bropat) Added Station alarm properties
|
||||||
|
* (bropat) Added `connection error` event to HTTPApi and EufySecurity
|
||||||
|
* (bropat) Changed default value of `trustedDeviceName`
|
||||||
|
* (martijnpoppen) NEW: HB3 Vehicle Detection (#241)
|
||||||
|
|
||||||
|
### 2.2.2 (2022-11-06)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue identifying alarm delay
|
||||||
|
|
||||||
|
### 2.2.1 (2022-11-05)
|
||||||
|
|
||||||
|
* (bropat) Added support for Floodlight Cam (T8420X)
|
||||||
|
* (Palmke) Implemented Homebase 3 familiar faces (#237)
|
||||||
|
* (bropat) Fixed regression in Station.startDownload
|
||||||
|
* (Palmke) Fixed issue #236
|
||||||
|
* (bropat) Fixed issue #233
|
||||||
|
* (bropat) Small bugfixes
|
||||||
|
|
||||||
|
### 2.2.0 (2022-11-01)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Change** Renamed all lock settings parameters according to standard
|
||||||
|
* (bropat) **Breaking Change** Station class initialization is now async
|
||||||
|
* (bropat) Renewed p2p device address discovery (now also includes local discovery via broadcast; cloud discovery optimised)
|
||||||
|
* (bropat) Added support for Doorbell Dual notification types (package delivered, package taken, package stranded, someone loitering, radar motion detected)
|
||||||
|
* (bropat) Added support for eufyCam 3C (#233)
|
||||||
|
* (bropat) Added support for eufyCam 3 (#228)
|
||||||
|
* (bropat) Added support for Homebase 3 (#228)
|
||||||
|
* (bropat) Added support to programmatically add access to lock (#204)
|
||||||
|
* (thieren) Added station event for connection timeout (#202)
|
||||||
|
* (bropat) Added Smart Safe support (tested only T7400; #182)
|
||||||
|
* (bropat) Added snooze command for supported devices (#173, #176)
|
||||||
|
* (bropat) Added support for video type store to NAS for indoor cameras (#147)
|
||||||
|
* (bropat) Switched API login to new login_sec endpoint
|
||||||
|
* (bropat) Incremented p2p disconnect timeout for energy saving device to 30 seconds
|
||||||
|
* (bropat) Implemented new resend of not acknowledged p2p commands
|
||||||
|
* (bropat) Fixed issue with energy saving measures interrupting running streams
|
||||||
|
* (bropat) Better error handling for not supported p2p commands
|
||||||
|
* (bropat) Fixed signalling of event `station command result`
|
||||||
|
* (bropat) Fixed local device discovery exception (udp broadcast)
|
||||||
|
* (bropat) Fixed checking of valid property values (function validValues)
|
||||||
|
* (bropat) Fixed regression in parsing lock push notifications
|
||||||
|
* (bropat) Fixed updating of device properties on p2p command result event for some devices
|
||||||
|
* (bropat) Fixed parsing of raw values of property `motionDetectionSensitivity`
|
||||||
|
* (bropat) Fixed MQTT certification verification for some eufy servers (disabled certification verrification, since some server have expired certs)
|
||||||
|
* (bropat) Fixed emitting of event "locked" for lock devices
|
||||||
|
* (bropat) Fixed issue #227
|
||||||
|
* (bropat) Fixed issue #215
|
||||||
|
* (bropat) Fixed issue #212
|
||||||
|
* (bropat) Fixed issue #207
|
||||||
|
* (bropat) Fixed issue #201
|
||||||
|
* (bropat) Fixed issue #196
|
||||||
|
* (martijnpoppen) FIX: set DevicePictureUrl for sound and crying (#234)
|
||||||
|
* (bropat) Small bugfixes and optimizations
|
||||||
|
* (bropat) Updated docs - Added partial supported device HomeBase 3 (T8030, S380)
|
||||||
|
* (bropat) Updated docs - Added supported devices eufyCam 3 (T8160, S330), eufyCam 3C (T8161, S300)
|
||||||
|
* (bropat) Updated docs - Added supported devices Smart Safe S10 (T7400), Smart Safe S12 (T7401)
|
||||||
|
* (bropat) Updated docs - Added supported devices SoloCam L20 (T8122), SoloCam L40 (T8123), SoloCam S40 (T8124), SoloCam E20 (T8130)
|
||||||
|
* (bropat) Changed default persistent directory path for saving persistent data
|
||||||
|
|
||||||
|
### 2.1.2 (2022-07-30)
|
||||||
|
|
||||||
|
* (Palmke) Dual Doorbell family detection (#177)
|
||||||
|
* (Palmke) Fixed issue #187
|
||||||
|
* (bropat) Fixed issue #186
|
||||||
|
|
||||||
|
### 2.1.1 (2022-07-16)
|
||||||
|
|
||||||
|
* (Palmke) Add alarm arm delay event (#180)
|
||||||
|
* (thieren) Fix: stream command for T8420 (#171)
|
||||||
|
* (Palmke) Don't send the alarm armed p2p events as alarm events (#169)
|
||||||
|
* (bropat) Fixed issue #167
|
||||||
|
* (bropat) Fixed issue #161
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 2.1.0 (2022-06-12)
|
||||||
|
|
||||||
|
* (bropat) Added toggle for Spotlight for Outdoor Cam Pro (T8441; #123)
|
||||||
|
* (bropat & thieren) Added talkback commands for supported devices (#38, #153; thanks @thieren)
|
||||||
|
* (fabianluque) Added missing RTSP properties for Floodlight T8423 (#146)
|
||||||
|
* (Palmke) Add alarm delay event (#88, #155)
|
||||||
|
* (Palmke) P&T T8410: Set motion zone and image mirror (#156)
|
||||||
|
* (Palmke) Send an event when the alarm is armed and alarm events from p2p (#105, #157)
|
||||||
|
* (bropat) Implemented simple request throttling for Eufy Cloud
|
||||||
|
* (bropat) Fixed push notification token renewal
|
||||||
|
* (bropat) Fixed issue #161
|
||||||
|
|
||||||
|
### 2.0.1 (2022-05-03)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Change** Fixed regression in device data loading
|
||||||
|
* (bropat) Target set back to ES2019
|
||||||
|
|
||||||
|
### 2.0.0 (2022-04-30)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Change** Requires node version >= 14.17
|
||||||
|
* (bropat) **Breaking Change** HTTPApi class, EufySecurity class and Device classes instantiation changed
|
||||||
|
* (bropat) **Breaking Change** Timestamp for device and station properties has been removed
|
||||||
|
* (bropat) Added support for Battery Doorbell Dual (T8213; #126)
|
||||||
|
* (bropat) Added support for Video Doorbell Dual (T8203; #141)
|
||||||
|
* (bropat) Added support for IndoorCam Mini (T8414; #143)
|
||||||
|
* (bropat) Added continuos recording setting for some supported cameras
|
||||||
|
* (bropat) Added continuos recording type setting for some supported cameras
|
||||||
|
* (bropat) Added default angle setting for IndoorCam Mini (T8414)
|
||||||
|
* (bropat) Added default angle idle time setting for IndoorCam Mini (T8414)
|
||||||
|
* (bropat) Added notification interval time setting for some supported cameras
|
||||||
|
* (bropat) Added calibrate command for some supported cameras
|
||||||
|
* (bropat) Added set default angle command for IndoorCam Mini (T8414
|
||||||
|
* (bropat) Added set privacy angle command for IndoorCam Mini (T8414)
|
||||||
|
* (bropat) Removed PREFER_LOCAL P2P connectivity mode. Default mode is now QUICKEST.
|
||||||
|
* (bropat) Added new charging status "solar charging" (value: 4; issue #127)
|
||||||
|
* (bropat) Fixed Eufy cloud authentication token renewal
|
||||||
|
* (bropat) Fixed some Eufy cloud authentication issues
|
||||||
|
* (bropat) Fixed authentication issues when changing country setting
|
||||||
|
* (bropat) Fixed possible wrong battery values on some devices
|
||||||
|
* (bropat) Fixed issue if device doesn't support P2P communication
|
||||||
|
* (bropat) Fixed issue #136
|
||||||
|
* (bropat) Fixed issue #122
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 1.6.6 (2022-02-12)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue where no devices/stations are found (#116)
|
||||||
|
|
||||||
|
### 1.6.5 (2022-02-08)
|
||||||
|
|
||||||
|
* (bropat) Fixed regression in authentication flow introduced when fixing issue #116
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 1.6.4 (2022-02-07)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue #116 (choosing the correct country as in the Eufy App is esentially)
|
||||||
|
|
||||||
|
**Note:** Selecting the correct country is essential for the devices to be found (should match the setting in the Eufy app).
|
||||||
|
|
||||||
|
### 1.6.3 (2022-02-06)
|
||||||
|
|
||||||
|
* (bropat) Initialize MQTT connection only if supported devices are found
|
||||||
|
|
||||||
|
### 1.6.2 (2022-02-05)
|
||||||
|
|
||||||
|
* (bropat) Fixed MQTT connection issue (error: 5)
|
||||||
|
|
||||||
|
### 1.6.1 (2022-02-05)
|
||||||
|
|
||||||
|
* (bropat) Fixed small issue on driver upgrade of persistence data (has no impact; error entry in log on first startup)
|
||||||
|
|
||||||
|
### 1.6.0 (2022-02-05)
|
||||||
|
|
||||||
|
* (bropat) Supports new [Home Management](https://communitysecurity.eufylife.com/t/tips-for-eufy-security-app-v4-0/2420747) feature of Eufy Security 4.0
|
||||||
|
* (bropat) Added support for Smart Lock Touch & Wifi (T8520; #89)
|
||||||
|
* (bropat) Implemented Eufy MQTT notification subscription for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added auto lock setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added auto lock schedule setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added auto lock schedule start time setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added auto lock schedule end time setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added auto lock timer setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added notification setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added notification locked setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added notification unlocked setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added one touch locking setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added scramble passcode setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added sound setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added wrong try protection setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added wrong try attempts setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added wrong try lockdown time setting for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added lock/unlock command for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Added lock calibration command for Smart Lock Touch & Wifi (T8520)
|
||||||
|
* (bropat) Improved p2p communication with energy saving devices
|
||||||
|
* (bropat) Added new HTTPApi methods supporting Eufy Security 4.0
|
||||||
|
* (bropat) Some small improvements were made to the HTTPApi
|
||||||
|
* (bropat) Fixed issue #97
|
||||||
|
* (bropat) Fixed issue #102
|
||||||
|
* (bropat) Fixed issue #109
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 1.5.0 (2021-12-19)
|
||||||
|
|
||||||
|
* (bropat) Added support for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion detection range setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion detection range standard sensitivity setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion detection range advanced left sensitivity setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion detection range advanced middle sensitivity setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion detection range advanced right sensitivity setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion detection range test mode setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion tracking sensitivity setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion auto-cruise setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added motion out-of-view detection setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added light setting color temperature manual setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added light setting color temperature mamotion setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added light setting color temperature schedule setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added light setting motion activation mode setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added video nightvision image adjustment setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added video color nightvision setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added auto calibration setting for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added start/stop rtsp livestream command for floodlight cam 2 pro (T8423)
|
||||||
|
* (bropat) Added battery and wifi rssi properties to eufycam 1/E
|
||||||
|
* (bropat) Implemented another p2p-keepalive mechanism found in some floodlights (e.g. T8420)
|
||||||
|
* (bropat) Fixed support for floodlight (T8420) - tested with FW: 1.0.0.35 HW: 2.2
|
||||||
|
* (bropat) Fixed status led setting for floodlight (T8420)
|
||||||
|
* (bropat) Fixed motion detected setting for floodlight (T8420)
|
||||||
|
* (bropat) Fixed motion detected sensitivity setting for floodlight (T8420)
|
||||||
|
* (bropat) Fixed audio recording setting for floodlight (T8420)
|
||||||
|
* (bropat) Fixed enable/disable device for floodlight (T8420)
|
||||||
|
* (bropat) Fixed start livestream command for floodlight (T8420)
|
||||||
|
* (bropat) Fixed issue #79
|
||||||
|
* (bropat) Fixed issue #66
|
||||||
|
* (bropat) Fixed some other minor issues
|
||||||
|
* (bropat) Added docs (:construction:)
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 1.4.0 (2021-11-22)
|
||||||
|
|
||||||
|
* (bropat) Implemented captcha authentication mechanism (API v2)
|
||||||
|
* (bropat) Fixed issue #69
|
||||||
|
|
||||||
|
### 1.3.0 (2021-11-20)
|
||||||
|
|
||||||
|
* (bropat) Implemented new encrypted authentication mechanism (API v2)
|
||||||
|
* (bropat) Dropped old plaintext authentication mechanism (API v1)
|
||||||
|
* (bropat) Fixed issue #67
|
||||||
|
* (bropat) Exchanged axios with got for HTTP/2 support
|
||||||
|
|
||||||
|
**Note:** If you have 2FA enabled, you will need to authenticate again after this update.
|
||||||
|
|
||||||
|
### 1.2.4 (2021-11-17)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue #63
|
||||||
|
|
||||||
|
### 1.2.3 (2021-11-16)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue #64
|
||||||
|
* (bropat) Fixed issue #65
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 1.2.2 (2021-11-06)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue of wrong channel value on event rtsp livestream stopped
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 1.2.1 (2021-10-23)
|
||||||
|
|
||||||
|
* (bropat) Changed event detection for start/stop local RTSP streaming
|
||||||
|
* (bropat) Fixed regression introduced by fixing issue #51
|
||||||
|
* (bropat) Fixed new implementation that detects interrupted p2p streams
|
||||||
|
* (bropat) Fixed missing start/stop local RTSP streaming commands to hasCommand and getCommands
|
||||||
|
|
||||||
|
### 1.2.0 (2021-10-17)
|
||||||
|
|
||||||
|
* (bropat) Extended p2p implementation to better support solo cameras and other battery powered devices
|
||||||
|
* (bropat) Revised p2p implementation to send commands sequentially
|
||||||
|
* (bropat) Added support for Floodlight T8422
|
||||||
|
* (bropat) Added support for SoloCam E40 (T8131)
|
||||||
|
* (bropat) Added experimental feature for supported devices: start/stop local RTSP streaming
|
||||||
|
* (bropat) Added new properties for solo cameras: battery, batteryTemperature, wifiSignalLevel, state, chargingStatus, lastChargingDays, lastChargingRecordedEvents, lastChargingTotalEvents, batteryUsageLastWeek
|
||||||
|
* (bropat) Implemented interrupted p2p stream detection
|
||||||
|
* (bropat) Fixed issue #51
|
||||||
|
* (bropat) Fixed push notifications for solo cameras (motion and person detection)
|
||||||
|
* (bropat) Fixed "livestream stopped" if live stream is started for multiple devices of the same station (1 p2p session could start only 1 live stream at a time)
|
||||||
|
* (bropat) Fixed "download finished" if download is started for multiple devices of the same station (1 p2p session could start only 1 download at a time)
|
||||||
|
* (bropat) Fixed an issue where the P2P connection type PREFER_LOCAL did not attempt to connect if no local IP address was found
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 1.1.2 (2021-08-19)
|
||||||
|
|
||||||
|
* (bropat) Fixed push notification issue on new indoor outdoor camera device (thx to @lenoxys)
|
||||||
|
* (bropat) Fixed issue where device doesn't support p2p connection
|
||||||
|
|
||||||
|
### 1.1.1 (2021-08-13)
|
||||||
|
|
||||||
|
* (bropat) Fixed p2p video streaming for some devices (fallback mechanism implemented)
|
||||||
|
* (bropat) Fixed p2p audio codec detection
|
||||||
|
|
||||||
|
### 1.1.0 (2021-08-11)
|
||||||
|
|
||||||
|
* (bropat) Added brightness light setting for 2c/2c pro cameras, new solo cameras and new outdoor cameras
|
||||||
|
* (bropat) Added enable/disable light setting for 2c/2c pro cameras, new solo cameras and new outdoor cameras
|
||||||
|
* (bropat) Added trigger/reset alarm sound for indoor cameras, solo cameras and floodlight cameras
|
||||||
|
* (bropat) Added video streaming quality setting for 2c pro cameras
|
||||||
|
* (bropat) Added video recording quality setting for 2c pro cameras
|
||||||
|
* (bropat) Added trigger alarm sound for indoor cameras, solo cameras (incl. new) and floodlight cameras
|
||||||
|
* (bropat) Added reset alarm sound for indoor cameras, solo cameras (incl. new) and floodlight cameras
|
||||||
|
* (bropat) Added battery charging state for keypad devices
|
||||||
|
* (bropat) Added new property "batteryIsCharging" for keypad devices
|
||||||
|
* (bropat) Added property "wifiRssi" for keypad devices
|
||||||
|
* (bropat) Added new property "nightvision" for devices supporting the "light" nightvision mode
|
||||||
|
* (bropat) Added new properties "switchModeWithAccessCode", "autoEndAlarm" and "turnOffAlarmWithButton" for station with registered keypad
|
||||||
|
* (bropat) Added default values for some properties that, if not set first, were not listed in the cloud response
|
||||||
|
* (bropat) Fixed issue with guard mode setting where the "Off" state was not handled correctly (only supported with keypad) (#27)
|
||||||
|
* (bropat) Fixed issue in class EufySecurity if start cloud stream command fails
|
||||||
|
* (bropat) Fixed issue with "locked" event for locks
|
||||||
|
* (bropat) Fixed issue with nightvision setting for devices with light (b&w, light, off)
|
||||||
|
* (bropat) Fixed issue in station property value conversion for number or boolean types
|
||||||
|
* (bropat) Fixed issue where "motionDetection" property was incorrectly updated instead of "motionDetected" when a push notification arrived
|
||||||
|
* (lenoxys) Handle Lock Push Event for Lock / Unlock #36
|
||||||
|
|
||||||
|
### 1.0.0 (2021-08-07)
|
||||||
|
|
||||||
|
* (bropat) Added new method "getSensorHistory" to HTTPApi class for getting entry sensor history data
|
||||||
|
* (bropat) Added new events "station connect" and "station close" to EufySecurity class
|
||||||
|
* (bropat) Added new "chargingStatus", "wifiSignalLevel", "rtspStreamUrl", "chirpVolume", "chirpTone", "videoHdr", "videoDistortionCorrection" and "videoRingRecord" properties for supported devices
|
||||||
|
* (bropat) Added enable/disable led setting for camera 1 products
|
||||||
|
* (bropat) Added motion detection sensitivity setting for camera 1 products and wired doorbell
|
||||||
|
* (bropat) Added motion detection type setting for camera 1 products
|
||||||
|
* (bropat) Added motion audio recording setting for camera 1 products and wired doorbell
|
||||||
|
* (bropat) Added ringtone volume setting for wired doorbell
|
||||||
|
* (bropat) Added enable/disable indoor chime setting for wired doorbell
|
||||||
|
* (bropat) Added notification ring setting for wired doorbell
|
||||||
|
* (bropat) Added notification motion setting for wired doorbell
|
||||||
|
* (bropat) Added video streaming quality setting for wired doorbell
|
||||||
|
* (bropat) Added video recording quality setting for wired doorbell
|
||||||
|
* (bropat) Added video HDR setting for wired doorbell
|
||||||
|
* (bropat) Added video distortion correction setting for wired doorbell
|
||||||
|
* (bropat) Added video ring recording setting for wired doorbell
|
||||||
|
* (bropat) Added notification type setting for camera 1 products, solo cameras and wired doorbell
|
||||||
|
* (bropat) Added chirp volume setting for entry sensor
|
||||||
|
* (bropat) Added chirp tone setting for entry sensor
|
||||||
|
* (bropat) Implemented queuing of p2p commands in class P2PClientProtocol if connection to station isn't already present
|
||||||
|
* (bropat) Renamed some properties for typo issues
|
||||||
|
* (bropat) Renamed some properties to correct the use of camelcase
|
||||||
|
* (bropat) Fixed issue where data was not updated (cloud and p2p polling)
|
||||||
|
* (bropat) Fixed issue with resetting api_base when changing credentials
|
||||||
|
* (bropat) Fixed some issues with clearing timeouts in class P2PClientProtocol
|
||||||
|
* (bropat) Fixed issue in class P2PClientProtocol not detecting video codec for some devices (#)
|
||||||
|
* (bropat) Fixed event "rtsp url" returning the url value containing nulls "\0"
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 0.9.4 (2021-07-23)
|
||||||
|
|
||||||
|
* (bropat) Fixed regression on p2p connection timeout and reconnect tentatives
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 0.9.3 (2021-07-20)
|
||||||
|
|
||||||
|
* (bropat) Fixed p2p livestream video regression
|
||||||
|
* (bropat) Merged #22 - Add custom modes in alarm mode (thx to @piitaya)
|
||||||
|
|
||||||
|
### 0.9.1 (2021-07-17)
|
||||||
|
|
||||||
|
* (bropat) Exported some missing error classes and types
|
||||||
|
* (bropat) Checking valid direction values for panAndTilt command
|
||||||
|
|
||||||
|
### 0.9.0 (2021-07-16)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Change** Station/EufySecurity "guard mode" event changed to emit only the guard mode
|
||||||
|
* (bropat) Added Station/EufySecurity "current mode" event that emits only the current mode change
|
||||||
|
* (bropat) Added more Eufy Cloud error codes to "ResponseErrorCode"
|
||||||
|
* (bropat) Added more server push notification types to "ServerPushEvent"
|
||||||
|
* (bropat) Added pan an tilt functionality to supported indoor cameras
|
||||||
|
* (bropat) Added functionality to handle invitations on "HTTPApi"
|
||||||
|
* (bropat) Added error detection if stopping or starting stream that isn't running or already running
|
||||||
|
* (bropat) Added new setting "acceptInvitations" to "EufySecurity" to accept invitations automatically
|
||||||
|
* (bropat) Added floodlight camera light switch
|
||||||
|
* (bropat) Added motion detection sensitivity for indoor cameras, solo cameras, floodlight cameras, camera 2 products and battery doorbells
|
||||||
|
* (bropat) Added motion detection type for indoor cameras, solo cameras, floodlight cameras, camera 2 products and battery doorbells
|
||||||
|
* (bropat) Added motion tracking for indoor camera pan & tilt cameras
|
||||||
|
* (bropat) Added video stream quality setting for indoor cameras, solo cameras, floodlight cameras and battery doorbell
|
||||||
|
* (bropat) Added video recording quality setting for indoor cameras
|
||||||
|
* (bropat) Added WDR setting for battery doorbells
|
||||||
|
* (bropat) Added microphone mute setting for indoor cameras, solo cameras, floodlight cameras, camera 2 products and battery doorbells
|
||||||
|
* (bropat) Added audio recording setting for indoor cameras, solo cameras, floodlight cameras, camera 2 products and battery doorbells
|
||||||
|
* (bropat) Added enable/disable speaker setting for indoor cameras, solo cameras, floodlight cameras, camera 2 products
|
||||||
|
* (bropat) Added speaker volume setting for indoor cameras, solo cameras, floodlight cameras, camera 2 products and battery doorbells
|
||||||
|
* (bropat) Added power source setting for camera 2 products cameras, eufy cameras and eufy E cameras
|
||||||
|
* (bropat) Added power working mode setting for solo cameras, camera 2 products, battery doorbells, eufy cameras and eufy E cameras
|
||||||
|
* (bropat) Added power custom working mode recording clip length setting for solo cameras, floodlight cameras, camera 2 products, battery doorbells, eufy cameras and eufy E cameras
|
||||||
|
* (bropat) Added power custom working mode recording retrigger interval setting for solo cameras, floodlight cameras, camera 2 products, battery doorbells, eufy cameras and eufy E cameras
|
||||||
|
* (bropat) Added power custom working mode recording ends if motion stops setting for solo cameras, floodlight cameras, camera 2 products, battery doorbells, eufy cameras and eufy E cameras
|
||||||
|
* (bropat) Added video streaming quality setting for indoor cameras, solo cameras, floodlight cameras and battery doorbells
|
||||||
|
* (bropat) Added video recording quality setting for indoor 2k cameras
|
||||||
|
* (bropat) Added motion detection sensitivity setting for indoor cameras, floodlight cameras and camera 2 products
|
||||||
|
* (bropat) Added enable/disable motion tracking setting for indoor pan & tilt cameras
|
||||||
|
* (bropat) Added motion detection type setting for indoor cameras, solo cameras, floodlight cameras, camera 2 products and battery doorbells
|
||||||
|
* (bropat) Added enable/disable WDR setting for battery doorbells
|
||||||
|
* (bropat) Added ringtone volume setting for battery doorbells
|
||||||
|
* (bropat) Added enable/disable chime indoor setting for battery doorbells
|
||||||
|
* (bropat) Added enable/disable chime homebase setting for battery doorbells
|
||||||
|
* (bropat) Added chime homebase ringtone volume setting for battery doorbells
|
||||||
|
* (bropat) Added chime homebase ringtone type setting for battery doorbells
|
||||||
|
* (bropat) Added notification type setting for solo cameras, floodlight cameras, camera 2 products, battery doorbells, eufy cameras and eufy E cameras
|
||||||
|
* (bropat) Added enable/disable person notification setting for indoor cameras
|
||||||
|
* (bropat) Added enable/disable pet notification setting for indoor cameras
|
||||||
|
* (bropat) Added enable/disable all other motion notification setting for indoor cameras
|
||||||
|
* (bropat) Added enable/disable all sound notification setting for indoor cameras
|
||||||
|
* (bropat) Added enable/disable crying notification setting for indoor cameras
|
||||||
|
* (bropat) Added enable/disable motion notification setting for battery doorbells
|
||||||
|
* (bropat) Added enable/disable ring notification setting for battery doorbells
|
||||||
|
* (bropat) Added trigger alarm sound for camera 2 products
|
||||||
|
* (bropat) Added reset alarm sound for camera 2 products
|
||||||
|
* (bropat) Added trigger alarm sound for homebase 1+2
|
||||||
|
* (bropat) Added reset alarm sound for homebase 1+2
|
||||||
|
* (bropat) Added alarm tone setting for homebase 1+2
|
||||||
|
* (bropat) Added alarm volume setting for homebase 1+2
|
||||||
|
* (bropat) Added prompt volume setting for homebase 1+2
|
||||||
|
* (bropat) Added time format setting for homebase 1+2
|
||||||
|
* (bropat) Added enable/disable switch mode app notification setting for homebase 1+2
|
||||||
|
* (bropat) Added enable/disable switch mode geofence notification setting for homebase 1+2
|
||||||
|
* (bropat) Added enable/disable switch mode schedule notification setting for homebase 1+2
|
||||||
|
* (bropat) Added enable/disable switch mode keypad notification setting for homebase 1+2
|
||||||
|
* (bropat) Added enable/disable start alarm delay notification setting for homebase 1+2
|
||||||
|
* (bropat) Added new floodlight, solo and outdoor cameras (untested!)
|
||||||
|
* (bropat) Added alarm event for Station
|
||||||
|
* (bropat) Picture url attribute is now also updated via push notifications
|
||||||
|
* (bropat) Fixed issue where the "pollingIntervalMinutes" setting of "EufySecurity" was not respected
|
||||||
|
* (bropat) Fixed p2p livestream for floodlight camera
|
||||||
|
* (bropat) Fixed p2p enable/disable device for floodlight camera
|
||||||
|
* (bropat) Fixed p2p enable/disable autonightvision for floodlight camera
|
||||||
|
* (bropat) Fixed p2p download video
|
||||||
|
* (bropat) Fixed P2PClientProtocol "close" event that was emitted even if there was no connection and a reconnection was attempted
|
||||||
|
* (bropat) Fixed "guard mode" and "current mode" event not emittet in some conditions
|
||||||
|
* (bropat) Fixed possible race conditions processing unordered p2p packets
|
||||||
|
* (bropat) Optimized p2p lookup functionality
|
||||||
|
* (bropat) Other small bugfixes and code cleanup
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 0.8.3 (2021-06-01)
|
||||||
|
|
||||||
|
* (bropat) Fixed regression in p2p protocol
|
||||||
|
|
||||||
|
### 0.8.2 (2021-05-26)
|
||||||
|
|
||||||
|
* (bropat) Fixed issue [#2](https://github.com/bropat/eufy-security-client/issues/2)
|
||||||
|
* (bropat) Added new high level property "type" for devices/stations
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 0.8.1 (2021-05-14)
|
||||||
|
|
||||||
|
* (bropat) Fixed (raw) property value refresh for devices and stations
|
||||||
|
* (bropat) Fixed "enabled" property for standalone devices
|
||||||
|
* (bropat) Fixed "lanIpAddress" property for standalone devices
|
||||||
|
* (bropat) Fixed "macAddress" property for standalone devices
|
||||||
|
* (bropat) Added "station raw property changed" and "device raw property changed" event for high level class EufySecurity
|
||||||
|
|
||||||
|
### 0.8.0 (2021-05-12)
|
||||||
|
|
||||||
|
* (bropat) **Breaking Changes** (renamed emitter, renamed some functions etc.)
|
||||||
|
* (bropat) Added high level class EufySecurity
|
||||||
|
* (bropat) Added high level properties with metadata information
|
||||||
|
* (bropat) Better error handling
|
||||||
|
* (bropat) Fixed Guard Mode Emitter
|
||||||
|
* (bropat) Fixed push notification for indoor and floodlight cams
|
||||||
|
* (bropat) Cleanup code
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 0.7.2 (2021-04-10)
|
||||||
|
|
||||||
|
* (bropat) Added new HTTP API methods: getVideoEvents, getAlarmEvents, getHistoryEvents, getAllVideoEvents, getAllAlarmEvents, getAllHistoryEvents
|
||||||
|
* (bropat) P2P session: Added station serial number to logging entries for debugging purposes
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 0.7.1 (2021-04-02)
|
||||||
|
|
||||||
|
* (bropat) Lowered UDP receive buffer size for FreeBSD
|
||||||
|
* (bropat) Fixed lookup timeout issue on "local prefered" connection establishment
|
||||||
|
|
||||||
|
### 0.7.0 (2021-03-30)
|
||||||
|
|
||||||
|
* (bropat) Added support for smart locks
|
||||||
|
* (bropat) Added new P2P feature: lock/unlock smart lock products
|
||||||
|
* (bropat) Optimized speed of P2P connection establishment
|
||||||
|
* (bropat) Implemented P2P connection setup preference: local prefered, local only or quickest connection
|
||||||
|
* (bropat) Trying to solve issue [#2](https://github.com/bropat/eufy-security-client/issues/2)
|
||||||
|
* (bropat) Dropped support for NodeJS 10.x (min. requirement 12)
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 0.6.0 (2021-03-11)
|
||||||
|
|
||||||
|
* (bropat) Added new command types to enum CommandType
|
||||||
|
* (bropat) Added new P2P feature: enable/disable pet detection for indoor cameras
|
||||||
|
* (bropat) Added new P2P feature: enable/disable sound detection for indoor cameras
|
||||||
|
* (bropat) Added new P2P feature: enable/disable led for wired doorbells
|
||||||
|
* (bropat) Added some functions to p2p station class: getLANIPAddress, getGuardMode, getCurrentMode
|
||||||
|
* (bropat) Added new device class: BatteryDoorbellCamera, IndoorCamera, SoloCamera
|
||||||
|
* (bropat) Added new functions to some device classes returning specific parameter values
|
||||||
|
* (bropat) Renamed interface ParameterValue to StringValue and added new: BooleanValue, NumberValue
|
||||||
|
* (bropat) All functions of the Device base class that return parameter values, return now the value and timestamp of the last modification
|
||||||
|
* (bropat) Fixed enable/disable led (for battery doorbells, indoor cameras, floodlight camera and solo cameras)
|
||||||
|
* (bropat) Fixed enable/disable motion detection (for wired doorbells, indoor cameras, floodlight camera and solo cameras)
|
||||||
|
* (bropat) Fixed change video watermark setting (for wired doorbells, battery doorbells, indoor cameras and floodlight camera)
|
||||||
|
* (bropat) Fixed issue with multibyte string with function buildCommandWithStringTypePayload
|
||||||
|
* (bropat) Fixed issue on PushMessage interface (fixed parsing of file_path)
|
||||||
|
|
||||||
|
### 0.5.1 (2021-03-05)
|
||||||
|
|
||||||
|
* (bropat) Fixed download of videos via p2p (wrong channel value in callback)
|
||||||
|
* (bropat) Updated versions of the dev package dependencies
|
||||||
|
|
||||||
|
### 0.5.0 (2021-03-03)
|
||||||
|
|
||||||
|
* (bropat) Added new P2P feature: enable/disable motion detection for camera products
|
||||||
|
* (bropat) Added new P2P feature: enable/disable rtsp stream for camera2 products, indoor and solo cameras
|
||||||
|
* (bropat) Added option to P2P session to enable quick start livestream (after receiving first video frame)
|
||||||
|
* (bropat) Added new methods to HTTPApi for setting custom HTTP session headers: PhoneModel, Country, Language
|
||||||
|
* (bropat) Changed return type of HTTPApi authenticate function
|
||||||
|
* (bropat) Fixed issue during livestreaming if p2p connection is lost
|
||||||
|
|
||||||
|
### 0.4.4 (2021-02-20)
|
||||||
|
|
||||||
|
* (bropat) Fixed possible race condition that sometimes interrupts the livestream
|
||||||
|
|
||||||
|
### 0.4.3 (2021-02-18)
|
||||||
|
|
||||||
|
* (bropat) Added new P2P feature: quick response for doorbell products
|
||||||
|
* (bropat) Fixed wired doorbell p2p livestream (should fix also indoor, floodlight and solo cameras)
|
||||||
|
* (bropat) Fixed issue on new PushMessage interface
|
||||||
|
* (bropat) Updated versions of the package dependencies
|
||||||
|
|
||||||
|
### 0.4.2 (2021-02-15)
|
||||||
|
|
||||||
|
* (bropat) Fixed battery doorbell start livestream P2P command
|
||||||
|
* (bropat) Added CMD_DOORBELL_SET_PAYLOAD as nested command type
|
||||||
|
|
||||||
|
### 0.4.1 (2021-02-14)
|
||||||
|
|
||||||
|
* (bropat) Fixed small typo
|
||||||
|
* (bropat) Uniform debug messages
|
||||||
|
|
||||||
|
### 0.4.0 (2021-02-13)
|
||||||
|
|
||||||
|
* (bropat) Added new P2P feature: Enable/disable device (for camera products)
|
||||||
|
* (bropat) Added new P2P feature: Enable/disable auto night vision (for camera products)
|
||||||
|
* (bropat) Added new P2P feature: Enable/disable led (for camera 2 products, indoor cameras, floodlight camera and solo cameras)
|
||||||
|
* (bropat) Added new P2P feature: Enable/disable anti-theft detection (for camera 2 products)
|
||||||
|
* (bropat) Added new P2P feature: Change video watermark setting (for camera products)
|
||||||
|
* (bropat) Fixed P2P command retry on error 503
|
||||||
|
* (bropat) Fixed issue on new PushMessage interface
|
||||||
|
* (bropat) Fixed issue with handling unencrypted video data
|
||||||
|
|
||||||
|
### 0.3.0 (2021-02-11)
|
||||||
|
|
||||||
|
* (bropat) Added new P2P feature: Download video
|
||||||
|
* (bropat) Implemented refreshing of device and station parameters via P2P
|
||||||
|
* (bropat) Migrated to TypedEmitter (tiny-typed-emitter)
|
||||||
|
* (bropat) Implemented new managed push notification class: PushNotificationService
|
||||||
|
* (bropat) Removed old push notification class: PushRegisterService
|
||||||
|
* (bropat) Renamed previous PushMessage interface to RawPushMessage
|
||||||
|
* (bropat) Introduced new PushMessage interface that normalizes all push notification types into one
|
||||||
|
* (bropat) Fixed issue where readable streams were not correctly destroyed when terminating p2p video streams
|
||||||
|
* (bropat) Fixed P2P start livestream command for Floodlight / Indoor / Solo cameras
|
||||||
|
* (bropat) Implemented refresh of GUARD_MODE on change of SCHEDULE_MODE over p2p (instantly)
|
||||||
|
|
||||||
|
### 0.2.2 (2021-02-06)
|
||||||
|
|
||||||
|
* (bropat) Exported missing P2P interface: StreamMetadata
|
||||||
|
|
||||||
|
### 0.2.1 (2021-02-06)
|
||||||
|
|
||||||
|
* (bropat) Added typescript declaration files
|
||||||
|
|
||||||
|
### 0.2.0 (2021-02-06)
|
||||||
|
|
||||||
|
* (bropat) initial release
|
||||||
|
|
||||||
|
## License
|
||||||
|
|
||||||
|
MIT License
|
||||||
|
|
||||||
|
Copyright (c) 2021-2024 bropat <patrick.broetto@gmail.com>
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
||||||
|
|||||||
127
build/error.d.ts
vendored
Normal file
127
build/error.d.ts
vendored
Normal file
@ -0,0 +1,127 @@
|
|||||||
|
export type Jsonable = string | number | boolean | object | null | undefined | readonly Jsonable[] | {
|
||||||
|
readonly [key: string]: Jsonable;
|
||||||
|
} | {
|
||||||
|
toJSON(): Jsonable;
|
||||||
|
};
|
||||||
|
export declare class BaseError extends Error {
|
||||||
|
readonly context?: Jsonable;
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare function ensureError(value: unknown): BaseError;
|
||||||
|
export declare class InvalidCountryCodeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class InvalidLanguageCodeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class StationNotFoundError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class DeviceNotFoundError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class NotSupportedError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class WrongStationError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class RTSPPropertyNotEnabledError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class InvalidPropertyValueError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class InvalidCommandValueError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ReadOnlyPropertyError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class LivestreamError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class TalkbackError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class StationConnectTimeoutError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class AddUserError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class DeleteUserError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class UpdateUserUsernameError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class UpdateUserScheduleError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class UpdateUserPasscodeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class PinNotVerifiedError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
178
build/error.js
Normal file
178
build/error.js
Normal file
@ -0,0 +1,178 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.PinNotVerifiedError = exports.UpdateUserPasscodeError = exports.UpdateUserScheduleError = exports.UpdateUserUsernameError = exports.DeleteUserError = exports.AddUserError = exports.StationConnectTimeoutError = exports.TalkbackError = exports.LivestreamError = exports.ReadOnlyPropertyError = exports.InvalidCommandValueError = exports.InvalidPropertyValueError = exports.RTSPPropertyNotEnabledError = exports.WrongStationError = exports.NotSupportedError = exports.DeviceNotFoundError = exports.StationNotFoundError = exports.InvalidLanguageCodeError = exports.InvalidCountryCodeError = exports.BaseError = void 0;
|
||||||
|
exports.ensureError = ensureError;
|
||||||
|
class BaseError extends Error {
|
||||||
|
context;
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
const { cause, context } = options;
|
||||||
|
super(message, { cause }); //NodeJs 16.9.0
|
||||||
|
this.name = this.constructor.name;
|
||||||
|
this.context = context;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BaseError = BaseError;
|
||||||
|
function ensureError(value) {
|
||||||
|
if (value instanceof Error)
|
||||||
|
return value;
|
||||||
|
let stringified = "[Unable to stringify the thrown value]";
|
||||||
|
try {
|
||||||
|
stringified = JSON.stringify(value);
|
||||||
|
}
|
||||||
|
catch { }
|
||||||
|
const error = new Error(`This value was thrown as is, not through an Error: ${stringified}`);
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
class InvalidCountryCodeError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = InvalidCountryCodeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.InvalidCountryCodeError = InvalidCountryCodeError;
|
||||||
|
class InvalidLanguageCodeError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = InvalidLanguageCodeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.InvalidLanguageCodeError = InvalidLanguageCodeError;
|
||||||
|
class StationNotFoundError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = StationNotFoundError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.StationNotFoundError = StationNotFoundError;
|
||||||
|
class DeviceNotFoundError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = DeviceNotFoundError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.DeviceNotFoundError = DeviceNotFoundError;
|
||||||
|
class NotSupportedError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = NotSupportedError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.NotSupportedError = NotSupportedError;
|
||||||
|
class WrongStationError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = WrongStationError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.WrongStationError = WrongStationError;
|
||||||
|
class RTSPPropertyNotEnabledError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = RTSPPropertyNotEnabledError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.RTSPPropertyNotEnabledError = RTSPPropertyNotEnabledError;
|
||||||
|
class InvalidPropertyValueError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = InvalidPropertyValueError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.InvalidPropertyValueError = InvalidPropertyValueError;
|
||||||
|
class InvalidCommandValueError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = InvalidCommandValueError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.InvalidCommandValueError = InvalidCommandValueError;
|
||||||
|
class ReadOnlyPropertyError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ReadOnlyPropertyError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ReadOnlyPropertyError = ReadOnlyPropertyError;
|
||||||
|
class LivestreamError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = LivestreamError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.LivestreamError = LivestreamError;
|
||||||
|
class TalkbackError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = TalkbackError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.TalkbackError = TalkbackError;
|
||||||
|
class StationConnectTimeoutError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = StationConnectTimeoutError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.StationConnectTimeoutError = StationConnectTimeoutError;
|
||||||
|
class AddUserError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = AddUserError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.AddUserError = AddUserError;
|
||||||
|
class DeleteUserError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = DeleteUserError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.DeleteUserError = DeleteUserError;
|
||||||
|
class UpdateUserUsernameError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = UpdateUserUsernameError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.UpdateUserUsernameError = UpdateUserUsernameError;
|
||||||
|
class UpdateUserScheduleError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = UpdateUserScheduleError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.UpdateUserScheduleError = UpdateUserScheduleError;
|
||||||
|
class UpdateUserPasscodeError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = UpdateUserPasscodeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.UpdateUserPasscodeError = UpdateUserPasscodeError;
|
||||||
|
class PinNotVerifiedError extends BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = PinNotVerifiedError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.PinNotVerifiedError = PinNotVerifiedError;
|
||||||
|
//# sourceMappingURL=error.js.map
|
||||||
1
build/error.js.map
Normal file
1
build/error.js.map
Normal file
File diff suppressed because one or more lines are too long
179
build/eufysecurity.d.ts
vendored
Normal file
179
build/eufysecurity.d.ts
vendored
Normal file
@ -0,0 +1,179 @@
|
|||||||
|
import { TypedEmitter } from "tiny-typed-emitter";
|
||||||
|
import { EufySecurityEvents, EufySecurityConfig } from "./interfaces";
|
||||||
|
import { HTTPApi } from "./http/api";
|
||||||
|
import { LoginOptions, Schedule } from "./http/interfaces";
|
||||||
|
import { Station } from "./http/station";
|
||||||
|
import { PushNotificationService } from "./push/service";
|
||||||
|
import { Credentials } from "./push/models";
|
||||||
|
import { Device } from "./http/device";
|
||||||
|
import { P2PConnectionType } from "./p2p/types";
|
||||||
|
import { Logger, LoggingCategories } from "./logging";
|
||||||
|
import { LogLevel } from "typescript-logging";
|
||||||
|
export declare class EufySecurity extends TypedEmitter<EufySecurityEvents> {
|
||||||
|
private config;
|
||||||
|
private api;
|
||||||
|
private houses;
|
||||||
|
private stations;
|
||||||
|
private devices;
|
||||||
|
private readonly P2P_REFRESH_INTERVAL_MIN;
|
||||||
|
private cameraMaxLivestreamSeconds;
|
||||||
|
private cameraStationLivestreamTimeout;
|
||||||
|
private pushService;
|
||||||
|
private mqttService;
|
||||||
|
private pushCloudRegistered;
|
||||||
|
private pushCloudChecked;
|
||||||
|
private persistentFile;
|
||||||
|
private persistentData;
|
||||||
|
private connected;
|
||||||
|
private retries;
|
||||||
|
private refreshEufySecurityCloudTimeout?;
|
||||||
|
private refreshEufySecurityP2PTimeout;
|
||||||
|
private deviceSnoozeTimeout;
|
||||||
|
private loadingEmitter;
|
||||||
|
private stationsLoaded?;
|
||||||
|
private devicesLoaded?;
|
||||||
|
private constructor();
|
||||||
|
static initialize(config: EufySecurityConfig, log?: Logger): Promise<EufySecurity>;
|
||||||
|
protected _initializeInternals(): Promise<void>;
|
||||||
|
private initMQTT;
|
||||||
|
setLoggingLevel(category: LoggingCategories, level: LogLevel): void;
|
||||||
|
getLoggingLevel(category: LoggingCategories): number;
|
||||||
|
setInternalLogger(logger: Logger): void;
|
||||||
|
getInternalLogger(): Logger | undefined;
|
||||||
|
getPushService(): PushNotificationService;
|
||||||
|
private addStation;
|
||||||
|
private removeStation;
|
||||||
|
private updateStation;
|
||||||
|
private addDevice;
|
||||||
|
private removeDevice;
|
||||||
|
private updateDevice;
|
||||||
|
getDevices(): Promise<Array<Device>>;
|
||||||
|
getDevicesFromStation(stationSN: string): Promise<Array<Device>>;
|
||||||
|
getDevice(deviceSN: string): Promise<Device>;
|
||||||
|
getStationDevice(stationSN: string, channel: number): Promise<Device>;
|
||||||
|
getStations(): Promise<Array<Station>>;
|
||||||
|
getStation(stationSN: string): Promise<Station>;
|
||||||
|
getApi(): HTTPApi;
|
||||||
|
connectToStation(stationSN: string, p2pConnectionType?: P2PConnectionType): Promise<void>;
|
||||||
|
isStationConnected(stationSN: string): Promise<boolean>;
|
||||||
|
isStationEnergySavingDevice(stationSN: string): Promise<boolean>;
|
||||||
|
private handleHouses;
|
||||||
|
private handleHubs;
|
||||||
|
private refreshP2PData;
|
||||||
|
private onStationConnect;
|
||||||
|
private onStationConnectionError;
|
||||||
|
private onStationClose;
|
||||||
|
private handleDevices;
|
||||||
|
refreshCloudData(): Promise<void>;
|
||||||
|
close(): void;
|
||||||
|
setCameraMaxLivestreamDuration(seconds: number): void;
|
||||||
|
getCameraMaxLivestreamDuration(): number;
|
||||||
|
registerPushNotifications(credentials?: Credentials, persistentIds?: string[]): Promise<void>;
|
||||||
|
connect(options?: LoginOptions): Promise<void>;
|
||||||
|
getPushPersistentIds(): string[];
|
||||||
|
private updateDeviceProperties;
|
||||||
|
private onAPIClose;
|
||||||
|
private onAPIConnect;
|
||||||
|
private onAPIConnectionError;
|
||||||
|
startStationLivestream(deviceSN: string): Promise<void>;
|
||||||
|
stopStationLivestream(deviceSN: string): Promise<void>;
|
||||||
|
private writePersistentData;
|
||||||
|
private saveCloudToken;
|
||||||
|
private savePushCredentials;
|
||||||
|
private savePushPersistentIds;
|
||||||
|
getVersion(): string;
|
||||||
|
isPushConnected(): boolean;
|
||||||
|
isMQTTConnected(): boolean;
|
||||||
|
isConnected(): boolean;
|
||||||
|
private processInvitations;
|
||||||
|
private onPushMessage;
|
||||||
|
startStationDownload(deviceSN: string, path: string, cipherID: number): Promise<void>;
|
||||||
|
cancelStationDownload(deviceSN: string): Promise<void>;
|
||||||
|
getConfig(): EufySecurityConfig;
|
||||||
|
setDeviceProperty(deviceSN: string, name: string, value: unknown): Promise<void>;
|
||||||
|
setStationProperty(stationSN: string, name: string, value: unknown): Promise<void>;
|
||||||
|
private onStartStationLivestream;
|
||||||
|
private onStopStationLivestream;
|
||||||
|
private onErrorStationLivestream;
|
||||||
|
private onStartStationRTSPLivestream;
|
||||||
|
private onStopStationRTSPLivestream;
|
||||||
|
private onStationStartDownload;
|
||||||
|
private onStationFinishDownload;
|
||||||
|
private onStationCommandResult;
|
||||||
|
private onStationSecondaryCommandResult;
|
||||||
|
private onStationRtspUrl;
|
||||||
|
private onStationGuardMode;
|
||||||
|
private onStationCurrentMode;
|
||||||
|
private onStationPropertyChanged;
|
||||||
|
private onStationRawPropertyChanged;
|
||||||
|
private onStationAlarmEvent;
|
||||||
|
private onStationAlarmDelayEvent;
|
||||||
|
private onStationArmDelayEvent;
|
||||||
|
private onStationAlarmArmedEvent;
|
||||||
|
private onDevicePropertyChanged;
|
||||||
|
private onDeviceRawPropertyChanged;
|
||||||
|
private onDeviceCryingDetected;
|
||||||
|
private onDeviceSoundDetected;
|
||||||
|
private onDevicePetDetected;
|
||||||
|
private onDeviceVehicleDetected;
|
||||||
|
private onDeviceMotionDetected;
|
||||||
|
private onDevicePersonDetected;
|
||||||
|
private onDeviceRings;
|
||||||
|
private onDeviceLocked;
|
||||||
|
private onDeviceOpen;
|
||||||
|
private onDevicePackageDelivered;
|
||||||
|
private onDevicePackageStranded;
|
||||||
|
private onDevicePackageTaken;
|
||||||
|
private onDeviceSomeoneLoitering;
|
||||||
|
private onDeviceRadarMotionDetected;
|
||||||
|
private onDevice911Alarm;
|
||||||
|
private onDeviceShakeAlarm;
|
||||||
|
private onDeviceWrongTryProtectAlarm;
|
||||||
|
private onDeviceLongTimeNotClose;
|
||||||
|
private onDeviceLowBattery;
|
||||||
|
private onDeviceJammed;
|
||||||
|
private onDeviceStrangerPersonDetected;
|
||||||
|
private onDeviceDogDetected;
|
||||||
|
private onDeviceDogLickDetected;
|
||||||
|
private onDeviceDogPoopDetected;
|
||||||
|
private onDeviceReady;
|
||||||
|
private onStationRuntimeState;
|
||||||
|
private onStationChargingState;
|
||||||
|
private onStationWifiRssi;
|
||||||
|
private onCaptchaRequest;
|
||||||
|
private onFloodlightManualSwitch;
|
||||||
|
private onAuthTokenInvalidated;
|
||||||
|
private onTfaRequest;
|
||||||
|
private onStationTalkbackStart;
|
||||||
|
private onStationTalkbackStop;
|
||||||
|
private onStationTalkbackError;
|
||||||
|
startStationTalkback(deviceSN: string): Promise<void>;
|
||||||
|
stopStationTalkback(deviceSN: string): Promise<void>;
|
||||||
|
private onStationDeviceShakeAlarm;
|
||||||
|
private onStationDevice911Alarm;
|
||||||
|
private onStationDeviceJammed;
|
||||||
|
private onStationDeviceLowBattery;
|
||||||
|
private onStationDeviceWrongTryProtectAlarm;
|
||||||
|
addUser(deviceSN: string, username: string, passcode: string, schedule?: Schedule): Promise<void>;
|
||||||
|
deleteUser(deviceSN: string, username: string): Promise<void>;
|
||||||
|
updateUser(deviceSN: string, username: string, newUsername: string): Promise<void>;
|
||||||
|
updateUserPasscode(deviceSN: string, username: string, passcode: string): Promise<void>;
|
||||||
|
updateUserSchedule(deviceSN: string, username: string, schedule: Schedule): Promise<void>;
|
||||||
|
private onStationDevicePinVerified;
|
||||||
|
private onStationSdInfoEx;
|
||||||
|
private _emitStationImageDownload;
|
||||||
|
private onStationImageDownload;
|
||||||
|
private onStationDatabaseQueryLatest;
|
||||||
|
private onStationDatabaseQueryLocal;
|
||||||
|
private onStationDatabaseCountByDate;
|
||||||
|
private onStationDatabaseDelete;
|
||||||
|
private onStationSensorStatus;
|
||||||
|
private onStationGarageDoorStatus;
|
||||||
|
private onStorageInfoHb3;
|
||||||
|
private onDeviceTampering;
|
||||||
|
private onDeviceLowTemperature;
|
||||||
|
private onDeviceHighTemperature;
|
||||||
|
private onDevicePinIncorrect;
|
||||||
|
private onDeviceLidStuck;
|
||||||
|
private onDeviceBatteryFullyCharged;
|
||||||
|
}
|
||||||
2634
build/eufysecurity.js
Normal file
2634
build/eufysecurity.js
Normal file
File diff suppressed because it is too large
Load Diff
1
build/eufysecurity.js.map
Normal file
1
build/eufysecurity.js.map
Normal file
File diff suppressed because one or more lines are too long
90
build/http/api.d.ts
vendored
Normal file
90
build/http/api.d.ts
vendored
Normal file
@ -0,0 +1,90 @@
|
|||||||
|
import { TypedEmitter } from "tiny-typed-emitter";
|
||||||
|
import { TrustDevice, Cipher, EventRecordResponse, ConfirmInvite, SensorHistoryEntry, ApiResponse, HouseDetail, DeviceListResponse, StationListResponse, HouseInviteListResponse, HouseListResponse, PassportProfileResponse, User, AddUserResponse } from "./models";
|
||||||
|
import { HTTPApiEvents, Ciphers, FullDevices, Hubs, Voices, Invites, HTTPApiRequest, HTTPApiPersistentData, LoginOptions, Schedule } from "./interfaces";
|
||||||
|
import { EventFilterType, PublicKeyType, VerfyCodeTypes } from "./types";
|
||||||
|
export declare class HTTPApi extends TypedEmitter<HTTPApiEvents> {
|
||||||
|
private static apiDomainBase;
|
||||||
|
private readonly SERVER_PUBLIC_KEY;
|
||||||
|
private apiBase;
|
||||||
|
private username;
|
||||||
|
private password;
|
||||||
|
private ecdh;
|
||||||
|
private token;
|
||||||
|
private tokenExpiration;
|
||||||
|
private renewAuthTokenJob?;
|
||||||
|
private connected;
|
||||||
|
private requestEufyCloud;
|
||||||
|
private throttle;
|
||||||
|
private devices;
|
||||||
|
private hubs;
|
||||||
|
private houses;
|
||||||
|
private persistentData;
|
||||||
|
private headers;
|
||||||
|
private constructor();
|
||||||
|
static getApiBaseFromCloud(country: string): Promise<string>;
|
||||||
|
private loadLibraries;
|
||||||
|
static initialize(country: string, username: string, password: string, persistentData?: HTTPApiPersistentData): Promise<HTTPApi>;
|
||||||
|
private clearScheduleRenewAuthToken;
|
||||||
|
private scheduleRenewAuthToken;
|
||||||
|
private invalidateToken;
|
||||||
|
setPhoneModel(model: string): void;
|
||||||
|
getPhoneModel(): string;
|
||||||
|
getCountry(): string;
|
||||||
|
setLanguage(language: string): void;
|
||||||
|
getLanguage(): string;
|
||||||
|
login(options?: LoginOptions): Promise<void>;
|
||||||
|
sendVerifyCode(type?: VerfyCodeTypes): Promise<boolean>;
|
||||||
|
listTrustDevice(): Promise<Array<TrustDevice>>;
|
||||||
|
addTrustDevice(verifyCode: string): Promise<boolean>;
|
||||||
|
getStationList(): Promise<Array<StationListResponse>>;
|
||||||
|
getDeviceList(): Promise<Array<DeviceListResponse>>;
|
||||||
|
refreshHouseData(): Promise<void>;
|
||||||
|
refreshStationData(): Promise<void>;
|
||||||
|
refreshDeviceData(): Promise<void>;
|
||||||
|
refreshAllData(): Promise<void>;
|
||||||
|
request(request: HTTPApiRequest, withoutUrlPrefix?: boolean): Promise<ApiResponse>;
|
||||||
|
checkPushToken(): Promise<boolean>;
|
||||||
|
registerPushToken(token: string): Promise<boolean>;
|
||||||
|
setParameters(stationSN: string, deviceSN: string, params: {
|
||||||
|
paramType: number;
|
||||||
|
paramValue: any;
|
||||||
|
}[]): Promise<boolean>;
|
||||||
|
getCiphers(/*stationSN: string, */ cipherIDs: Array<number>, userID: string): Promise<Ciphers>;
|
||||||
|
getVoices(deviceSN: string): Promise<Voices>;
|
||||||
|
getCipher(/*stationSN: string, */ cipherID: number, userID: string): Promise<Cipher>;
|
||||||
|
getDevices(): FullDevices;
|
||||||
|
getHubs(): Hubs;
|
||||||
|
getToken(): string | null;
|
||||||
|
getTokenExpiration(): Date | null;
|
||||||
|
setToken(token: string): void;
|
||||||
|
setTokenExpiration(tokenExpiration: Date): void;
|
||||||
|
getAPIBase(): string;
|
||||||
|
setOpenUDID(openudid: string): void;
|
||||||
|
setSerialNumber(serialnumber: string): void;
|
||||||
|
private _getEvents;
|
||||||
|
getVideoEvents(startTime: Date, endTime: Date, filter?: EventFilterType, maxResults?: number): Promise<Array<EventRecordResponse>>;
|
||||||
|
getAlarmEvents(startTime: Date, endTime: Date, filter?: EventFilterType, maxResults?: number): Promise<Array<EventRecordResponse>>;
|
||||||
|
getHistoryEvents(startTime: Date, endTime: Date, filter?: EventFilterType, maxResults?: number): Promise<Array<EventRecordResponse>>;
|
||||||
|
getAllVideoEvents(filter?: EventFilterType, maxResults?: number): Promise<Array<EventRecordResponse>>;
|
||||||
|
getAllAlarmEvents(filter?: EventFilterType, maxResults?: number): Promise<Array<EventRecordResponse>>;
|
||||||
|
getAllHistoryEvents(filter?: EventFilterType, maxResults?: number): Promise<Array<EventRecordResponse>>;
|
||||||
|
isConnected(): boolean;
|
||||||
|
getInvites(): Promise<Invites>;
|
||||||
|
confirmInvites(confirmInvites: Array<ConfirmInvite>): Promise<boolean>;
|
||||||
|
getPublicKey(deviceSN: string, type: PublicKeyType): Promise<string>;
|
||||||
|
decryptAPIData(data?: string, json?: boolean): any;
|
||||||
|
getSensorHistory(stationSN: string, deviceSN: string): Promise<Array<SensorHistoryEntry>>;
|
||||||
|
getHouseDetail(houseID: string): Promise<HouseDetail | null>;
|
||||||
|
getHouseList(): Promise<Array<HouseListResponse>>;
|
||||||
|
getHouseInviteList(isInviter?: number): Promise<Array<HouseInviteListResponse>>;
|
||||||
|
confirmHouseInvite(houseID: string, inviteID: number): Promise<boolean>;
|
||||||
|
getPersistentData(): HTTPApiPersistentData | undefined;
|
||||||
|
getPassportProfile(): Promise<PassportProfileResponse | null>;
|
||||||
|
addUser(deviceSN: string, nickname: string, stationSN?: string): Promise<AddUserResponse | null>;
|
||||||
|
deleteUser(deviceSN: string, shortUserId: string, stationSN?: string): Promise<boolean>;
|
||||||
|
getUsers(deviceSN: string, stationSN: string): Promise<Array<User> | null>;
|
||||||
|
getUser(deviceSN: string, stationSN: string, shortUserId: string): Promise<User | null>;
|
||||||
|
updateUser(deviceSN: string, stationSN: string, shortUserId: string, nickname: string): Promise<boolean>;
|
||||||
|
getImage(deviceSN: string, url: string): Promise<Buffer>;
|
||||||
|
updateUserPassword(deviceSN: string, shortUserId: string, passwordId: string, schedule: Schedule, stationSN?: string): Promise<boolean>;
|
||||||
|
}
|
||||||
1578
build/http/api.js
Normal file
1578
build/http/api.js
Normal file
File diff suppressed because it is too large
Load Diff
1
build/http/api.js.map
Normal file
1
build/http/api.js.map
Normal file
File diff suppressed because one or more lines are too long
8
build/http/cache.d.ts
vendored
Normal file
8
build/http/cache.d.ts
vendored
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
export declare class Cache extends Map {
|
||||||
|
private ttl;
|
||||||
|
private schedules;
|
||||||
|
constructor(ttl?: number);
|
||||||
|
delete(key: any): boolean;
|
||||||
|
set(key: any, value: any, ttl?: number): this;
|
||||||
|
get(key: any): any;
|
||||||
|
}
|
||||||
34
build/http/cache.js
Normal file
34
build/http/cache.js
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.Cache = void 0;
|
||||||
|
class Cache extends Map {
|
||||||
|
ttl = 60000;
|
||||||
|
schedules = new Map();
|
||||||
|
constructor(ttl) {
|
||||||
|
super();
|
||||||
|
if (ttl !== undefined)
|
||||||
|
this.ttl = ttl;
|
||||||
|
}
|
||||||
|
delete(key) {
|
||||||
|
const result = super.delete(key);
|
||||||
|
clearTimeout(this.schedules.get(key));
|
||||||
|
this.schedules.delete(key);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
set(key, value, ttl = this.ttl) {
|
||||||
|
super.set(key, value);
|
||||||
|
if (this.schedules.has(key)) {
|
||||||
|
clearTimeout(this.schedules.get(key));
|
||||||
|
}
|
||||||
|
const schedule = setTimeout(() => {
|
||||||
|
this.delete(key);
|
||||||
|
}, ttl);
|
||||||
|
this.schedules.set(key, schedule);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
get(key) {
|
||||||
|
return super.get(key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.Cache = Cache;
|
||||||
|
//# sourceMappingURL=cache.js.map
|
||||||
1
build/http/cache.js.map
Normal file
1
build/http/cache.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"cache.js","sourceRoot":"","sources":["../../src/http/cache.ts"],"names":[],"mappings":";;;AAAA,MAAa,KAAM,SAAQ,GAAG;IAElB,GAAG,GAAG,KAAK,CAAC;IACZ,SAAS,GAAI,IAAI,GAAG,EAAE,CAAC;IAE/B,YAAY,GAAY;QACpB,KAAK,EAAE,CAAC;QACR,IAAI,GAAG,KAAK,SAAS;YACjB,IAAI,CAAC,GAAG,GAAG,GAAG,CAAC;IACvB,CAAC;IAEM,MAAM,CAAC,GAAQ;QAClB,MAAM,MAAM,GAAG,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;QACjC,YAAY,CAAC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC;QACtC,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;QAC3B,OAAO,MAAM,CAAC;IAClB,CAAC;IAEM,GAAG,CAAC,GAAQ,EAAE,KAAU,EAAE,GAAG,GAAG,IAAI,CAAC,GAAG;QAC3C,KAAK,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;QACtB,IAAI,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,CAAC;YAC1B,YAAY,CAAC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC;QAC1C,CAAC;QAED,MAAM,QAAQ,GAAG,UAAU,CAAC,GAAG,EAAE;YAC7B,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;QACrB,CAAC,EAAE,GAAG,CAAC,CAAC;QACR,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,GAAG,EAAE,QAAQ,CAAC,CAAC;QAClC,OAAO,IAAI,CAAC;IAChB,CAAC;IAEM,GAAG,CAAC,GAAQ;QACf,OAAO,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;IAC1B,CAAC;CACJ;AAlCD,sBAkCC"}
|
||||||
3
build/http/const.d.ts
vendored
Normal file
3
build/http/const.d.ts
vendored
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
import { EufyTimezone } from "./utils";
|
||||||
|
export declare const PhoneModels: Array<string>;
|
||||||
|
export declare const timeZoneData: Array<EufyTimezone>;
|
||||||
8546
build/http/const.js
Normal file
8546
build/http/const.js
Normal file
File diff suppressed because it is too large
Load Diff
1
build/http/const.js.map
Normal file
1
build/http/const.js.map
Normal file
File diff suppressed because one or more lines are too long
474
build/http/device.d.ts
vendored
Normal file
474
build/http/device.d.ts
vendored
Normal file
@ -0,0 +1,474 @@
|
|||||||
|
import { TypedEmitter } from "tiny-typed-emitter";
|
||||||
|
import { HTTPApi } from "./api";
|
||||||
|
import { CommandName, DeviceEvent, SourceType, TrackerType } from "./types";
|
||||||
|
import { DeviceListResponse } from "./models";
|
||||||
|
import { DeviceEvents, PropertyValue, PropertyValues, PropertyMetadataAny, IndexedProperty, RawValues, Schedule, Voices, DeviceConfig } from "./interfaces";
|
||||||
|
import { PushMessage } from "../push/models";
|
||||||
|
import { DeviceSmartLockNotifyData } from "../mqtt/model";
|
||||||
|
import { Station } from "./station";
|
||||||
|
export declare class Device extends TypedEmitter<DeviceEvents> {
|
||||||
|
protected api: HTTPApi;
|
||||||
|
protected rawDevice: DeviceListResponse;
|
||||||
|
protected eventTimeouts: Map<DeviceEvent, NodeJS.Timeout>;
|
||||||
|
protected pictureEventTimeouts: Map<string, NodeJS.Timeout>;
|
||||||
|
protected properties: PropertyValues;
|
||||||
|
protected config: DeviceConfig;
|
||||||
|
private rawProperties;
|
||||||
|
private ready;
|
||||||
|
protected constructor(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig);
|
||||||
|
protected initializeState(): void;
|
||||||
|
initialize(): void;
|
||||||
|
getRawDevice(): DeviceListResponse;
|
||||||
|
update(device: DeviceListResponse): void;
|
||||||
|
updateProperty(name: string, value: PropertyValue, force?: boolean): boolean;
|
||||||
|
updateRawProperties(values: RawValues): void;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
updateRawProperty(type: number, value: string, source: SourceType): boolean;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
getPropertyMetadata(name: string, hidden?: boolean): PropertyMetadataAny;
|
||||||
|
getPropertyValue(name: string): PropertyValue;
|
||||||
|
hasPropertyValue(name: string): boolean;
|
||||||
|
getRawProperty(type: number): string | undefined;
|
||||||
|
getRawProperties(): RawValues;
|
||||||
|
getProperties(): PropertyValues;
|
||||||
|
getPropertiesMetadata(hidden?: boolean): IndexedProperty;
|
||||||
|
hasProperty(name: string, hidden?: boolean): boolean;
|
||||||
|
getCommands(): Array<CommandName>;
|
||||||
|
hasCommand(name: CommandName): boolean;
|
||||||
|
processPushNotification(_station: Station, _message: PushMessage, _eventDurationSeconds: number): void;
|
||||||
|
setCustomPropertyValue(name: string, value: PropertyValue): void;
|
||||||
|
destroy(): void;
|
||||||
|
protected clearEventTimeout(eventType: DeviceEvent): void;
|
||||||
|
static isSupported(type: number): boolean;
|
||||||
|
static isCamera(type: number): boolean;
|
||||||
|
static hasBattery(type: number): boolean;
|
||||||
|
static isStation(type: number): boolean;
|
||||||
|
static isCamera1(type: number): boolean;
|
||||||
|
static isCameraE(type: number): boolean;
|
||||||
|
static isSensor(type: number): boolean;
|
||||||
|
static isKeyPad(type: number): boolean;
|
||||||
|
static isDoorbell(type: number): boolean;
|
||||||
|
static isWiredDoorbell(type: number): boolean;
|
||||||
|
static isWiredDoorbellT8200X(type: number, serialnumber: string): boolean;
|
||||||
|
static isWiredDoorbellDual(type: number): boolean;
|
||||||
|
static isIndoorCamera(type: number): boolean;
|
||||||
|
static isPanAndTiltCamera(type: number): boolean;
|
||||||
|
static isOutdoorPanAndTiltCamera(type: number): boolean;
|
||||||
|
static isIndoorPanAndTiltCameraS350(type: number): boolean;
|
||||||
|
static isFloodLight(type: number): boolean;
|
||||||
|
static isFloodLightT8420X(type: number, serialnumber: string): boolean;
|
||||||
|
static isFloodLightT8423(type: number): boolean;
|
||||||
|
static isFloodLightT8425(type: number): boolean;
|
||||||
|
static isWallLightCam(type: number): boolean;
|
||||||
|
static isLock(type: number): boolean;
|
||||||
|
static isLockKeypad(type: number): boolean;
|
||||||
|
static isLockBle(type: number): boolean;
|
||||||
|
static isLockBleNoFinger(type: number): boolean;
|
||||||
|
static isLockWifi(type: number, serialnumber: string): boolean;
|
||||||
|
static isLockWifiNoFinger(type: number): boolean;
|
||||||
|
static isLockWifiR10(type: number): boolean;
|
||||||
|
static isLockWifiR20(type: number): boolean;
|
||||||
|
static isLockWifiVideo(type: number): boolean;
|
||||||
|
static isLockWifiR10Keypad(type: number): boolean;
|
||||||
|
static isLockWifiR20Keypad(type: number): boolean;
|
||||||
|
static isLockWifiT8506(type: number): boolean;
|
||||||
|
static isLockWifiT8502(type: number): boolean;
|
||||||
|
static isLockWifiT8510P(type: number, serialnumber: string): boolean;
|
||||||
|
static isLockWifiT8520P(type: number, serialnumber: string): boolean;
|
||||||
|
static isBatteryDoorbell1(type: number): boolean;
|
||||||
|
static isBatteryDoorbell2(type: number): boolean;
|
||||||
|
static isBatteryDoorbellDual(type: number): boolean;
|
||||||
|
static isBatteryDoorbellDualE340(type: number): boolean;
|
||||||
|
static isBatteryDoorbellC30(type: number): boolean;
|
||||||
|
static isBatteryDoorbellC31(type: number): boolean;
|
||||||
|
static isDoorbellDual(type: number): boolean;
|
||||||
|
static isBatteryDoorbell(type: number): boolean;
|
||||||
|
static isSoloCamera(type: number): boolean;
|
||||||
|
static isSoloCameraPro(type: number): boolean;
|
||||||
|
static isSoloCameraSpotlight1080(type: number): boolean;
|
||||||
|
static isSoloCameraSpotlight2k(type: number): boolean;
|
||||||
|
static isSoloCameraSpotlightSolar(type: number): boolean;
|
||||||
|
static isSoloCameraSolar(type: number): boolean;
|
||||||
|
static isSoloCameraC210(type: number): boolean;
|
||||||
|
static isSoloCameraE30(type: number): boolean;
|
||||||
|
static isSoloCameras(type: number): boolean;
|
||||||
|
static isStarlight4GLTE(type: number): boolean;
|
||||||
|
static isIndoorOutdoorCamera1080p(type: number): boolean;
|
||||||
|
static isIndoorOutdoorCamera1080pNoLight(type: number): boolean;
|
||||||
|
static isIndoorOutdoorCamera2k(type: number): boolean;
|
||||||
|
static isIndoorCamMini(type: number): boolean;
|
||||||
|
static isCamera1Product(type: number): boolean;
|
||||||
|
static isCamera2(type: number): boolean;
|
||||||
|
static isCamera2C(type: number): boolean;
|
||||||
|
static isCamera2Pro(type: number): boolean;
|
||||||
|
static isCamera2CPro(type: number): boolean;
|
||||||
|
static isCamera2Product(type: number): boolean;
|
||||||
|
static isCamera3(type: number): boolean;
|
||||||
|
static isCamera3C(type: number): boolean;
|
||||||
|
static isCamera3Pro(type: number): boolean;
|
||||||
|
static isCameraProfessional247(type: number): boolean;
|
||||||
|
static isCamera3Product(type: number): boolean;
|
||||||
|
static isEntrySensor(type: number): boolean;
|
||||||
|
static isMotionSensor(type: number): boolean;
|
||||||
|
static isSmartDrop(type: number): boolean;
|
||||||
|
static isSmartSafe(type: number): boolean;
|
||||||
|
static isGarageCamera(type: number): boolean;
|
||||||
|
static isIntegratedDeviceBySn(sn: string): boolean;
|
||||||
|
static isSoloCameraBySn(sn: string): boolean;
|
||||||
|
static isSmartDropBySn(sn: string): boolean;
|
||||||
|
static isLockBySn(sn: string): boolean;
|
||||||
|
static isGarageCameraBySn(sn: string): boolean;
|
||||||
|
static isFloodlightBySn(sn: string): boolean;
|
||||||
|
static isIndoorCameraBySn(sn: string): boolean;
|
||||||
|
static is4GCameraBySn(sn: string): boolean;
|
||||||
|
static isSmartSafeBySn(sn: string): boolean;
|
||||||
|
static isSmartTrackCard(type: number): boolean;
|
||||||
|
static isSmartTrackLink(type: number): boolean;
|
||||||
|
static isSmartTrack(type: number): boolean;
|
||||||
|
isCamera(): boolean;
|
||||||
|
isFloodLight(): boolean;
|
||||||
|
isFloodLightT8420X(): boolean;
|
||||||
|
isFloodLightT8423(): boolean;
|
||||||
|
isFloodLightT8425(): boolean;
|
||||||
|
isWallLightCam(): boolean;
|
||||||
|
isDoorbell(): boolean;
|
||||||
|
isWiredDoorbell(): boolean;
|
||||||
|
isWiredDoorbellT8200X(): boolean;
|
||||||
|
isWiredDoorbellDual(): boolean;
|
||||||
|
isLock(): boolean;
|
||||||
|
isLockKeypad(): boolean;
|
||||||
|
isLockBle(): boolean;
|
||||||
|
isLockBleNoFinger(): boolean;
|
||||||
|
isLockWifi(): boolean;
|
||||||
|
isLockWifiNoFinger(): boolean;
|
||||||
|
isLockWifiR10(): boolean;
|
||||||
|
isLockWifiR20(): boolean;
|
||||||
|
isLockWifiVideo(): boolean;
|
||||||
|
isLockWifiR10Keypad(): boolean;
|
||||||
|
isLockWifiR20Keypad(): boolean;
|
||||||
|
isLockWifiT8506(): boolean;
|
||||||
|
isLockWifiT8502(): boolean;
|
||||||
|
isLockWifiT8510P(): boolean;
|
||||||
|
isLockWifiT8520P(): boolean;
|
||||||
|
isBatteryDoorbell1(): boolean;
|
||||||
|
isBatteryDoorbell2(): boolean;
|
||||||
|
isBatteryDoorbellDual(): boolean;
|
||||||
|
isBatteryDoorbellDualE340(): boolean;
|
||||||
|
isBatteryDoorbellC30(): boolean;
|
||||||
|
isBatteryDoorbellC31(): boolean;
|
||||||
|
isDoorbellDual(): boolean;
|
||||||
|
isBatteryDoorbell(): boolean;
|
||||||
|
isSoloCamera(): boolean;
|
||||||
|
isSoloCameraPro(): boolean;
|
||||||
|
isSoloCameraSpotlight1080(): boolean;
|
||||||
|
isSoloCameraSpotlight2k(): boolean;
|
||||||
|
isSoloCameraSpotlightSolar(): boolean;
|
||||||
|
isSoloCameraSolar(): boolean;
|
||||||
|
isSoloCameraC210(): boolean;
|
||||||
|
isSoloCameraE30(): boolean;
|
||||||
|
isStarlight4GLTE(): boolean;
|
||||||
|
isIndoorOutdoorCamera1080p(): boolean;
|
||||||
|
isIndoorOutdoorCamera1080pNoLight(): boolean;
|
||||||
|
isIndoorOutdoorCamera2k(): boolean;
|
||||||
|
isIndoorCamMini(): boolean;
|
||||||
|
isSoloCameras(): boolean;
|
||||||
|
isCamera2(): boolean;
|
||||||
|
isCamera2C(): boolean;
|
||||||
|
isCamera2Pro(): boolean;
|
||||||
|
isCamera2CPro(): boolean;
|
||||||
|
isCamera2Product(): boolean;
|
||||||
|
isCamera3(): boolean;
|
||||||
|
isCamera3C(): boolean;
|
||||||
|
isCameraProfessional247(): boolean;
|
||||||
|
isCamera3Pro(): boolean;
|
||||||
|
isCamera3Product(): boolean;
|
||||||
|
isEntrySensor(): boolean;
|
||||||
|
isKeyPad(): boolean;
|
||||||
|
isMotionSensor(): boolean;
|
||||||
|
isIndoorCamera(): boolean;
|
||||||
|
isPanAndTiltCamera(): boolean;
|
||||||
|
isOutdoorPanAndTiltCamera(): boolean;
|
||||||
|
isIndoorPanAndTiltCameraS350(): boolean;
|
||||||
|
isSmartDrop(): boolean;
|
||||||
|
isSmartSafe(): boolean;
|
||||||
|
isGarageCamera(): boolean;
|
||||||
|
isIntegratedDevice(): boolean;
|
||||||
|
isSmartTrack(): boolean;
|
||||||
|
isSmartTrackCard(): boolean;
|
||||||
|
isSmartTrackLink(): boolean;
|
||||||
|
hasBattery(): boolean;
|
||||||
|
getDeviceKey(): string;
|
||||||
|
getDeviceType(): number;
|
||||||
|
getHardwareVersion(): string;
|
||||||
|
getSoftwareVersion(): string;
|
||||||
|
getModel(): string;
|
||||||
|
getName(): string;
|
||||||
|
getSerial(): string;
|
||||||
|
getStationSerial(): string;
|
||||||
|
setParameters(params: {
|
||||||
|
paramType: number;
|
||||||
|
paramValue: any;
|
||||||
|
}[]): Promise<boolean>;
|
||||||
|
getChannel(): number;
|
||||||
|
getStateID(state: string, level?: number): string;
|
||||||
|
getStateChannel(): string;
|
||||||
|
getWifiRssi(): PropertyValue;
|
||||||
|
getStoragePath(filename: string): string;
|
||||||
|
isEnabled(): PropertyValue;
|
||||||
|
}
|
||||||
|
export declare class Camera extends Device {
|
||||||
|
protected constructor(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig);
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<Camera>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
getLastCameraImageURL(): PropertyValue;
|
||||||
|
getMACAddress(): string;
|
||||||
|
startDetection(): Promise<void>;
|
||||||
|
stopDetection(): Promise<void>;
|
||||||
|
getState(): PropertyValue;
|
||||||
|
close(): Promise<void>;
|
||||||
|
getLastChargingDays(): number;
|
||||||
|
getLastChargingFalseEvents(): number;
|
||||||
|
getLastChargingRecordedEvents(): number;
|
||||||
|
getLastChargingTotalEvents(): number;
|
||||||
|
getBatteryValue(): PropertyValue;
|
||||||
|
getBatteryTemperature(): PropertyValue;
|
||||||
|
isMotionDetectionEnabled(): PropertyValue;
|
||||||
|
isLedEnabled(): PropertyValue;
|
||||||
|
isAutoNightVisionEnabled(): PropertyValue;
|
||||||
|
isRTSPStreamEnabled(): PropertyValue;
|
||||||
|
isAntiTheftDetectionEnabled(): PropertyValue;
|
||||||
|
getWatermark(): PropertyValue;
|
||||||
|
isMotionDetected(): boolean;
|
||||||
|
isPersonDetected(): boolean;
|
||||||
|
getDetectedPerson(): string;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
}
|
||||||
|
export declare class SoloCamera extends Camera {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<SoloCamera>;
|
||||||
|
isLedEnabled(): PropertyValue;
|
||||||
|
isMotionDetectionEnabled(): PropertyValue;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
}
|
||||||
|
export declare class IndoorCamera extends Camera {
|
||||||
|
protected constructor(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig);
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<IndoorCamera>;
|
||||||
|
isLedEnabled(): PropertyValue;
|
||||||
|
isMotionDetectionEnabled(): PropertyValue;
|
||||||
|
isPetDetectionEnabled(): PropertyValue;
|
||||||
|
isSoundDetectionEnabled(): PropertyValue;
|
||||||
|
isPetDetected(): boolean;
|
||||||
|
isSoundDetected(): boolean;
|
||||||
|
isCryingDetected(): boolean;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
destroy(): void;
|
||||||
|
}
|
||||||
|
export declare class DoorbellCamera extends Camera {
|
||||||
|
protected voices: Voices;
|
||||||
|
protected constructor(api: HTTPApi, device: DeviceListResponse, voices: Voices, deviceConfig: DeviceConfig);
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<DoorbellCamera>;
|
||||||
|
private loadMetadataVoiceStates;
|
||||||
|
getVoiceName(id: number): string;
|
||||||
|
getVoices(): Voices;
|
||||||
|
getPropertiesMetadata(hidden?: boolean): IndexedProperty;
|
||||||
|
isRinging(): boolean;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
}
|
||||||
|
export declare class WiredDoorbellCamera extends DoorbellCamera {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<WiredDoorbellCamera>;
|
||||||
|
isLedEnabled(): PropertyValue;
|
||||||
|
isAutoNightVisionEnabled(): PropertyValue;
|
||||||
|
isMotionDetectionEnabled(): PropertyValue;
|
||||||
|
}
|
||||||
|
export declare class BatteryDoorbellCamera extends DoorbellCamera {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<BatteryDoorbellCamera>;
|
||||||
|
isLedEnabled(): PropertyValue;
|
||||||
|
}
|
||||||
|
export declare class FloodlightCamera extends Camera {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<FloodlightCamera>;
|
||||||
|
isLedEnabled(): PropertyValue;
|
||||||
|
isMotionDetectionEnabled(): PropertyValue;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
}
|
||||||
|
export declare class WallLightCam extends Camera {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<WallLightCam>;
|
||||||
|
isLedEnabled(): PropertyValue;
|
||||||
|
isMotionDetectionEnabled(): PropertyValue;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
getPropertiesMetadata(hidden?: boolean): IndexedProperty;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
}
|
||||||
|
export declare class GarageCamera extends Camera {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<GarageCamera>;
|
||||||
|
isLedEnabled(): PropertyValue;
|
||||||
|
isMotionDetectionEnabled(): PropertyValue;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
}
|
||||||
|
export declare class Sensor extends Device {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<Sensor>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
getState(): PropertyValue;
|
||||||
|
}
|
||||||
|
export declare class EntrySensor extends Sensor {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<EntrySensor>;
|
||||||
|
isSensorOpen(): PropertyValue;
|
||||||
|
getSensorChangeTime(): PropertyValue;
|
||||||
|
isBatteryLow(): PropertyValue;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
}
|
||||||
|
export declare class MotionSensor extends Sensor {
|
||||||
|
static readonly MOTION_COOLDOWN_MS = 120000;
|
||||||
|
protected constructor(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig);
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<MotionSensor>;
|
||||||
|
isMotionDetected(): boolean;
|
||||||
|
getMotionSensorPIREvent(): PropertyValue;
|
||||||
|
isBatteryLow(): PropertyValue;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
}
|
||||||
|
export declare class Lock extends Device {
|
||||||
|
static readonly VERSION_CODE_SMART_LOCK = 3;
|
||||||
|
static readonly VERSION_CODE_LOCKV12 = 18;
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<Lock>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
getState(): PropertyValue;
|
||||||
|
getBatteryValue(): PropertyValue;
|
||||||
|
getWifiRssi(): PropertyValue;
|
||||||
|
isLocked(): PropertyValue;
|
||||||
|
getLockStatus(): PropertyValue;
|
||||||
|
static encodeESLCmdOnOff(short_user_id: number, nickname: string, lock: boolean): Buffer;
|
||||||
|
static encodeESLCmdQueryStatus(admin_user_id: string): Buffer;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
processMQTTNotification(message: DeviceSmartLockNotifyData, eventDurationSeconds: number): void;
|
||||||
|
private processNotification;
|
||||||
|
private static getCurrentTimeInSeconds;
|
||||||
|
private static getUInt8Buffer;
|
||||||
|
private static getUint16LEBuffer;
|
||||||
|
private static getUint16BEBuffer;
|
||||||
|
static encodeCmdStatus(user_id: string): Buffer;
|
||||||
|
static encodeCmdUnlock(short_user_id: string, value: number, username: string): Buffer;
|
||||||
|
static encodeCmdCalibrate(user_id: string): Buffer;
|
||||||
|
static encodeCmdAddUser(short_user_id: string, passcode: string, username: string, schedule?: Schedule, user_permission?: number): Buffer;
|
||||||
|
static encodeCmdAddTemporaryUser(schedule?: Schedule, unlimited?: boolean): Buffer;
|
||||||
|
static encodeCmdDeleteTemporaryUser(password_id: string): Buffer;
|
||||||
|
static encodeCmdDeleteUser(short_user_id: string): Buffer;
|
||||||
|
static encodeCmdVerifyPw(password: string): Buffer;
|
||||||
|
static encodeCmdQueryLockRecord(index: number): Buffer;
|
||||||
|
static encodeCmdQueryUser(short_user_id: string): Buffer;
|
||||||
|
static encodeCmdQueryPassword(password_id: string): Buffer;
|
||||||
|
static encodeCmdModifyPassword(password_id: string, passcode: string): Buffer;
|
||||||
|
static encodeCmdUpdateSchedule(short_user_id: string, schedule: Schedule): Buffer;
|
||||||
|
static encodeCmdModifyUsername(username: string, password_id: string): Buffer;
|
||||||
|
static encodeCmdGetLockParam(user_id: string): Buffer;
|
||||||
|
static encodeCmdSetLockParamAutoLock(enabled: boolean, lockTimeSeconds: number): Buffer;
|
||||||
|
private static hexTime;
|
||||||
|
static encodeCmdSetLockParamAutoLockSchedule(enabled: boolean, schedule_start: string, schedule_end: string): Buffer;
|
||||||
|
static encodeCmdSetLockParamOneTouchLock(enabled: boolean): Buffer;
|
||||||
|
static encodeCmdSetLockParamWrongTryProtect(enabled: boolean, lockdownTime: number, attempts: number): Buffer;
|
||||||
|
static encodeCmdSetLockParamScramblePasscode(enabled: boolean): Buffer;
|
||||||
|
static encodeCmdSetLockParamSound(value: number): Buffer;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
static encodeCmdSmartLockUnlock(adminUserId: string, lock: boolean, username: string, shortUserId: string): Buffer;
|
||||||
|
static encodeCmdSmartLockCalibrate(adminUserId: string): Buffer;
|
||||||
|
static encodeCmdSetSmartLockParamWrongTryProtect(adminUserId: string, enabled: boolean, attempts: number, lockdownTime: number): Buffer;
|
||||||
|
private static hexTimeSmartLock;
|
||||||
|
static encodeCmdSetSmartLockParamAutoLock(adminUserId: string, enabled: boolean, lockTimeSeconds: number, schedule: boolean, scheduleStart: string, scheduleEnd: string): Buffer;
|
||||||
|
static encodeCmdSetSmartLockParamOneTouchLock(adminUserId: string, enabled: boolean): Buffer;
|
||||||
|
static encodeCmdSetSmartLockParamScramblePasscode(adminUserId: string, enabled: boolean): Buffer;
|
||||||
|
static encodeCmdSetSmartLockParamSound(adminUserId: string, value: number): Buffer;
|
||||||
|
static encodeCmdSmartLockAddUser(adminUserId: string, shortUserId: string, passcode: string, username: string, schedule?: Schedule, userPermission?: number): Buffer;
|
||||||
|
static encodeCmdSmartLockDeleteUser(adminUserId: string, shortUserId: string): Buffer;
|
||||||
|
static encodeCmdSmartLockUpdateSchedule(adminUserId: string, shortUserId: string, username: string, schedule: Schedule, userPermission?: number): Buffer;
|
||||||
|
static encodeCmdSmartLockModifyPassword(adminUserId: string, passwordId: string, passcode: string): Buffer;
|
||||||
|
static encodeCmdSmartLockGetUserList(adminUserId: string): Buffer;
|
||||||
|
static encodeCmdSmartLockStatus(adminUserId: string): Buffer;
|
||||||
|
static encodeCmdSmartLockGetParams(adminUserId: string): Buffer;
|
||||||
|
}
|
||||||
|
export declare class LockKeypad extends Device {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<LockKeypad>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
}
|
||||||
|
export declare class Keypad extends Device {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<Keypad>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
getState(): PropertyValue;
|
||||||
|
isBatteryLow(): PropertyValue;
|
||||||
|
isBatteryCharging(): PropertyValue;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
}
|
||||||
|
export declare class SmartSafe extends Device {
|
||||||
|
static readonly IV = "052E19EB3F880512E99EBB684D4DC1FE";
|
||||||
|
static readonly DATA_HEADER: number[];
|
||||||
|
static readonly VERSION_CODE = 1;
|
||||||
|
static readonly PUSH_NOTIFICATION_POSITION: {
|
||||||
|
[index: string]: number;
|
||||||
|
};
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<SmartSafe>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
private static getCurrentTimeInSeconds;
|
||||||
|
private static getUInt8Buffer;
|
||||||
|
private static getUint16LEBuffer;
|
||||||
|
private static encodeCmdSingleUInt8;
|
||||||
|
static encodeCmdWrongTryProtect(user_id: string, enabled: boolean, attempts: number, lockdownTime: number): Buffer;
|
||||||
|
static encodeCmdLeftOpenAlarm(user_id: string, enabled: boolean, duration: number): Buffer;
|
||||||
|
static encodeCmdDualUnlock(user_id: string, enabled: boolean): Buffer;
|
||||||
|
static encodeCmdScramblePIN(user_id: string, enabled: boolean): Buffer;
|
||||||
|
static encodeCmdPowerSave(user_id: string, enabled: boolean): Buffer;
|
||||||
|
static encodeCmdInteriorBrightness(user_id: string, interiorBrightness: number, duration: number): Buffer;
|
||||||
|
static encodeCmdTamperAlarm(user_id: string, option: number): Buffer;
|
||||||
|
static encodeCmdRemoteUnlock(user_id: string, option: number): Buffer;
|
||||||
|
static encodeCmdAlertVolume(user_id: string, volume: number): Buffer;
|
||||||
|
static encodeCmdPromptVolume(user_id: string, volume: number): Buffer;
|
||||||
|
static encodeCmdPushNotification(user_id: string, modes: number): Buffer;
|
||||||
|
static encodeCmdUnlock(user_id: string): Buffer;
|
||||||
|
static encodeCmdVerifyPIN(user_id: string, pin: string): Buffer;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
shakeEvent(event: number, eventDurationSeconds: number): void;
|
||||||
|
alarm911Event(event: number, eventDurationSeconds: number): void;
|
||||||
|
jammedEvent(eventDurationSeconds: number): void;
|
||||||
|
lowBatteryEvent(eventDurationSeconds: number): void;
|
||||||
|
wrongTryProtectAlarmEvent(eventDurationSeconds: number): void;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
getState(): PropertyValue;
|
||||||
|
getBatteryValue(): PropertyValue;
|
||||||
|
getWifiRssi(): PropertyValue;
|
||||||
|
isLocked(): boolean;
|
||||||
|
}
|
||||||
|
export declare class Tracker extends Device {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<Tracker>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
setFindPhone(value: boolean): Promise<boolean>;
|
||||||
|
setLeftBehindAlarm(value: boolean): Promise<boolean>;
|
||||||
|
setTrackerType(value: TrackerType): Promise<boolean>;
|
||||||
|
}
|
||||||
|
export declare class DoorbellLock extends DoorbellCamera {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<DoorbellLock>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
getState(): PropertyValue;
|
||||||
|
getBatteryValue(): PropertyValue;
|
||||||
|
getWifiRssi(): PropertyValue;
|
||||||
|
isLocked(): PropertyValue;
|
||||||
|
getLockStatus(): PropertyValue;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
}
|
||||||
|
export declare class SmartDrop extends Camera {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<SmartDrop>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
processPushNotification(station: Station, message: PushMessage, eventDurationSeconds: number): void;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
}
|
||||||
|
export declare class UnknownDevice extends Device {
|
||||||
|
static getInstance(api: HTTPApi, device: DeviceListResponse, deviceConfig: DeviceConfig): Promise<UnknownDevice>;
|
||||||
|
getStateChannel(): string;
|
||||||
|
}
|
||||||
4306
build/http/device.js
Normal file
4306
build/http/device.js
Normal file
File diff suppressed because it is too large
Load Diff
1
build/http/device.js.map
Normal file
1
build/http/device.js.map
Normal file
File diff suppressed because one or more lines are too long
73
build/http/error.d.ts
vendored
Normal file
73
build/http/error.d.ts
vendored
Normal file
@ -0,0 +1,73 @@
|
|||||||
|
import { BaseError, Jsonable } from "../error";
|
||||||
|
export declare class InvalidPropertyError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class LivestreamAlreadyRunningError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class LivestreamNotRunningError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class PropertyNotSupportedError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ApiResponseCodeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ApiInvalidResponseError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ApiHTTPResponseCodeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ApiGenericError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ApiBaseLoadError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ApiRequestError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ImageBaseCodeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ImageSeedError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
101
build/http/error.js
Normal file
101
build/http/error.js
Normal file
@ -0,0 +1,101 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.ImageSeedError = exports.ImageBaseCodeError = exports.ApiRequestError = exports.ApiBaseLoadError = exports.ApiGenericError = exports.ApiHTTPResponseCodeError = exports.ApiInvalidResponseError = exports.ApiResponseCodeError = exports.PropertyNotSupportedError = exports.LivestreamNotRunningError = exports.LivestreamAlreadyRunningError = exports.InvalidPropertyError = void 0;
|
||||||
|
const error_1 = require("../error");
|
||||||
|
class InvalidPropertyError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = InvalidPropertyError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.InvalidPropertyError = InvalidPropertyError;
|
||||||
|
class LivestreamAlreadyRunningError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = LivestreamAlreadyRunningError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.LivestreamAlreadyRunningError = LivestreamAlreadyRunningError;
|
||||||
|
class LivestreamNotRunningError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = LivestreamNotRunningError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.LivestreamNotRunningError = LivestreamNotRunningError;
|
||||||
|
class PropertyNotSupportedError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = PropertyNotSupportedError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.PropertyNotSupportedError = PropertyNotSupportedError;
|
||||||
|
class ApiResponseCodeError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ApiResponseCodeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ApiResponseCodeError = ApiResponseCodeError;
|
||||||
|
class ApiInvalidResponseError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ApiInvalidResponseError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ApiInvalidResponseError = ApiInvalidResponseError;
|
||||||
|
class ApiHTTPResponseCodeError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ApiHTTPResponseCodeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ApiHTTPResponseCodeError = ApiHTTPResponseCodeError;
|
||||||
|
class ApiGenericError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ApiGenericError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ApiGenericError = ApiGenericError;
|
||||||
|
class ApiBaseLoadError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ApiBaseLoadError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ApiBaseLoadError = ApiBaseLoadError;
|
||||||
|
class ApiRequestError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ApiRequestError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ApiRequestError = ApiRequestError;
|
||||||
|
class ImageBaseCodeError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ImageBaseCodeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ImageBaseCodeError = ImageBaseCodeError;
|
||||||
|
class ImageSeedError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ImageSeedError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ImageSeedError = ImageSeedError;
|
||||||
|
//# sourceMappingURL=error.js.map
|
||||||
1
build/http/error.js.map
Normal file
1
build/http/error.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"error.js","sourceRoot":"","sources":["../../src/http/error.ts"],"names":[],"mappings":";;;AAAA,oCAA+C;AAE/C,MAAa,oBAAqB,SAAQ,iBAAS;IAC/C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,oBAAoB,CAAC,IAAI,CAAC;IAC1C,CAAC;CACJ;AAND,oDAMC;AAED,MAAa,6BAA8B,SAAQ,iBAAS;IACxD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,6BAA6B,CAAC,IAAI,CAAC;IACnD,CAAC;CACJ;AAND,sEAMC;AAED,MAAa,yBAA0B,SAAQ,iBAAS;IACpD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,yBAAyB,CAAC,IAAI,CAAC;IAC/C,CAAC;CACJ;AAND,8DAMC;AAED,MAAa,yBAA0B,SAAQ,iBAAS;IACpD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,yBAAyB,CAAC,IAAI,CAAC;IAC/C,CAAC;CACJ;AAND,8DAMC;AAED,MAAa,oBAAqB,SAAQ,iBAAS;IAC/C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,oBAAoB,CAAC,IAAI,CAAC;IAC1C,CAAC;CACJ;AAND,oDAMC;AAED,MAAa,uBAAwB,SAAQ,iBAAS;IAClD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,uBAAuB,CAAC,IAAI,CAAC;IAC7C,CAAC;CACJ;AAND,0DAMC;AAED,MAAa,wBAAyB,SAAQ,iBAAS;IACnD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,wBAAwB,CAAC,IAAI,CAAC;IAC9C,CAAC;CACJ;AAND,4DAMC;AAED,MAAa,eAAgB,SAAQ,iBAAS;IAC1C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,eAAe,CAAC,IAAI,CAAC;IACrC,CAAC;CACJ;AAND,0CAMC;AAED,MAAa,gBAAiB,SAAQ,iBAAS;IAE3C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,gBAAgB,CAAC,IAAI,CAAC;IACtC,CAAC;CACJ;AAPD,4CAOC;AAED,MAAa,eAAgB,SAAQ,iBAAS;IAE1C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,eAAe,CAAC,IAAI,CAAC;IACrC,CAAC;CACJ;AAPD,0CAOC;AAED,MAAa,kBAAmB,SAAQ,iBAAS;IAE7C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,kBAAkB,CAAC,IAAI,CAAC;IACxC,CAAC;CACJ;AAPD,gDAOC;AAED,MAAa,cAAe,SAAQ,iBAAS;IAEzC,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,cAAc,CAAC,IAAI,CAAC;IACpC,CAAC;CACJ;AAPD,wCAOC"}
|
||||||
10
build/http/index.d.ts
vendored
Normal file
10
build/http/index.d.ts
vendored
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
export * from "./api";
|
||||||
|
export * from "./cache";
|
||||||
|
export * from "./device";
|
||||||
|
export * from "./interfaces";
|
||||||
|
export * from "./models";
|
||||||
|
export * from "./parameter";
|
||||||
|
export * from "./station";
|
||||||
|
export * from "./types";
|
||||||
|
export * from "./error";
|
||||||
|
export { isGreaterEqualMinVersion, getAbsoluteFilePath } from "./utils";
|
||||||
30
build/http/index.js
Normal file
30
build/http/index.js
Normal file
@ -0,0 +1,30 @@
|
|||||||
|
"use strict";
|
||||||
|
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
var desc = Object.getOwnPropertyDescriptor(m, k);
|
||||||
|
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
||||||
|
desc = { enumerable: true, get: function() { return m[k]; } };
|
||||||
|
}
|
||||||
|
Object.defineProperty(o, k2, desc);
|
||||||
|
}) : (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
o[k2] = m[k];
|
||||||
|
}));
|
||||||
|
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
||||||
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.getAbsoluteFilePath = exports.isGreaterEqualMinVersion = void 0;
|
||||||
|
__exportStar(require("./api"), exports);
|
||||||
|
__exportStar(require("./cache"), exports);
|
||||||
|
__exportStar(require("./device"), exports);
|
||||||
|
__exportStar(require("./interfaces"), exports);
|
||||||
|
__exportStar(require("./models"), exports);
|
||||||
|
__exportStar(require("./parameter"), exports);
|
||||||
|
__exportStar(require("./station"), exports);
|
||||||
|
__exportStar(require("./types"), exports);
|
||||||
|
__exportStar(require("./error"), exports);
|
||||||
|
var utils_1 = require("./utils");
|
||||||
|
Object.defineProperty(exports, "isGreaterEqualMinVersion", { enumerable: true, get: function () { return utils_1.isGreaterEqualMinVersion; } });
|
||||||
|
Object.defineProperty(exports, "getAbsoluteFilePath", { enumerable: true, get: function () { return utils_1.getAbsoluteFilePath; } });
|
||||||
|
//# sourceMappingURL=index.js.map
|
||||||
1
build/http/index.js.map
Normal file
1
build/http/index.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/http/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAAA,wCAAsB;AACtB,0CAAwB;AACxB,2CAAyB;AACzB,+CAA6B;AAC7B,2CAAyB;AACzB,8CAA4B;AAC5B,4CAA0B;AAC1B,0CAAwB;AACxB,0CAAwB;AACxB,iCAAuE;AAA9D,iHAAA,wBAAwB,OAAA;AAAE,4GAAA,mBAAmB,OAAA"}
|
||||||
241
build/http/interfaces.d.ts
vendored
Normal file
241
build/http/interfaces.d.ts
vendored
Normal file
@ -0,0 +1,241 @@
|
|||||||
|
import { Readable } from "stream";
|
||||||
|
import type { Method } from "got" with {
|
||||||
|
"resolution-mode": "import"
|
||||||
|
};
|
||||||
|
import type { ImageFileExtension } from "image-type" with {
|
||||||
|
"resolution-mode": "import"
|
||||||
|
};
|
||||||
|
import { DatabaseCountByDate, DatabaseQueryLatestInfo, DatabaseQueryLocal, StreamMetadata } from "../p2p/interfaces";
|
||||||
|
import { CommandResult, StorageInfoBodyHB3 } from "../p2p/models";
|
||||||
|
import { AlarmEvent, DatabaseReturnCode, SmartSafeAlarm911Event, SmartSafeShakeAlarmEvent, TFCardStatus } from "../p2p/types";
|
||||||
|
import { Camera, Device } from "./device";
|
||||||
|
import { Cipher, Voice, Invite, DeviceListResponse, StationListResponse, HouseListResponse } from "./models";
|
||||||
|
import { Station } from "./station";
|
||||||
|
import { CommandName, PropertyName, SourceType } from "./types";
|
||||||
|
import { TalkbackStream } from "../p2p/talkback";
|
||||||
|
export type PropertyValue = number | boolean | string | object;
|
||||||
|
export interface PropertyValues {
|
||||||
|
[index: string]: PropertyValue;
|
||||||
|
}
|
||||||
|
export interface DeviceConfig {
|
||||||
|
simultaneousDetections?: boolean;
|
||||||
|
}
|
||||||
|
export interface RawValue {
|
||||||
|
value: string;
|
||||||
|
source: SourceType;
|
||||||
|
}
|
||||||
|
export interface RawValues {
|
||||||
|
[index: number]: RawValue;
|
||||||
|
}
|
||||||
|
export interface Devices {
|
||||||
|
[index: string]: Device;
|
||||||
|
}
|
||||||
|
export interface Cameras {
|
||||||
|
[index: string]: Camera;
|
||||||
|
}
|
||||||
|
export interface Stations {
|
||||||
|
[index: string]: Station;
|
||||||
|
}
|
||||||
|
export interface Houses {
|
||||||
|
[index: string]: HouseListResponse;
|
||||||
|
}
|
||||||
|
export interface Hubs {
|
||||||
|
[index: string]: StationListResponse;
|
||||||
|
}
|
||||||
|
export interface FullDevices {
|
||||||
|
[index: string]: DeviceListResponse;
|
||||||
|
}
|
||||||
|
export interface Ciphers {
|
||||||
|
[index: number]: Cipher;
|
||||||
|
}
|
||||||
|
export interface Voices {
|
||||||
|
[index: number]: Voice;
|
||||||
|
}
|
||||||
|
export interface Invites {
|
||||||
|
[index: number]: Invite;
|
||||||
|
}
|
||||||
|
export interface HTTPApiRequest {
|
||||||
|
method: Method;
|
||||||
|
endpoint: string | URL;
|
||||||
|
responseType?: "text" | "json" | "buffer";
|
||||||
|
data?: any;
|
||||||
|
}
|
||||||
|
export type PropertyMetadataType = "number" | "boolean" | "string" | "object";
|
||||||
|
export interface PropertyMetadataAny {
|
||||||
|
key: number | string;
|
||||||
|
name: PropertyName;
|
||||||
|
type: PropertyMetadataType;
|
||||||
|
default?: any;
|
||||||
|
readable: boolean;
|
||||||
|
writeable: boolean;
|
||||||
|
description?: string;
|
||||||
|
label?: string;
|
||||||
|
commandId?: number;
|
||||||
|
}
|
||||||
|
export interface PropertyMetadataNumeric extends PropertyMetadataAny {
|
||||||
|
type: "number";
|
||||||
|
min?: number;
|
||||||
|
max?: number;
|
||||||
|
steps?: number;
|
||||||
|
default?: number;
|
||||||
|
states?: Record<number, string>;
|
||||||
|
unit?: string;
|
||||||
|
}
|
||||||
|
export interface PropertyMetadataBoolean extends PropertyMetadataAny {
|
||||||
|
type: "boolean";
|
||||||
|
default?: boolean;
|
||||||
|
}
|
||||||
|
export interface PropertyMetadataString extends PropertyMetadataAny {
|
||||||
|
type: "string";
|
||||||
|
minLength?: number;
|
||||||
|
maxLength?: number;
|
||||||
|
default?: string;
|
||||||
|
format?: RegExp;
|
||||||
|
}
|
||||||
|
export interface PropertyMetadataObject extends PropertyMetadataAny {
|
||||||
|
type: "object";
|
||||||
|
isValidObject?: (obj: any) => boolean;
|
||||||
|
default?: any;
|
||||||
|
}
|
||||||
|
export interface IndexedProperty {
|
||||||
|
[index: string]: PropertyMetadataAny;
|
||||||
|
}
|
||||||
|
export interface Properties {
|
||||||
|
[index: number]: IndexedProperty;
|
||||||
|
}
|
||||||
|
export interface Commands {
|
||||||
|
[index: number]: Array<CommandName>;
|
||||||
|
}
|
||||||
|
export interface HTTPApiPersistentData {
|
||||||
|
user_id: string;
|
||||||
|
email: string;
|
||||||
|
nick_name: string;
|
||||||
|
device_public_keys: {
|
||||||
|
[index: string]: string;
|
||||||
|
};
|
||||||
|
clientPrivateKey: string;
|
||||||
|
serverPublicKey: string;
|
||||||
|
}
|
||||||
|
export interface CaptchaOptions {
|
||||||
|
captchaCode: string;
|
||||||
|
captchaId: string;
|
||||||
|
}
|
||||||
|
export interface LoginOptions {
|
||||||
|
verifyCode?: string;
|
||||||
|
captcha?: CaptchaOptions;
|
||||||
|
force: boolean;
|
||||||
|
}
|
||||||
|
export interface Schedule {
|
||||||
|
startDateTime?: Date;
|
||||||
|
endDateTime?: Date;
|
||||||
|
week?: {
|
||||||
|
monday: boolean;
|
||||||
|
tuesday: boolean;
|
||||||
|
wednesday: boolean;
|
||||||
|
thursday: boolean;
|
||||||
|
friday: boolean;
|
||||||
|
saturday: boolean;
|
||||||
|
sunday: boolean;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface ImageType {
|
||||||
|
ext: ImageFileExtension | "unknown";
|
||||||
|
mime: string;
|
||||||
|
}
|
||||||
|
export interface Picture {
|
||||||
|
data: Buffer;
|
||||||
|
type: ImageType;
|
||||||
|
}
|
||||||
|
export interface HTTPApiEvents {
|
||||||
|
"devices": (devices: FullDevices) => void;
|
||||||
|
"hubs": (hubs: Hubs) => void;
|
||||||
|
"houses": (houses: Houses) => void;
|
||||||
|
"connect": () => void;
|
||||||
|
"close": () => void;
|
||||||
|
"connection error": (error: Error) => void;
|
||||||
|
"tfa request": () => void;
|
||||||
|
"captcha request": (id: string, captcha: string) => void;
|
||||||
|
"auth token invalidated": () => void;
|
||||||
|
}
|
||||||
|
export interface StationEvents {
|
||||||
|
"connect": (station: Station) => void;
|
||||||
|
"close": (station: Station) => void;
|
||||||
|
"connection error": (station: Station, error: Error) => void;
|
||||||
|
"raw device property changed": (deviceSN: string, params: RawValues) => void;
|
||||||
|
"property changed": (station: Station, name: string, value: PropertyValue, ready: boolean) => void;
|
||||||
|
"raw property changed": (station: Station, type: number, value: string) => void;
|
||||||
|
"command result": (station: Station, result: CommandResult) => void;
|
||||||
|
"download start": (station: Station, channel: number, metadata: StreamMetadata, videostream: Readable, audiostream: Readable) => void;
|
||||||
|
"download finish": (station: Station, channel: number) => void;
|
||||||
|
"livestream start": (station: Station, channel: number, metadata: StreamMetadata, videostream: Readable, audiostream: Readable) => void;
|
||||||
|
"livestream stop": (station: Station, channel: number) => void;
|
||||||
|
"livestream error": (station: Station, channel: number, error: Error) => void;
|
||||||
|
"rtsp livestream start": (station: Station, channel: number) => void;
|
||||||
|
"rtsp livestream stop": (station: Station, channel: number) => void;
|
||||||
|
"rtsp url": (station: Station, channel: number, value: string) => void;
|
||||||
|
"guard mode": (station: Station, guardMode: number) => void;
|
||||||
|
"current mode": (station: Station, currentMode: number) => void;
|
||||||
|
"alarm event": (station: Station, alarmEvent: AlarmEvent) => void;
|
||||||
|
"ready": (station: Station) => void;
|
||||||
|
"runtime state": (station: Station, channel: number, batteryLevel: number, temperature: number) => void;
|
||||||
|
"charging state": (station: Station, channel: number, chargeType: number, batteryLevel: number) => void;
|
||||||
|
"wifi rssi": (station: Station, channel: number, rssi: number) => void;
|
||||||
|
"floodlight manual switch": (station: Station, channel: number, enabled: boolean) => void;
|
||||||
|
"alarm delay event": (station: Station, alarmDelayEvent: AlarmEvent, alarmDelay: number) => void;
|
||||||
|
"alarm arm delay event": (station: Station, armDelay: number) => void;
|
||||||
|
"alarm armed event": (station: Station) => void;
|
||||||
|
"talkback started": (station: Station, channel: number, talkbackStream: TalkbackStream) => void;
|
||||||
|
"talkback stopped": (station: Station, channel: number) => void;
|
||||||
|
"talkback error": (station: Station, channel: number, error: Error) => void;
|
||||||
|
"secondary command result": (station: Station, result: CommandResult) => void;
|
||||||
|
"device shake alarm": (deviceSN: string, event: SmartSafeShakeAlarmEvent) => void;
|
||||||
|
"device 911 alarm": (deviceSN: string, event: SmartSafeAlarm911Event) => void;
|
||||||
|
"device jammed": (deviceSN: string) => void;
|
||||||
|
"device low battery": (deviceSN: string) => void;
|
||||||
|
"device wrong try-protect alarm": (deviceSN: string) => void;
|
||||||
|
"device pin verified": (deviceSN: string, successfull: boolean) => void;
|
||||||
|
"sd info ex": (station: Station, sdStatus: TFCardStatus, sdCapacity: number, sdCapacityAvailable: number) => void;
|
||||||
|
"image download": (station: Station, file: string, image: Buffer) => void;
|
||||||
|
"database query latest": (station: Station, returnCode: DatabaseReturnCode, data: Array<DatabaseQueryLatestInfo>) => void;
|
||||||
|
"database query local": (station: Station, returnCode: DatabaseReturnCode, data: Array<DatabaseQueryLocal>) => void;
|
||||||
|
"database count by date": (station: Station, returnCode: DatabaseReturnCode, data: Array<DatabaseCountByDate>) => void;
|
||||||
|
"database delete": (station: Station, returnCode: DatabaseReturnCode, failedIds: Array<unknown>) => void;
|
||||||
|
"sensor status": (station: Station, channel: number, status: number) => void;
|
||||||
|
"garage door status": (station: Station, channel: number, doorId: number, status: number) => void;
|
||||||
|
"storage info hb3": (station: Station, channel: number, storageInfo: StorageInfoBodyHB3) => void;
|
||||||
|
}
|
||||||
|
export interface DeviceEvents {
|
||||||
|
"property changed": (device: Device, name: string, value: PropertyValue, ready: boolean) => void;
|
||||||
|
"raw property changed": (device: Device, type: number, value: string) => void;
|
||||||
|
"motion detected": (device: Device, state: boolean) => void;
|
||||||
|
"person detected": (device: Device, state: boolean, person: string) => void;
|
||||||
|
"pet detected": (device: Device, state: boolean) => void;
|
||||||
|
"sound detected": (device: Device, state: boolean) => void;
|
||||||
|
"crying detected": (device: Device, state: boolean) => void;
|
||||||
|
"vehicle detected": (device: Device, state: boolean) => void;
|
||||||
|
"dog detected": (device: Device, state: boolean) => void;
|
||||||
|
"dog lick detected": (device: Device, state: boolean) => void;
|
||||||
|
"dog poop detected": (device: Device, state: boolean) => void;
|
||||||
|
"stranger person detected": (device: Device, state: boolean) => void;
|
||||||
|
"rings": (device: Device, state: boolean) => void;
|
||||||
|
"locked": (device: Device, state: boolean) => void;
|
||||||
|
"open": (device: Device, state: boolean) => void;
|
||||||
|
"ready": (device: Device) => void;
|
||||||
|
"package delivered": (device: Device, state: boolean) => void;
|
||||||
|
"package stranded": (device: Device, state: boolean) => void;
|
||||||
|
"package taken": (device: Device, state: boolean) => void;
|
||||||
|
"someone loitering": (device: Device, state: boolean) => void;
|
||||||
|
"radar motion detected": (device: Device, state: boolean) => void;
|
||||||
|
"911 alarm": (device: Device, state: boolean, detail: SmartSafeAlarm911Event) => void;
|
||||||
|
"shake alarm": (device: Device, state: boolean, detail: SmartSafeShakeAlarmEvent) => void;
|
||||||
|
"wrong try-protect alarm": (device: Device, state: boolean) => void;
|
||||||
|
"long time not close": (device: Device, state: boolean) => void;
|
||||||
|
"low battery": (device: Device, state: boolean) => void;
|
||||||
|
"jammed": (device: Device, state: boolean) => void;
|
||||||
|
"tampering": (device: Device, state: boolean) => void;
|
||||||
|
"low temperature": (device: Device, state: boolean) => void;
|
||||||
|
"high temperature": (device: Device, state: boolean) => void;
|
||||||
|
"pin incorrect": (device: Device, state: boolean) => void;
|
||||||
|
"lid stuck": (device: Device, state: boolean) => void;
|
||||||
|
"battery fully charged": (device: Device, state: boolean) => void;
|
||||||
|
}
|
||||||
3
build/http/interfaces.js
Normal file
3
build/http/interfaces.js
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
//# sourceMappingURL=interfaces.js.map
|
||||||
1
build/http/interfaces.js.map
Normal file
1
build/http/interfaces.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"interfaces.js","sourceRoot":"","sources":["../../src/http/interfaces.ts"],"names":[],"mappings":""}
|
||||||
608
build/http/models.d.ts
vendored
Normal file
608
build/http/models.d.ts
vendored
Normal file
@ -0,0 +1,608 @@
|
|||||||
|
import { UserPasswordType, UserType } from "./types";
|
||||||
|
export interface ApiResponse {
|
||||||
|
status: number;
|
||||||
|
statusText: string;
|
||||||
|
data: any;
|
||||||
|
headers: any;
|
||||||
|
}
|
||||||
|
export interface ResultResponse {
|
||||||
|
code: number;
|
||||||
|
msg: string;
|
||||||
|
data?: any;
|
||||||
|
outline?: any;
|
||||||
|
}
|
||||||
|
export interface LoginResultResponse {
|
||||||
|
user_id: string;
|
||||||
|
email: string;
|
||||||
|
nick_name: string;
|
||||||
|
auth_token: string;
|
||||||
|
token_expires_at: number;
|
||||||
|
avatar: string;
|
||||||
|
invitation_code: string;
|
||||||
|
inviter_code: string;
|
||||||
|
verify_code_url: string;
|
||||||
|
mac_addr: string;
|
||||||
|
domain: string;
|
||||||
|
ab_code: string;
|
||||||
|
geo_key: string;
|
||||||
|
privilege: number;
|
||||||
|
phone: string;
|
||||||
|
phone_code: string;
|
||||||
|
server_secret_info: {
|
||||||
|
public_key: string;
|
||||||
|
} | null;
|
||||||
|
params: Array<{
|
||||||
|
param_type: number;
|
||||||
|
param_value: string;
|
||||||
|
}> | null;
|
||||||
|
trust_list: Array<TrustDevice>;
|
||||||
|
}
|
||||||
|
export interface CaptchaResponse {
|
||||||
|
captcha_id: string;
|
||||||
|
item: string;
|
||||||
|
}
|
||||||
|
export interface LoginRequest {
|
||||||
|
ab: string;
|
||||||
|
client_secret_info: {
|
||||||
|
public_key: string;
|
||||||
|
};
|
||||||
|
enc: number;
|
||||||
|
email: string;
|
||||||
|
password: string;
|
||||||
|
time_zone: number;
|
||||||
|
verify_code?: string;
|
||||||
|
captcha_id?: string;
|
||||||
|
answer?: string;
|
||||||
|
transaction: string;
|
||||||
|
}
|
||||||
|
export interface Member {
|
||||||
|
family_id: number;
|
||||||
|
station_sn: string;
|
||||||
|
admin_user_id: string;
|
||||||
|
member_user_id: string;
|
||||||
|
short_user_id: string;
|
||||||
|
member_type: number;
|
||||||
|
permissions: number;
|
||||||
|
member_nick: string;
|
||||||
|
action_user_id: string;
|
||||||
|
fence_state: number;
|
||||||
|
extra: string;
|
||||||
|
member_avatar: string;
|
||||||
|
house_id: string;
|
||||||
|
create_time: number;
|
||||||
|
update_time: number;
|
||||||
|
status: number;
|
||||||
|
email: string;
|
||||||
|
nick_name: string;
|
||||||
|
avatar: string;
|
||||||
|
action_user_email: string;
|
||||||
|
action_user_name: string;
|
||||||
|
}
|
||||||
|
export interface StationListDevice {
|
||||||
|
device_id: number;
|
||||||
|
is_init_complete: boolean;
|
||||||
|
device_sn: string;
|
||||||
|
device_name: string;
|
||||||
|
device_model: string;
|
||||||
|
time_zone: string;
|
||||||
|
device_type: number;
|
||||||
|
device_channel: number;
|
||||||
|
station_sn: string;
|
||||||
|
schedule: string;
|
||||||
|
schedulex: string;
|
||||||
|
wifi_mac: string;
|
||||||
|
sub1g_mac: string;
|
||||||
|
main_sw_version: string;
|
||||||
|
main_hw_version: string;
|
||||||
|
sec_sw_version: string;
|
||||||
|
sec_hw_version: string;
|
||||||
|
sector_id: number;
|
||||||
|
event_num: number;
|
||||||
|
wifi_ssid: string;
|
||||||
|
ip_addr: string;
|
||||||
|
main_sw_time: number;
|
||||||
|
sec_sw_time: number;
|
||||||
|
bind_time: number;
|
||||||
|
local_ip: string;
|
||||||
|
language: string;
|
||||||
|
sku_number: string;
|
||||||
|
lot_number: string;
|
||||||
|
cpu_id: string;
|
||||||
|
create_time: number;
|
||||||
|
update_time: number;
|
||||||
|
status: number;
|
||||||
|
}
|
||||||
|
export interface StationListResponse {
|
||||||
|
readonly [index: string]: unknown;
|
||||||
|
station_id: number;
|
||||||
|
station_sn: string;
|
||||||
|
station_name: string;
|
||||||
|
station_model: string;
|
||||||
|
time_zone: string;
|
||||||
|
wifi_ssid: string;
|
||||||
|
ip_addr: string;
|
||||||
|
wifi_mac: string;
|
||||||
|
sub1g_mac: string;
|
||||||
|
main_sw_version: string;
|
||||||
|
main_hw_version: string;
|
||||||
|
sec_sw_version: string;
|
||||||
|
sec_hw_version: string;
|
||||||
|
volume: string;
|
||||||
|
main_sw_time: number;
|
||||||
|
sec_sw_time: number;
|
||||||
|
bt_mac: string;
|
||||||
|
setup_code: string;
|
||||||
|
setup_id: string;
|
||||||
|
device_type: number;
|
||||||
|
event_num: number;
|
||||||
|
sku_number: string;
|
||||||
|
lot_number: string;
|
||||||
|
create_time: number;
|
||||||
|
update_time: number;
|
||||||
|
status: number;
|
||||||
|
station_status: number;
|
||||||
|
status_change_time: number;
|
||||||
|
p2p_did: string;
|
||||||
|
push_did: string;
|
||||||
|
p2p_license: string;
|
||||||
|
push_license: string;
|
||||||
|
ndt_did: string;
|
||||||
|
ndt_license: string;
|
||||||
|
wakeup_flag: number;
|
||||||
|
p2p_conn: string;
|
||||||
|
app_conn: string;
|
||||||
|
wipn_enc_dec_key: string;
|
||||||
|
wipn_ndt_aes128key: string;
|
||||||
|
query_server_did: string;
|
||||||
|
prefix: string;
|
||||||
|
wakeup_key: string;
|
||||||
|
member: Member;
|
||||||
|
params: Array<ParameterResponse>;
|
||||||
|
devices: Array<StationListDevice>;
|
||||||
|
sensor_info: null;
|
||||||
|
is_init_complete: boolean;
|
||||||
|
virtual_version: string;
|
||||||
|
house_id?: string;
|
||||||
|
}
|
||||||
|
export interface ParameterResponse {
|
||||||
|
param_id: number;
|
||||||
|
station_sn: string;
|
||||||
|
param_type: number;
|
||||||
|
param_value: string;
|
||||||
|
create_time: number;
|
||||||
|
update_time: number;
|
||||||
|
status: number;
|
||||||
|
}
|
||||||
|
export interface DeviceResponse {
|
||||||
|
device_id: number;
|
||||||
|
is_init_complete: boolean;
|
||||||
|
device_sn: string;
|
||||||
|
device_name: string;
|
||||||
|
device_model: string;
|
||||||
|
time_zone: string;
|
||||||
|
device_type: number;
|
||||||
|
device_channel: number;
|
||||||
|
station_sn: string;
|
||||||
|
schedule: string;
|
||||||
|
schedulex: string;
|
||||||
|
wifi_mac: string;
|
||||||
|
sub1g_mac: string;
|
||||||
|
main_sw_version: string;
|
||||||
|
main_hw_version: string;
|
||||||
|
sec_sw_version: string;
|
||||||
|
sec_hw_version: string;
|
||||||
|
sector_id: number;
|
||||||
|
event_num: number;
|
||||||
|
wifi_ssid: string;
|
||||||
|
ip_addr: string;
|
||||||
|
main_sw_time: number;
|
||||||
|
sec_sw_time: number;
|
||||||
|
bind_time: number;
|
||||||
|
cover_path: string;
|
||||||
|
cover_time: number;
|
||||||
|
local_ip: string;
|
||||||
|
language: string;
|
||||||
|
sku_number: string;
|
||||||
|
lot_number: string;
|
||||||
|
create_time: number;
|
||||||
|
update_time: number;
|
||||||
|
status: number;
|
||||||
|
}
|
||||||
|
export interface DeviceRequest {
|
||||||
|
device_sn: string;
|
||||||
|
num: number;
|
||||||
|
orderby: string;
|
||||||
|
page: number;
|
||||||
|
station_sn: string;
|
||||||
|
}
|
||||||
|
export interface DeviceListResponse {
|
||||||
|
readonly [index: string]: unknown;
|
||||||
|
device_id: number;
|
||||||
|
is_init_complete: boolean;
|
||||||
|
device_sn: string;
|
||||||
|
device_name: string;
|
||||||
|
device_model: string;
|
||||||
|
time_zone: string;
|
||||||
|
device_type: number;
|
||||||
|
device_channel: number;
|
||||||
|
station_sn: string;
|
||||||
|
schedule: string;
|
||||||
|
schedulex: string;
|
||||||
|
wifi_mac: string;
|
||||||
|
sub1g_mac: string;
|
||||||
|
main_sw_version: string;
|
||||||
|
main_hw_version: string;
|
||||||
|
sec_sw_version: string;
|
||||||
|
sec_hw_version: string;
|
||||||
|
sector_id: number;
|
||||||
|
event_num: number;
|
||||||
|
wifi_ssid: string;
|
||||||
|
ip_addr: string;
|
||||||
|
volume: string;
|
||||||
|
main_sw_time: number;
|
||||||
|
sec_sw_time: number;
|
||||||
|
bind_time: number;
|
||||||
|
bt_mac: string;
|
||||||
|
cover_path: string;
|
||||||
|
cover_time: number;
|
||||||
|
local_ip: string;
|
||||||
|
language: string;
|
||||||
|
sku_number: string;
|
||||||
|
lot_number: string;
|
||||||
|
cpu_id: string;
|
||||||
|
create_time: number;
|
||||||
|
update_time: number;
|
||||||
|
status: number;
|
||||||
|
svr_domain: string;
|
||||||
|
svr_port: number;
|
||||||
|
station_conn: {
|
||||||
|
station_sn: string;
|
||||||
|
station_name: string;
|
||||||
|
station_model: string;
|
||||||
|
main_sw_version: string;
|
||||||
|
main_hw_version: string;
|
||||||
|
p2p_did: string;
|
||||||
|
push_did: string;
|
||||||
|
ndt_did: string;
|
||||||
|
p2p_conn: string;
|
||||||
|
app_conn: string;
|
||||||
|
binded: false;
|
||||||
|
setup_code: string;
|
||||||
|
setup_id: string;
|
||||||
|
bt_mac: string;
|
||||||
|
wifi_mac: string;
|
||||||
|
dsk_key: string;
|
||||||
|
expiration: number;
|
||||||
|
};
|
||||||
|
family_num: number;
|
||||||
|
member: Member;
|
||||||
|
permission: any;
|
||||||
|
params: Array<ParameterResponse>;
|
||||||
|
pir_total: number;
|
||||||
|
pir_none: number;
|
||||||
|
pir_missing: number;
|
||||||
|
week_pir_total: number;
|
||||||
|
week_pir_none: number;
|
||||||
|
month_pir_total: number;
|
||||||
|
month_pir_none: number;
|
||||||
|
charging_days: number;
|
||||||
|
charing_total: number;
|
||||||
|
charging_reserve: number;
|
||||||
|
charging_missing: number;
|
||||||
|
battery_usage_last_week: number;
|
||||||
|
virtual_version: string;
|
||||||
|
relate_devices: any;
|
||||||
|
house_id?: string;
|
||||||
|
}
|
||||||
|
export interface DskKeyResponse {
|
||||||
|
enabled: boolean;
|
||||||
|
dsk_keys: Array<{
|
||||||
|
station_sn: string;
|
||||||
|
dsk_key: string;
|
||||||
|
expiration: number;
|
||||||
|
about_to_be_replaced: boolean;
|
||||||
|
}>;
|
||||||
|
}
|
||||||
|
export interface EventRecordResponse {
|
||||||
|
monitor_id: number;
|
||||||
|
transfer_monitor_id: number;
|
||||||
|
station_sn: string;
|
||||||
|
device_sn: string;
|
||||||
|
storage_type: number;
|
||||||
|
storage_path: string;
|
||||||
|
hevc_storage_path: string;
|
||||||
|
cloud_path: string;
|
||||||
|
frame_num: number;
|
||||||
|
thumb_path: string;
|
||||||
|
thumb_data: string;
|
||||||
|
start_time: number;
|
||||||
|
end_time: number;
|
||||||
|
cipher_id: number;
|
||||||
|
cipher_user_id: string;
|
||||||
|
has_human: number;
|
||||||
|
volume: string;
|
||||||
|
vision: number;
|
||||||
|
device_name: string;
|
||||||
|
device_type: number;
|
||||||
|
video_type: number;
|
||||||
|
extra: string;
|
||||||
|
user_range_id: number;
|
||||||
|
viewed: boolean;
|
||||||
|
create_time: number;
|
||||||
|
update_time: number;
|
||||||
|
status: number;
|
||||||
|
station_name: string;
|
||||||
|
p2p_did: string;
|
||||||
|
push_did: string;
|
||||||
|
p2p_license: string;
|
||||||
|
push_license: string;
|
||||||
|
ndt_did: string;
|
||||||
|
ndt_license: string;
|
||||||
|
wakeup_flag: number;
|
||||||
|
p2p_conn: string;
|
||||||
|
app_conn: string;
|
||||||
|
wipn_enc_dec_key: string;
|
||||||
|
wipn_ndt_aes128key: string;
|
||||||
|
query_server_did: string;
|
||||||
|
prefix: string;
|
||||||
|
wakeup_key: string;
|
||||||
|
ai_faces: Array<{
|
||||||
|
is_stranger: number;
|
||||||
|
face_url: string;
|
||||||
|
owner_id: string;
|
||||||
|
user_range_id: number;
|
||||||
|
}>;
|
||||||
|
is_favorite: boolean;
|
||||||
|
storage_alias: number;
|
||||||
|
}
|
||||||
|
export interface EventRecordRequest {
|
||||||
|
device_sn: string;
|
||||||
|
end_time: number;
|
||||||
|
id: number;
|
||||||
|
id_type: number;
|
||||||
|
is_favorite: boolean;
|
||||||
|
num: number;
|
||||||
|
pullup: boolean;
|
||||||
|
shared: boolean;
|
||||||
|
start_time: number;
|
||||||
|
station_sn: string;
|
||||||
|
storage: number;
|
||||||
|
}
|
||||||
|
export interface StreamRequest {
|
||||||
|
device_sn: string;
|
||||||
|
station_sn: string;
|
||||||
|
proto?: number;
|
||||||
|
}
|
||||||
|
export interface TrustDevice {
|
||||||
|
open_udid: string;
|
||||||
|
phone_model: string;
|
||||||
|
is_current_device: number;
|
||||||
|
}
|
||||||
|
export interface Cipher {
|
||||||
|
cipher_id: number;
|
||||||
|
user_id: string;
|
||||||
|
private_key: string;
|
||||||
|
}
|
||||||
|
export interface Voice {
|
||||||
|
voice_id: number;
|
||||||
|
user_id: string;
|
||||||
|
desc: string;
|
||||||
|
device_sn: string;
|
||||||
|
voice_link: string;
|
||||||
|
voice_type: number;
|
||||||
|
key_prefix: string;
|
||||||
|
}
|
||||||
|
export interface DeviceInvite {
|
||||||
|
device_sn: string;
|
||||||
|
checked: boolean;
|
||||||
|
}
|
||||||
|
export interface Invite {
|
||||||
|
invite_id: number;
|
||||||
|
station_sn: string;
|
||||||
|
email: string;
|
||||||
|
devices: Array<DeviceInvite>;
|
||||||
|
action_user_id: string;
|
||||||
|
member_nick: string;
|
||||||
|
member_type: number;
|
||||||
|
permissions: number;
|
||||||
|
create_time: number;
|
||||||
|
update_time: number;
|
||||||
|
status: number;
|
||||||
|
action_user_email: string;
|
||||||
|
action_user_nick: string;
|
||||||
|
}
|
||||||
|
export interface ConfirmInvite {
|
||||||
|
device_sns: Array<string>;
|
||||||
|
invite_id: number;
|
||||||
|
station_sn: string;
|
||||||
|
}
|
||||||
|
export interface SensorHistoryEntry {
|
||||||
|
trigger_time: number;
|
||||||
|
create_time: number;
|
||||||
|
status: string;
|
||||||
|
}
|
||||||
|
export interface HouseUser {
|
||||||
|
id: number;
|
||||||
|
house_id: string;
|
||||||
|
email: string;
|
||||||
|
avatar: string;
|
||||||
|
user_id: string;
|
||||||
|
admin_user_id: string;
|
||||||
|
state: string;
|
||||||
|
role_type: number;
|
||||||
|
}
|
||||||
|
export interface HouseDetail {
|
||||||
|
house_id: string;
|
||||||
|
house_name: string;
|
||||||
|
is_default: number;
|
||||||
|
id: number;
|
||||||
|
geofence_id: number;
|
||||||
|
address: string;
|
||||||
|
latitude: number;
|
||||||
|
longitude: number;
|
||||||
|
radius_range: number;
|
||||||
|
away_mode: number;
|
||||||
|
home_mode: number;
|
||||||
|
location_msg: number;
|
||||||
|
create_time: number;
|
||||||
|
house_users: Array<HouseUser>;
|
||||||
|
house_stations: any;
|
||||||
|
}
|
||||||
|
export interface HouseListResponse {
|
||||||
|
readonly [index: string]: unknown;
|
||||||
|
house_id: string;
|
||||||
|
user_id: string;
|
||||||
|
admin_user_id: string;
|
||||||
|
role_type: number;
|
||||||
|
house_name: string;
|
||||||
|
is_default: number;
|
||||||
|
geofence_id: number;
|
||||||
|
address: string;
|
||||||
|
latitude: number;
|
||||||
|
longitude: number;
|
||||||
|
radius_range: number;
|
||||||
|
location_msg: number;
|
||||||
|
create_time: number;
|
||||||
|
away_mode: number;
|
||||||
|
home_mode: number;
|
||||||
|
}
|
||||||
|
export interface HouseInviteListResponse {
|
||||||
|
readonly [index: string]: unknown;
|
||||||
|
id: number;
|
||||||
|
house_name: string;
|
||||||
|
action_user_nick: string;
|
||||||
|
action_user_email: string;
|
||||||
|
house_id: string;
|
||||||
|
email: string;
|
||||||
|
user_id: string;
|
||||||
|
role_type: number;
|
||||||
|
}
|
||||||
|
export interface ConfirmHouseInvite {
|
||||||
|
house_id: string;
|
||||||
|
invite_id: number;
|
||||||
|
is_inviter: number;
|
||||||
|
user_id: string;
|
||||||
|
}
|
||||||
|
export interface PassportProfileResponse {
|
||||||
|
user_id: string;
|
||||||
|
email: string;
|
||||||
|
nick_name: string;
|
||||||
|
avatar: string;
|
||||||
|
invitation_code: string;
|
||||||
|
inviter_code: string;
|
||||||
|
verify_code_url: string;
|
||||||
|
mac_addr: string;
|
||||||
|
country: {
|
||||||
|
id: number;
|
||||||
|
name: string;
|
||||||
|
code: string;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface StationSecuritySettings {
|
||||||
|
account_id: string;
|
||||||
|
count_down_alarm: StationSecuritySettingsDelayDetails;
|
||||||
|
count_down_arm: StationSecuritySettingsDelayDetails;
|
||||||
|
devices: StationSecuritySettingsDeviceDetails;
|
||||||
|
}
|
||||||
|
export interface StationSecuritySettingsDelayDetails {
|
||||||
|
account_id: string;
|
||||||
|
channel_list: number[];
|
||||||
|
delay_time: number;
|
||||||
|
}
|
||||||
|
export interface StationSecuritySettingsDeviceDetails {
|
||||||
|
action: number;
|
||||||
|
device_channel: number;
|
||||||
|
}
|
||||||
|
export interface SnoozeDetail {
|
||||||
|
snooze_time: number;
|
||||||
|
snooze_chime?: boolean;
|
||||||
|
snooze_motion?: boolean;
|
||||||
|
snooze_homebase?: boolean;
|
||||||
|
}
|
||||||
|
export interface RawSchedule {
|
||||||
|
endDay: string;
|
||||||
|
week: string;
|
||||||
|
startDay: string;
|
||||||
|
startTime: string;
|
||||||
|
endTime: string;
|
||||||
|
}
|
||||||
|
export interface UserPassword {
|
||||||
|
expiration_time: number;
|
||||||
|
is_permanent: number;
|
||||||
|
password: string;
|
||||||
|
password_id: string;
|
||||||
|
password_type: UserPasswordType;
|
||||||
|
name: string;
|
||||||
|
schedule: RawSchedule;
|
||||||
|
}
|
||||||
|
export interface User {
|
||||||
|
avatar: string;
|
||||||
|
password_list: Array<UserPassword>;
|
||||||
|
user_id: string;
|
||||||
|
short_user_id: string;
|
||||||
|
user_name: string;
|
||||||
|
user_type: UserType;
|
||||||
|
is_show: boolean;
|
||||||
|
}
|
||||||
|
export interface UsersResponse {
|
||||||
|
device_sn: string;
|
||||||
|
user_list: Array<User>;
|
||||||
|
}
|
||||||
|
export interface AddUserResponse {
|
||||||
|
user_id: string;
|
||||||
|
short_user_id: string;
|
||||||
|
}
|
||||||
|
export interface GarageDoorSensorsProperty {
|
||||||
|
cmd: number;
|
||||||
|
data: {
|
||||||
|
door_1: {
|
||||||
|
power: number;
|
||||||
|
mac_address: string;
|
||||||
|
version: string;
|
||||||
|
name: string;
|
||||||
|
sn: string;
|
||||||
|
playalarm: number;
|
||||||
|
ota: number;
|
||||||
|
needota: number;
|
||||||
|
};
|
||||||
|
door_2: {
|
||||||
|
power: number;
|
||||||
|
mac_address: string;
|
||||||
|
version: string;
|
||||||
|
name: string;
|
||||||
|
sn: string;
|
||||||
|
playalarm: number;
|
||||||
|
ota: number;
|
||||||
|
needota: number;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface FloodlightDetectionRangeT8425Property {
|
||||||
|
cur_mode: number;
|
||||||
|
test_mode: number;
|
||||||
|
mode0: Array<{
|
||||||
|
id: number;
|
||||||
|
sst: number;
|
||||||
|
}>;
|
||||||
|
mode1: Array<{
|
||||||
|
id: number;
|
||||||
|
sst: number;
|
||||||
|
}>;
|
||||||
|
mode2: Array<{
|
||||||
|
id: number;
|
||||||
|
sst: number;
|
||||||
|
}>;
|
||||||
|
}
|
||||||
|
export interface FloodlightLightSettingsBrightnessScheduleT8425Property {
|
||||||
|
sunset2rise: number;
|
||||||
|
longtitude: string;
|
||||||
|
latitude: string;
|
||||||
|
brightness: number;
|
||||||
|
schedule: Array<unknown>;
|
||||||
|
}
|
||||||
|
export interface FloodlightLightSettingsMotionT8425Property {
|
||||||
|
brightness: number;
|
||||||
|
enable: number;
|
||||||
|
mode: number;
|
||||||
|
time: number;
|
||||||
|
}
|
||||||
3
build/http/models.js
Normal file
3
build/http/models.js
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
//# sourceMappingURL=models.js.map
|
||||||
1
build/http/models.js.map
Normal file
1
build/http/models.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"models.js","sourceRoot":"","sources":["../../src/http/models.ts"],"names":[],"mappings":""}
|
||||||
5
build/http/parameter.d.ts
vendored
Normal file
5
build/http/parameter.d.ts
vendored
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
import { Category } from "typescript-logging-category-style";
|
||||||
|
export declare class ParameterHelper {
|
||||||
|
static readValue(serialNumber: string, type: number, value: string, log: Category): string | undefined;
|
||||||
|
static writeValue(type: number, value: string): string;
|
||||||
|
}
|
||||||
103
build/http/parameter.js
Normal file
103
build/http/parameter.js
Normal file
@ -0,0 +1,103 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.ParameterHelper = void 0;
|
||||||
|
const types_1 = require("../p2p/types");
|
||||||
|
const utils_1 = require("../p2p/utils");
|
||||||
|
const utils_2 = require("../utils");
|
||||||
|
const types_2 = require("./types");
|
||||||
|
const utils_3 = require("./utils");
|
||||||
|
const error_1 = require("../error");
|
||||||
|
class ParameterHelper {
|
||||||
|
static readValue(serialNumber, type, value, log) {
|
||||||
|
if (value) {
|
||||||
|
if (type === types_2.ParamType.SNOOZE_MODE ||
|
||||||
|
type === types_2.ParamType.CAMERA_MOTION_ZONES ||
|
||||||
|
type === types_1.CommandType.CMD_SET_DOORSENSOR_ALWAYS_OPEN_DELAY ||
|
||||||
|
type === types_1.CommandType.CMD_SET_DOORSENSOR_ALWAYS_OPEN ||
|
||||||
|
type === types_1.CommandType.ARM_DELAY_HOME ||
|
||||||
|
type === types_1.CommandType.ARM_DELAY_AWAY ||
|
||||||
|
type === types_1.CommandType.ARM_DELAY_CUS1 ||
|
||||||
|
type === types_1.CommandType.ARM_DELAY_CUS2 ||
|
||||||
|
type === types_1.CommandType.ARM_DELAY_CUS3 ||
|
||||||
|
type === types_1.CommandType.ARM_DELAY_OFF ||
|
||||||
|
type === types_1.CommandType.CELLULAR_INFO ||
|
||||||
|
type === types_1.CommandType.CMD_WALL_LIGHT_SETTINGS_MANUAL_COLORED_LIGHTING ||
|
||||||
|
type === types_1.CommandType.CMD_WALL_LIGHT_SETTINGS_SCHEDULE_COLORED_LIGHTING ||
|
||||||
|
type === types_1.CommandType.CMD_WALL_LIGHT_SETTINGS_MANUAL_COLORED_LIGHTING ||
|
||||||
|
type === types_1.CommandType.CMD_WALL_LIGHT_SETTINGS_COLORED_LIGHTING_COLORS ||
|
||||||
|
type === types_1.CommandType.CMD_WALL_LIGHT_SETTINGS_DYNAMIC_LIGHTING_THEMES ||
|
||||||
|
type === types_1.CommandType.CMD_INDOOR_DET_SET_ACTIVE_ZONE ||
|
||||||
|
type === types_1.CommandType.CMD_SET_PRIVACYPARAM ||
|
||||||
|
type === types_1.CommandType.CMD_BAT_DOORBELL_VIDEO_QUALITY2 ||
|
||||||
|
type === types_1.CommandType.CMD_BAT_DOORBELL_RECORD_QUALITY2 ||
|
||||||
|
type === types_1.CommandType.CMD_SET_CROSS_TRACKING_CAMERA_LIST ||
|
||||||
|
type === types_1.CommandType.CMD_SET_CROSS_TRACKING_GROUP_LIST ||
|
||||||
|
type === types_1.CommandType.CMD_FLOODLIGHT_SET_DETECTION_RANGE_T8425 ||
|
||||||
|
type === types_1.CommandType.CMD_SET_LIGHT_CTRL_BRIGHT_PIR_T8425 ||
|
||||||
|
type === types_1.CommandType.CMD_SET_LIGHT_CTRL_BRIGHT_SCH_T8425) {
|
||||||
|
if (typeof value === "string") {
|
||||||
|
const parsedValue = (0, utils_2.parseJSON)((0, utils_1.getNullTerminatedString)((0, utils_1.decodeBase64)(value), "utf-8"), log);
|
||||||
|
if (parsedValue === undefined) {
|
||||||
|
log.debug("Non-parsable parameter value received from eufy cloud. Will be ignored.", { serialNumber: serialNumber, type: type, value: value });
|
||||||
|
}
|
||||||
|
return parsedValue;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return value; //return object
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (type === types_1.CommandType.CMD_BAT_DOORBELL_SET_NOTIFICATION_MODE ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_RADAR_WD_DETECTION_SENSITIVITY ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_RADAR_WD_AUTO_RESPONSE ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_PACKAGE_STRAND_TIME ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_RING_AUTO_RESPONSE ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_PACKAGE_GUARD_TIME ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_RADAR_WD_DISTANCE ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_RADAR_WD_TIME ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_DELIVERY_GUARD_SWITCH ||
|
||||||
|
type === types_1.CommandType.CMD_DOORBELL_DUAL_PACKAGE_GUARD_VOICE ||
|
||||||
|
type === types_1.CommandType.CMD_CAMERA_GARAGE_DOOR_SENSORS ||
|
||||||
|
type === types_1.CommandType.CMD_MOTION_SET_LEAVING_REACTIONS) {
|
||||||
|
if (typeof value === "string") {
|
||||||
|
const parsedValue = (0, utils_2.parseJSON)(value, log);
|
||||||
|
if (parsedValue === undefined) {
|
||||||
|
log.debug("Non-parsable parameter value received from eufy cloud. Will be ignored.", { serialNumber: serialNumber, type: type, value: value });
|
||||||
|
}
|
||||||
|
return parsedValue;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return value; //return object
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (type === types_1.TrackerCommandType.COMMAND_NEW_LOCATION ||
|
||||||
|
type === types_1.TrackerCommandType.LOCATION_NEW_ADDRESS) {
|
||||||
|
try {
|
||||||
|
const decrypted = (0, utils_3.decryptTrackerData)(Buffer.from(value, "hex"), Buffer.from(serialNumber));
|
||||||
|
if (decrypted !== undefined) {
|
||||||
|
return decrypted.toString("utf8").trim();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (err) {
|
||||||
|
const error = (0, error_1.ensureError)(err);
|
||||||
|
log.debug("Non-parsable parameter value received from eufy cloud. Will be ignored.", { serialNumber: serialNumber, type: type, value: value, error: (0, utils_2.getError)(error) });
|
||||||
|
}
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
static writeValue(type, value) {
|
||||||
|
if (value) {
|
||||||
|
if (type === types_2.ParamType.SNOOZE_MODE ||
|
||||||
|
type === types_2.ParamType.CAMERA_MOTION_ZONES ||
|
||||||
|
type === types_1.CommandType.CMD_SET_DOORSENSOR_ALWAYS_OPEN_DELAY ||
|
||||||
|
type === types_1.CommandType.CMD_SET_DOORSENSOR_ALWAYS_OPEN) {
|
||||||
|
return Buffer.from(JSON.stringify(value)).toString("base64");
|
||||||
|
}
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ParameterHelper = ParameterHelper;
|
||||||
|
//# sourceMappingURL=parameter.js.map
|
||||||
1
build/http/parameter.js.map
Normal file
1
build/http/parameter.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"parameter.js","sourceRoot":"","sources":["../../src/http/parameter.ts"],"names":[],"mappings":";;;AAEA,wCAA+D;AAC/D,wCAAqE;AACrE,oCAA+C;AAC/C,mCAAoC;AACpC,mCAA6C;AAC7C,oCAAuC;AAEvC,MAAa,eAAe;IAEjB,MAAM,CAAC,SAAS,CAAC,YAAoB,EAAE,IAAY,EAAE,KAAa,EAAE,GAAa;QACpF,IAAI,KAAK,EAAE,CAAC;YACR,IAAI,IAAI,KAAK,iBAAS,CAAC,WAAW;gBAC9B,IAAI,KAAK,iBAAS,CAAC,mBAAmB;gBACtC,IAAI,KAAK,mBAAW,CAAC,oCAAoC;gBACzD,IAAI,KAAK,mBAAW,CAAC,8BAA8B;gBACnD,IAAI,KAAK,mBAAW,CAAC,cAAc;gBACnC,IAAI,KAAK,mBAAW,CAAC,cAAc;gBACnC,IAAI,KAAK,mBAAW,CAAC,cAAc;gBACnC,IAAI,KAAK,mBAAW,CAAC,cAAc;gBACnC,IAAI,KAAK,mBAAW,CAAC,cAAc;gBACnC,IAAI,KAAK,mBAAW,CAAC,aAAa;gBAClC,IAAI,KAAK,mBAAW,CAAC,aAAa;gBAClC,IAAI,KAAK,mBAAW,CAAC,+CAA+C;gBACpE,IAAI,KAAK,mBAAW,CAAC,iDAAiD;gBACtE,IAAI,KAAK,mBAAW,CAAC,+CAA+C;gBACpE,IAAI,KAAK,mBAAW,CAAC,+CAA+C;gBACpE,IAAI,KAAK,mBAAW,CAAC,+CAA+C;gBACpE,IAAI,KAAK,mBAAW,CAAC,8BAA8B;gBACnD,IAAI,KAAK,mBAAW,CAAC,oBAAoB;gBACzC,IAAI,KAAK,mBAAW,CAAC,+BAA+B;gBACpD,IAAI,KAAK,mBAAW,CAAC,gCAAgC;gBACrD,IAAI,KAAK,mBAAW,CAAC,kCAAkC;gBACvD,IAAI,KAAK,mBAAW,CAAC,iCAAiC;gBACtD,IAAI,KAAK,mBAAW,CAAC,wCAAwC;gBAC7D,IAAI,KAAK,mBAAW,CAAC,mCAAmC;gBACxD,IAAI,KAAK,mBAAW,CAAC,mCAAmC,EAAE,CAAC;gBAC3D,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;oBAC5B,MAAM,WAAW,GAAG,IAAA,iBAAS,EAAC,IAAA,+BAAuB,EAAC,IAAA,oBAAY,EAAC,KAAK,CAAC,EAAE,OAAO,CAAC,EAAE,GAAG,CAAC,CAAC;oBAC1F,IAAI,WAAW,KAAK,SAAS,EAAE,CAAC;wBAC5B,GAAG,CAAC,KAAK,CAAC,yEAAyE,EAAE,EAAE,YAAY,EAAE,YAAY,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CAAC;oBACnJ,CAAC;oBACD,OAAO,WAAW,CAAC;gBACvB,CAAC;qBAAM,CAAC;oBACJ,OAAO,KAAK,CAAC,CAAC,eAAe;gBACjC,CAAC;YACL,CAAC;iBAAM,IAAI,IAAI,KAAK,mBAAW,CAAC,sCAAsC;gBAClE,IAAI,KAAK,mBAAW,CAAC,gDAAgD;gBACrE,IAAI,KAAK,mBAAW,CAAC,wCAAwC;gBAC7D,IAAI,KAAK,mBAAW,CAAC,qCAAqC;gBAC1D,IAAI,KAAK,mBAAW,CAAC,oCAAoC;gBACzD,IAAI,KAAK,mBAAW,CAAC,oCAAoC;gBACzD,IAAI,KAAK,mBAAW,CAAC,mCAAmC;gBACxD,IAAI,KAAK,mBAAW,CAAC,+BAA+B;gBACpD,IAAI,KAAK,mBAAW,CAAC,uCAAuC;gBAC5D,IAAI,KAAK,mBAAW,CAAC,qCAAqC;gBAC1D,IAAI,KAAK,mBAAW,CAAC,8BAA8B;gBACnD,IAAI,KAAK,mBAAW,CAAC,gCAAgC,EAAE,CAAC;gBACxD,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;oBAC5B,MAAM,WAAW,GAAG,IAAA,iBAAS,EAAC,KAAK,EAAE,GAAG,CAAC,CAAC;oBAC1C,IAAI,WAAW,KAAK,SAAS,EAAE,CAAC;wBAC5B,GAAG,CAAC,KAAK,CAAC,yEAAyE,EAAE,EAAE,YAAY,EAAE,YAAY,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CAAC;oBACnJ,CAAC;oBACD,OAAO,WAAW,CAAC;gBACvB,CAAC;qBAAM,CAAC;oBACJ,OAAO,KAAK,CAAC,CAAC,eAAe;gBACjC,CAAC;YACL,CAAC;iBAAM,IAAI,IAAI,KAAK,0BAAkB,CAAC,oBAAoB;gBACvD,IAAI,KAAK,0BAAkB,CAAC,oBAAoB,EAAE,CAAC;gBACnD,IAAI,CAAC;oBACD,MAAM,SAAS,GAAG,IAAA,0BAAkB,EAAC,MAAM,CAAC,IAAI,CAAC,KAAK,EAAG,KAAK,CAAC,EAAE,MAAM,CAAC,IAAI,CAAC,YAAY,CAAC,CAAC,CAAC;oBAC5F,IAAI,SAAS,KAAK,SAAS,EAAE,CAAC;wBAC1B,OAAO,SAAS,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,CAAC;oBAC7C,CAAC;gBACL,CAAC;gBAAC,OAAO,GAAG,EAAE,CAAC;oBACX,MAAM,KAAK,GAAG,IAAA,mBAAW,EAAC,GAAG,CAAC,CAAC;oBAC/B,GAAG,CAAC,KAAK,CAAC,yEAAyE,EAAE,EAAE,YAAY,EAAE,YAAY,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,IAAA,gBAAQ,EAAC,KAAK,CAAC,EAAE,CAAC,CAAC;gBAC3K,CAAC;gBACD,OAAO,EAAE,CAAC;YACd,CAAC;QACL,CAAC;QACD,OAAO,KAAK,CAAC;IACjB,CAAC;IAEM,MAAM,CAAC,UAAU,CAAC,IAAY,EAAE,KAAa;QAChD,IAAI,KAAK,EAAE,CAAC;YACR,IAAI,IAAI,KAAK,iBAAS,CAAC,WAAW;gBAC9B,IAAI,KAAK,iBAAS,CAAC,mBAAmB;gBACtC,IAAI,KAAK,mBAAW,CAAC,oCAAoC;gBACzD,IAAI,KAAK,mBAAW,CAAC,8BAA8B,EAAE,CAAC;gBACtD,OAAO,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;YACjE,CAAC;YACD,OAAO,KAAK,CAAC;QACjB,CAAC;QACD,OAAO,EAAE,CAAC;IACd,CAAC;CAEJ;AAzFD,0CAyFC"}
|
||||||
364
build/http/station.d.ts
vendored
Normal file
364
build/http/station.d.ts
vendored
Normal file
@ -0,0 +1,364 @@
|
|||||||
|
import { TypedEmitter } from "tiny-typed-emitter";
|
||||||
|
import { HTTPApi } from "./api";
|
||||||
|
import { AlarmTone, NotificationSwitchMode, DeviceType, FloodlightMotionTriggeredDistance, GuardMode, NotificationType, PowerSource, PropertyName, TimeFormat, CommandName, VideoTypeStoreToNAS, HB3DetectionTypes, WalllightNotificationType, DailyLightingType, MotionActivationMode, LightingActiveMode, SourceType, T8170DetectionTypes, IndoorS350NotificationTypes, SoloCameraDetectionTypes, MotionDetectionRangeType, ViewModeType, FloodlightT8425NotificationTypes, PresetPositionType, IndoorS350DetectionTypes } from "./types";
|
||||||
|
import { SnoozeDetail, StationListResponse } from "./models";
|
||||||
|
import { IndexedProperty, PropertyMetadataAny, PropertyValue, PropertyValues, RawValues, StationEvents, Schedule } from "./interfaces";
|
||||||
|
import { CrossTrackingGroupEntry, DynamicLighting, MotionZone, RGBColor } from "../p2p/interfaces";
|
||||||
|
import { CalibrateGarageType, FilterDetectType, FilterEventType, FilterStorageType, P2PConnectionType, PanTiltDirection, VideoCodec, WatermarkSetting1, WatermarkSetting2, WatermarkSetting3, WatermarkSetting4, WatermarkSetting5 } from "../p2p/types";
|
||||||
|
import { Device } from "./device";
|
||||||
|
import { PushMessage } from "../push/models";
|
||||||
|
export declare class Station extends TypedEmitter<StationEvents> {
|
||||||
|
private api;
|
||||||
|
private rawStation;
|
||||||
|
private p2pSession;
|
||||||
|
private properties;
|
||||||
|
private rawProperties;
|
||||||
|
private ready;
|
||||||
|
private lockPublicKey;
|
||||||
|
private currentDelay;
|
||||||
|
private reconnectTimeout?;
|
||||||
|
private terminating;
|
||||||
|
private p2pConnectionType;
|
||||||
|
static readonly CHANNEL: number;
|
||||||
|
static readonly CHANNEL_INDOOR: number;
|
||||||
|
private pinVerified;
|
||||||
|
protected constructor(api: HTTPApi, station: StationListResponse, ipAddress?: string, listeningPort?: number, publicKey?: string, enableEmbeddedPKCS1Support?: boolean);
|
||||||
|
protected initializeState(): void;
|
||||||
|
initialize(): void;
|
||||||
|
static getInstance(api: HTTPApi, stationData: StationListResponse, ipAddress?: string, listeningPort?: number, enableEmbeddedPKCS1Support?: boolean): Promise<Station>;
|
||||||
|
getStateID(state: string, level?: number): string;
|
||||||
|
getStateChannel(): string;
|
||||||
|
getRawStation(): StationListResponse;
|
||||||
|
update(station: StationListResponse): void;
|
||||||
|
updateProperty(name: string, value: PropertyValue, force?: boolean): boolean;
|
||||||
|
updateRawProperties(values: RawValues): void;
|
||||||
|
protected handlePropertyChange(metadata: PropertyMetadataAny, oldValue: PropertyValue, newValue: PropertyValue): void;
|
||||||
|
updateRawProperty(type: number, value: string, source: SourceType): boolean;
|
||||||
|
protected convertRawPropertyValue(property: PropertyMetadataAny, value: string): PropertyValue;
|
||||||
|
getPropertyMetadata(name: string, hidden?: boolean): PropertyMetadataAny;
|
||||||
|
getPropertyValue(name: string): PropertyValue;
|
||||||
|
hasPropertyValue(name: string): boolean;
|
||||||
|
getRawProperty(type: number): string | undefined;
|
||||||
|
getRawProperties(): RawValues;
|
||||||
|
getProperties(): PropertyValues;
|
||||||
|
getPropertiesMetadata(hidden?: boolean): IndexedProperty;
|
||||||
|
hasProperty(name: string, hidden?: boolean): boolean;
|
||||||
|
getCommands(): Array<CommandName>;
|
||||||
|
hasCommand(name: CommandName): boolean;
|
||||||
|
static getChannel(type: number): number;
|
||||||
|
static isStation(type: number): boolean;
|
||||||
|
isStation(): boolean;
|
||||||
|
static isStationHomeBase3(type: number): boolean;
|
||||||
|
static isStationHomeBase3BySn(sn: string): boolean;
|
||||||
|
isStationHomeBase3(): boolean;
|
||||||
|
isIntegratedDevice(): boolean;
|
||||||
|
isP2PConnectableDevice(): boolean;
|
||||||
|
getDeviceType(): number;
|
||||||
|
getHardwareVersion(): string;
|
||||||
|
getMACAddress(): string;
|
||||||
|
getModel(): string;
|
||||||
|
getName(): string;
|
||||||
|
getSerial(): string;
|
||||||
|
getSoftwareVersion(): string;
|
||||||
|
getIPAddress(): string;
|
||||||
|
getLANIPAddress(): PropertyValue;
|
||||||
|
getGuardMode(): PropertyValue;
|
||||||
|
getCurrentMode(): PropertyValue;
|
||||||
|
processPushNotification(message: PushMessage): void;
|
||||||
|
isConnected(): boolean;
|
||||||
|
close(): void;
|
||||||
|
isEnergySavingDevice(): boolean;
|
||||||
|
connect(): Promise<void>;
|
||||||
|
private onFinishDownload;
|
||||||
|
private onStartDownload;
|
||||||
|
private onStopLivestream;
|
||||||
|
private onErrorLivestream;
|
||||||
|
private onStartLivestream;
|
||||||
|
private onStopRTSPLivestream;
|
||||||
|
private onStartRTSPLivestream;
|
||||||
|
private onWifiRssiChanged;
|
||||||
|
private onRTSPUrl;
|
||||||
|
private onParameter;
|
||||||
|
private onAlarmDelay;
|
||||||
|
private onAlarmArmed;
|
||||||
|
private onAlarmEvent;
|
||||||
|
setGuardMode(mode: GuardMode): void;
|
||||||
|
getCameraInfo(): void;
|
||||||
|
getStorageInfoEx(): void;
|
||||||
|
private onAlarmMode;
|
||||||
|
private getArmDelay;
|
||||||
|
private _getDeviceSerial;
|
||||||
|
private _handleCameraInfoParameters;
|
||||||
|
private onCameraInfo;
|
||||||
|
private onCommandResponse;
|
||||||
|
private onSecondaryCommandResponse;
|
||||||
|
private onConnect;
|
||||||
|
private onDisconnect;
|
||||||
|
private onTimeout;
|
||||||
|
private getCurrentDelay;
|
||||||
|
private resetCurrentDelay;
|
||||||
|
private scheduleReconnect;
|
||||||
|
rebootHUB(): void;
|
||||||
|
setStatusLed(device: Device, value: boolean): void;
|
||||||
|
setAutoNightVision(device: Device, value: boolean): void;
|
||||||
|
setNightVision(device: Device, value: number): void;
|
||||||
|
setMotionDetection(device: Device, value: boolean): void;
|
||||||
|
setSoundDetection(device: Device, value: boolean): void;
|
||||||
|
setSoundDetectionType(device: Device, value: number): void;
|
||||||
|
setSoundDetectionSensitivity(device: Device, value: number): void;
|
||||||
|
setPetDetection(device: Device, value: boolean): void;
|
||||||
|
panAndTilt(device: Device, direction: PanTiltDirection, command?: number): void;
|
||||||
|
switchLight(device: Device, value: boolean): void;
|
||||||
|
setMotionDetectionSensitivity(device: Device, value: number): void;
|
||||||
|
setMotionDetectionType(device: Device, value: number): void;
|
||||||
|
setMotionDetectionTypeHB3(device: Device, type: HB3DetectionTypes | T8170DetectionTypes | SoloCameraDetectionTypes | IndoorS350DetectionTypes, value: boolean): void;
|
||||||
|
setMotionZone(device: Device, value: MotionZone): void;
|
||||||
|
setMotionTracking(device: Device, value: boolean): void;
|
||||||
|
setPanAndTiltRotationSpeed(device: Device, value: number): void;
|
||||||
|
setMicMute(device: Device, value: boolean): void;
|
||||||
|
setAudioRecording(device: Device, value: boolean): void;
|
||||||
|
enableSpeaker(device: Device, value: boolean): void;
|
||||||
|
setSpeakerVolume(device: Device, value: number): void;
|
||||||
|
setRingtoneVolume(device: Device, value: number): void;
|
||||||
|
enableIndoorChime(device: Device, value: boolean): void;
|
||||||
|
enableHomebaseChime(device: Device, value: boolean): void;
|
||||||
|
setHomebaseChimeRingtoneVolume(device: Device, value: number): void;
|
||||||
|
setHomebaseChimeRingtoneType(device: Device, value: number): void;
|
||||||
|
setNotificationType(device: Device, value: NotificationType | WalllightNotificationType): void;
|
||||||
|
setNotificationPerson(device: Device, value: boolean): void;
|
||||||
|
setNotificationPet(device: Device, value: boolean): void;
|
||||||
|
setNotificationAllOtherMotion(device: Device, value: boolean): void;
|
||||||
|
setNotificationAllSound(device: Device, value: boolean): void;
|
||||||
|
setNotificationCrying(device: Device, value: boolean): void;
|
||||||
|
setNotificationRing(device: Device, value: boolean): void;
|
||||||
|
setNotificationMotion(device: Device, value: boolean): void;
|
||||||
|
setPowerSource(device: Device, value: PowerSource): void;
|
||||||
|
setPowerWorkingMode(device: Device, value: number): void;
|
||||||
|
setRecordingClipLength(device: Device, value: number): void;
|
||||||
|
setRecordingRetriggerInterval(device: Device, value: number): void;
|
||||||
|
setRecordingEndClipMotionStops(device: Device, value: boolean): void;
|
||||||
|
setVideoStreamingQuality(device: Device, value: number): void;
|
||||||
|
setVideoRecordingQuality(device: Device, value: number): void;
|
||||||
|
setWDR(device: Device, value: boolean): void;
|
||||||
|
setFloodlightLightSettingsEnable(device: Device, value: boolean): void;
|
||||||
|
setFloodlightLightSettingsBrightnessManual(device: Device, value: number): void;
|
||||||
|
setFloodlightLightSettingsBrightnessMotion(device: Device, value: number): void;
|
||||||
|
setFloodlightLightSettingsBrightnessSchedule(device: Device, value: number): void;
|
||||||
|
setFloodlightLightSettingsMotionTriggered(device: Device, value: boolean): void;
|
||||||
|
setFloodlightLightSettingsMotionTriggeredDistance(device: Device, value: FloodlightMotionTriggeredDistance): void;
|
||||||
|
setFloodlightLightSettingsMotionTriggeredTimer(device: Device, seconds: number): void;
|
||||||
|
triggerStationAlarmSound(seconds: number): void;
|
||||||
|
resetStationAlarmSound(): void;
|
||||||
|
triggerDeviceAlarmSound(device: Device, seconds: number): void;
|
||||||
|
resetDeviceAlarmSound(device: Device): void;
|
||||||
|
setStationAlarmRingtoneVolume(value: number): void;
|
||||||
|
setStationAlarmTone(value: AlarmTone): void;
|
||||||
|
setStationPromptVolume(value: number): void;
|
||||||
|
setStationNotificationSwitchMode(mode: NotificationSwitchMode, value: boolean): void;
|
||||||
|
setStationNotificationStartAlarmDelay(value: boolean): void;
|
||||||
|
setStationTimeFormat(value: TimeFormat): void;
|
||||||
|
setRTSPStream(device: Device, value: boolean): void;
|
||||||
|
setAntiTheftDetection(device: Device, value: boolean): void;
|
||||||
|
setWatermark(device: Device, value: WatermarkSetting1 | WatermarkSetting2 | WatermarkSetting3 | WatermarkSetting4 | WatermarkSetting5): void;
|
||||||
|
enableDevice(device: Device, value: boolean): void;
|
||||||
|
startDownload(device: Device, path: string, cipher_id?: number): Promise<void>;
|
||||||
|
cancelDownload(device: Device): void;
|
||||||
|
startLivestream(device: Device, videoCodec?: VideoCodec): void;
|
||||||
|
stopLivestream(device: Device): void;
|
||||||
|
isLiveStreaming(device: Device): boolean;
|
||||||
|
isDownloading(device: Device): boolean;
|
||||||
|
quickResponse(device: Device, voice_id: number): void;
|
||||||
|
setChirpVolume(device: Device, value: number): void;
|
||||||
|
setChirpTone(device: Device, value: number): void;
|
||||||
|
setHDR(device: Device, value: boolean): void;
|
||||||
|
setDistortionCorrection(device: Device, value: boolean): void;
|
||||||
|
setRingRecord(device: Device, value: number): void;
|
||||||
|
lockDevice(device: Device, value: boolean): void;
|
||||||
|
setStationSwitchModeWithAccessCode(value: boolean): void;
|
||||||
|
setStationAutoEndAlarm(value: boolean): void;
|
||||||
|
setStationTurnOffAlarmWithButton(value: boolean): void;
|
||||||
|
startRTSPStream(device: Device): void;
|
||||||
|
stopRTSPStream(device: Device): void;
|
||||||
|
setMotionDetectionRange(device: Device, type: MotionDetectionRangeType): void;
|
||||||
|
setMotionDetectionRangeStandardSensitivity(device: Device, sensitivity: number): void;
|
||||||
|
setMotionDetectionRangeAdvancedLeftSensitivity(device: Device, sensitivity: number): void;
|
||||||
|
setMotionDetectionRangeAdvancedMiddleSensitivity(device: Device, sensitivity: number): void;
|
||||||
|
setMotionDetectionRangeAdvancedRightSensitivity(device: Device, sensitivity: number): void;
|
||||||
|
setMotionDetectionTestMode(device: Device, enabled: boolean): void;
|
||||||
|
setMotionTrackingSensitivity(device: Device, sensitivity: number): void;
|
||||||
|
setMotionAutoCruise(device: Device, enabled: boolean): void;
|
||||||
|
setMotionOutOfViewDetection(device: Device, enabled: boolean): void;
|
||||||
|
setLightSettingsColorTemperatureManual(device: Device, value: number): void;
|
||||||
|
setLightSettingsColorTemperatureMotion(device: Device, value: number): void;
|
||||||
|
setLightSettingsColorTemperatureSchedule(device: Device, value: number): void;
|
||||||
|
setLightSettingsMotionActivationMode(device: Device, value: MotionActivationMode): void;
|
||||||
|
setVideoNightvisionImageAdjustment(device: Device, enabled: boolean): void;
|
||||||
|
setVideoColorNightvision(device: Device, enabled: boolean): void;
|
||||||
|
setAutoCalibration(device: Device, enabled: boolean): void;
|
||||||
|
isRTSPLiveStreaming(device: Device): boolean;
|
||||||
|
setConnectionType(type: P2PConnectionType): void;
|
||||||
|
getConnectionType(): P2PConnectionType;
|
||||||
|
private onRuntimeState;
|
||||||
|
private onChargingState;
|
||||||
|
hasDevice(deviceSN: string): boolean;
|
||||||
|
hasDeviceWithType(deviceType: DeviceType): boolean;
|
||||||
|
private onFloodlightManualSwitch;
|
||||||
|
calibrateLock(device: Device): void;
|
||||||
|
private convertAdvancedLockSettingValue;
|
||||||
|
private convertAdvancedLockSettingValueT8530;
|
||||||
|
private getAdvancedLockSettingsPayload;
|
||||||
|
private getAdvancedLockSettingsPayloadT8530;
|
||||||
|
private getAdvancedLockSettingName;
|
||||||
|
private getAdvancedLockSettingNameT8530;
|
||||||
|
setAdvancedLockParams(device: Device, property: PropertyName, value: PropertyValue): void;
|
||||||
|
setLoiteringDetection(device: Device, value: boolean): void;
|
||||||
|
setLoiteringDetectionRange(device: Device, value: number): void;
|
||||||
|
setLoiteringDetectionLength(device: Device, value: number): void;
|
||||||
|
private _setMotionDetectionSensitivity;
|
||||||
|
private _getMotionDetectionSensitivityAdvanced;
|
||||||
|
setMotionDetectionSensitivityMode(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityStandard(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityAdvancedA(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityAdvancedB(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityAdvancedC(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityAdvancedD(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityAdvancedE(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityAdvancedF(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityAdvancedG(device: Device, value: number): void;
|
||||||
|
setMotionDetectionSensitivityAdvancedH(device: Device, value: number): void;
|
||||||
|
private _setLoiteringCustomResponse;
|
||||||
|
setLoiteringCustomResponseAutoVoiceResponse(device: Device, value: boolean): void;
|
||||||
|
setLoiteringCustomResponseAutoVoiceResponseVoice(device: Device, value: number): void;
|
||||||
|
setLoiteringCustomResponseHomeBaseNotification(device: Device, value: boolean): void;
|
||||||
|
setLoiteringCustomResponsePhoneNotification(device: Device, value: boolean): void;
|
||||||
|
setLoiteringCustomResponseTimeFrom(device: Device, value: string): void;
|
||||||
|
setLoiteringCustomResponseTimeTo(device: Device, value: string): void;
|
||||||
|
setDeliveryGuard(device: Device, value: boolean): void;
|
||||||
|
setDeliveryGuardPackageGuarding(device: Device, value: boolean): void;
|
||||||
|
setDeliveryGuardPackageGuardingVoiceResponseVoice(device: Device, value: number): void;
|
||||||
|
private setDeliveryGuardPackageGuardingActivatedTime;
|
||||||
|
setDeliveryGuardPackageGuardingActivatedTimeFrom(device: Device, value: string): void;
|
||||||
|
setDeliveryGuardPackageGuardingActivatedTimeTo(device: Device, value: string): void;
|
||||||
|
setDeliveryGuardUncollectedPackageAlert(device: Device, value: boolean): void;
|
||||||
|
setDeliveryGuardUncollectedPackageAlertTimeToCheck(device: Device, value: string): void;
|
||||||
|
setDeliveryGuardPackageLiveCheckAssistance(device: Device, value: boolean): void;
|
||||||
|
setDualCamWatchViewMode(device: Device, value: ViewModeType): void;
|
||||||
|
private _setRingAutoResponse;
|
||||||
|
setRingAutoResponse(device: Device, value: boolean): void;
|
||||||
|
setRingAutoResponseVoiceResponse(device: Device, value: boolean): void;
|
||||||
|
setRingAutoResponseVoiceResponseVoice(device: Device, value: number): void;
|
||||||
|
setRingAutoResponseTimeFrom(device: Device, value: string): void;
|
||||||
|
setRingAutoResponseTimeTo(device: Device, value: string): void;
|
||||||
|
setNotificationRadarDetector(device: Device, value: boolean): void;
|
||||||
|
calibrate(device: Device): void;
|
||||||
|
setContinuousRecording(device: Device, value: boolean): void;
|
||||||
|
setContinuousRecordingType(device: Device, value: number): void;
|
||||||
|
enableDefaultAngle(device: Device, value: boolean): void;
|
||||||
|
setDefaultAngleIdleTime(device: Device, value: number): void;
|
||||||
|
setDefaultAngle(device: Device): void;
|
||||||
|
setPrivacyAngle(device: Device): void;
|
||||||
|
setNotificationIntervalTime(device: Device, value: number): void;
|
||||||
|
setSoundDetectionRoundLook(device: Device, value: boolean): void;
|
||||||
|
startTalkback(device: Device): void;
|
||||||
|
stopTalkback(device: Device): void;
|
||||||
|
private onTalkbackStarted;
|
||||||
|
private onTalkbackStopped;
|
||||||
|
private onTalkbackError;
|
||||||
|
isTalkbackOngoing(device: Device): boolean;
|
||||||
|
setScramblePasscode(device: Device, value: boolean): void;
|
||||||
|
setWrongTryProtection(device: Device, value: boolean): void;
|
||||||
|
setWrongTryAttempts(device: Device, value: number): void;
|
||||||
|
setWrongTryLockdownTime(device: Device, value: number): void;
|
||||||
|
private _sendSmartSafeCommand;
|
||||||
|
setSmartSafeParams(device: Device, property: PropertyName, value: PropertyValue): void;
|
||||||
|
unlock(device: Device): void;
|
||||||
|
verifyPIN(device: Device, pin: string): void;
|
||||||
|
private onDeviceShakeAlarm;
|
||||||
|
private onDevice911Alarm;
|
||||||
|
private onDeviceJammed;
|
||||||
|
private onDeviceLowBattery;
|
||||||
|
private onDeviceWrongTryProtectAlarm;
|
||||||
|
private onSdInfoEx;
|
||||||
|
setVideoTypeStoreToNAS(device: Device, value: VideoTypeStoreToNAS): void;
|
||||||
|
snooze(device: Device, value: SnoozeDetail): void;
|
||||||
|
addUser(device: Device, username: string, shortUserId: string, passcode: string, schedule?: Schedule): void;
|
||||||
|
deleteUser(device: Device, username: string, shortUserId: string): void;
|
||||||
|
updateUserSchedule(device: Device, username: string, shortUserId: string, schedule: Schedule): void;
|
||||||
|
updateUserPasscode(device: Device, username: string, passwordId: string, passcode: string): void;
|
||||||
|
setLockV12Params(device: Device, property: PropertyName, value: PropertyValue): void;
|
||||||
|
setSmartLockParams(device: Device, property: PropertyName, value: PropertyValue): void;
|
||||||
|
setAutoLock(device: Device, value: boolean): void;
|
||||||
|
setAutoLockSchedule(device: Device, value: boolean): void;
|
||||||
|
setAutoLockScheduleStartTime(device: Device, value: string): void;
|
||||||
|
setAutoLockScheduleEndTime(device: Device, value: string): void;
|
||||||
|
setAutoLockTimer(device: Device, value: number): void;
|
||||||
|
setOneTouchLocking(device: Device, value: boolean): void;
|
||||||
|
setSound(device: Device, value: number): void;
|
||||||
|
setNotification(device: Device, value: boolean): void;
|
||||||
|
setNotificationLocked(device: Device, value: boolean): void;
|
||||||
|
setNotificationUnlocked(device: Device, value: boolean): void;
|
||||||
|
private _sendLockV12P2PCommand;
|
||||||
|
queryAllUserId(device: Device): void;
|
||||||
|
chimeHomebase(value: number): void;
|
||||||
|
private onImageDownload;
|
||||||
|
downloadImage(cover_path: string): void;
|
||||||
|
private onTFCardStatus;
|
||||||
|
databaseQueryLatestInfo(failureCallback?: () => void): void;
|
||||||
|
databaseQueryLocal(serialNumbers: Array<string>, startDate: Date, endDate: Date, eventType?: FilterEventType, detectionType?: FilterDetectType, storageType?: FilterStorageType): void;
|
||||||
|
databaseDelete(ids: Array<number>): void;
|
||||||
|
databaseCountByDate(startDate: Date, endDate: Date): void;
|
||||||
|
private onDatabaseQueryLatest;
|
||||||
|
private onDatabaseQueryLocal;
|
||||||
|
private onDatabaseCountByDate;
|
||||||
|
private onDatabaseDelete;
|
||||||
|
private onSensorStatus;
|
||||||
|
setMotionDetectionTypeHuman(device: Device, value: boolean): void;
|
||||||
|
setMotionDetectionTypeAllOtherMotions(device: Device, value: boolean): void;
|
||||||
|
private _setLightSettingsLightingActiveMode;
|
||||||
|
setLightSettingsManualLightingActiveMode(device: Device, value: LightingActiveMode): void;
|
||||||
|
setLightSettingsManualDailyLighting(device: Device, value: DailyLightingType): void;
|
||||||
|
setLightSettingsManualColoredLighting(device: Device, value: RGBColor): void;
|
||||||
|
setLightSettingsManualDynamicLighting(device: Device, value: number): void;
|
||||||
|
setLightSettingsMotionLightingActiveMode(device: Device, value: LightingActiveMode): void;
|
||||||
|
setLightSettingsMotionDailyLighting(device: Device, value: DailyLightingType): void;
|
||||||
|
setLightSettingsMotionColoredLighting(device: Device, value: RGBColor): void;
|
||||||
|
setLightSettingsMotionDynamicLighting(device: Device, value: number): void;
|
||||||
|
setLightSettingsScheduleLightingActiveMode(device: Device, value: LightingActiveMode): void;
|
||||||
|
setLightSettingsScheduleDailyLighting(device: Device, value: DailyLightingType): void;
|
||||||
|
setLightSettingsScheduleColoredLighting(device: Device, value: RGBColor): void;
|
||||||
|
setLightSettingsScheduleDynamicLighting(device: Device, value: number): void;
|
||||||
|
setLightSettingsColoredLightingColors(device: Device, value: Array<RGBColor>): void;
|
||||||
|
setLightSettingsDynamicLightingThemes(device: Device, value: Array<DynamicLighting>): void;
|
||||||
|
setDoorControlWarning(device: Device, value: boolean): void;
|
||||||
|
openDoor(device: Device, value: boolean, doorId?: number): void;
|
||||||
|
private onGarageDoorStatus;
|
||||||
|
calibrateGarageDoor(device: Device, doorId: number, type: CalibrateGarageType): void;
|
||||||
|
private onStorageInfoHB3;
|
||||||
|
setMirrorMode(device: Device, value: boolean): void;
|
||||||
|
setFlickerAdjustment(device: Device, value: number): void;
|
||||||
|
setCrossCameraTracking(value: boolean): void;
|
||||||
|
setContinuousTrackingTime(value: number): void;
|
||||||
|
setTrackingAssistance(value: boolean): void;
|
||||||
|
setCrossTrackingCameraList(value: Array<string>): void;
|
||||||
|
setCrossTrackingGroupList(value: Array<CrossTrackingGroupEntry>): void;
|
||||||
|
setNotificationIndoor(device: Device, type: IndoorS350NotificationTypes, value: boolean): void;
|
||||||
|
setNotificationFloodlightT8425(device: Device, type: FloodlightT8425NotificationTypes, value: boolean): void;
|
||||||
|
presetPosition(device: Device, position: PresetPositionType): void;
|
||||||
|
savePresetPosition(device: Device, position: PresetPositionType): void;
|
||||||
|
deletePresetPosition(device: Device, position: PresetPositionType): void;
|
||||||
|
setLeavingDetection(device: Device, value: boolean): void;
|
||||||
|
private _setLeavingReactions;
|
||||||
|
setLeavingReactionNotification(device: Device, value: boolean): void;
|
||||||
|
setLeavingReactionStartTime(device: Device, value: string): void;
|
||||||
|
setLeavingReactionEndTime(device: Device, value: string): void;
|
||||||
|
setBeepVolume(device: Device, value: number): void;
|
||||||
|
setNightvisionOptimization(device: Device, value: boolean): void;
|
||||||
|
setNightvisionOptimizationSide(device: Device, value: number): void;
|
||||||
|
getLockParameters(): void;
|
||||||
|
getLockStatus(): void;
|
||||||
|
private onSequenceError;
|
||||||
|
updateUsername(device: Device, username: string, passwordId: string): void;
|
||||||
|
setOpenMethod(device: Device, value: number): void;
|
||||||
|
setMotionActivatedPrompt(device: Device, value: boolean): void;
|
||||||
|
open(device: Device): void;
|
||||||
|
}
|
||||||
10561
build/http/station.js
Normal file
10561
build/http/station.js
Normal file
File diff suppressed because it is too large
Load Diff
1
build/http/station.js.map
Normal file
1
build/http/station.js.map
Normal file
File diff suppressed because one or more lines are too long
1333
build/http/types.d.ts
vendored
Normal file
1333
build/http/types.d.ts
vendored
Normal file
File diff suppressed because it is too large
Load Diff
9684
build/http/types.js
Normal file
9684
build/http/types.js
Normal file
File diff suppressed because it is too large
Load Diff
1
build/http/types.js.map
Normal file
1
build/http/types.js.map
Normal file
File diff suppressed because one or more lines are too long
79
build/http/utils.d.ts
vendored
Normal file
79
build/http/utils.d.ts
vendored
Normal file
@ -0,0 +1,79 @@
|
|||||||
|
import { Device } from "./device";
|
||||||
|
import { Picture, Schedule } from "./interfaces";
|
||||||
|
import { NotificationSwitchMode, SignalLevel, HB3DetectionTypes, SourceType, T8170DetectionTypes, IndoorS350NotificationTypes, FloodlightT8425NotificationTypes, SmartLockNotification, IndoorS350DetectionTypes } from "./types";
|
||||||
|
import { HTTPApi } from "./api";
|
||||||
|
import { LockPushEvent } from "./../push/types";
|
||||||
|
import { Station } from "./station";
|
||||||
|
import { PushMessage } from "../push/models";
|
||||||
|
export declare const isGreaterEqualMinVersion: (minimal_version: string, current_version: string) => boolean;
|
||||||
|
export declare const pad: (num: number) => string;
|
||||||
|
export declare const getTimezoneGMTString: () => string;
|
||||||
|
export declare const getAbsoluteFilePath: (device_type: number, channel: number, filename: string) => string;
|
||||||
|
export declare const getImageFilePath: (device_type: number, channel: number, filename: string) => string;
|
||||||
|
export declare const isNotificationSwitchMode: (value: number, mode: NotificationSwitchMode) => boolean;
|
||||||
|
export declare const switchNotificationMode: (currentValue: number, mode: NotificationSwitchMode, enable: boolean) => number;
|
||||||
|
export declare const calculateWifiSignalLevel: (device: Device, rssi: number) => SignalLevel;
|
||||||
|
export declare const calculateCellularSignalLevel: (rssi: number) => SignalLevel;
|
||||||
|
export declare const encryptAPIData: (data: string, key: Buffer) => string;
|
||||||
|
export declare const decryptAPIData: (data: string, key: Buffer) => Buffer;
|
||||||
|
export declare const getBlocklist: (directions: Array<number>) => Array<number>;
|
||||||
|
export declare const getDistances: (blocklist: Array<number>) => Array<number>;
|
||||||
|
export declare const isHB3DetectionModeEnabled: (value: number, type: HB3DetectionTypes) => boolean;
|
||||||
|
export declare const getHB3DetectionMode: (value: number, type: HB3DetectionTypes, enable: boolean) => number;
|
||||||
|
export interface EufyTimezone {
|
||||||
|
timeZoneName: string;
|
||||||
|
timeId: string;
|
||||||
|
timeSn: string;
|
||||||
|
timeZoneGMT: string;
|
||||||
|
}
|
||||||
|
export declare const getEufyTimezone: () => EufyTimezone | undefined;
|
||||||
|
export declare const getAdvancedLockTimezone: (stationSN: string) => string;
|
||||||
|
export declare class WritePayload {
|
||||||
|
private split_byte;
|
||||||
|
private data;
|
||||||
|
write(bytes: Buffer): void;
|
||||||
|
getData(): Buffer;
|
||||||
|
}
|
||||||
|
export declare class ParsePayload {
|
||||||
|
private data;
|
||||||
|
constructor(data: Buffer);
|
||||||
|
readUint32BE(indexValue: number): number;
|
||||||
|
readUint32LE(indexValue: number): number;
|
||||||
|
readUint16BE(indexValue: number): number;
|
||||||
|
readUint16LE(indexValue: number): number;
|
||||||
|
readString(indexValue: number): string;
|
||||||
|
readStringHex(indexValue: number): string;
|
||||||
|
readInt8(indexValue: number): number;
|
||||||
|
readData(indexValue: number): Buffer;
|
||||||
|
private getDataPosition;
|
||||||
|
private getNextStep;
|
||||||
|
}
|
||||||
|
export declare const encodePasscode: (pass: string) => string;
|
||||||
|
export declare const hexDate: (date: Date) => string;
|
||||||
|
export declare const hexTime: (date: Date) => string;
|
||||||
|
export declare const hexWeek: (schedule: Schedule) => string;
|
||||||
|
export declare const hexStringScheduleToSchedule: (startDay: string, startTime: string, endDay: string, endTime: string, week: string) => Schedule;
|
||||||
|
export declare const randomNumber: (min: number, max: number) => number;
|
||||||
|
export declare const getIdSuffix: (p2pDid: string) => number;
|
||||||
|
export declare const getImageBaseCode: (serialnumber: string, p2pDid: string) => string;
|
||||||
|
export declare const getImageSeed: (p2pDid: string, code: string) => string;
|
||||||
|
export declare const getImageKey: (serialnumber: string, p2pDid: string, code: string) => string;
|
||||||
|
export declare const decodeImage: (p2pDid: string, data: Buffer) => Buffer;
|
||||||
|
export declare const getImagePath: (path: string) => string;
|
||||||
|
export declare const getImage: (api: HTTPApi, serial: string, url: string) => Promise<Picture>;
|
||||||
|
export declare const isPrioritySourceType: (current: SourceType | undefined, update: SourceType) => boolean;
|
||||||
|
export declare const decryptTrackerData: (data: Buffer, key: Buffer) => Buffer;
|
||||||
|
export declare const isT8170DetectionModeEnabled: (value: number, type: T8170DetectionTypes) => boolean;
|
||||||
|
export declare const getT8170DetectionMode: (value: number, type: T8170DetectionTypes, enable: boolean) => number;
|
||||||
|
export declare const isIndoorS350DetectionModeEnabled: (value: number, type: IndoorS350DetectionTypes) => boolean;
|
||||||
|
export declare const getIndoorS350DetectionMode: (value: number, type: IndoorS350DetectionTypes, enable: boolean) => number;
|
||||||
|
export declare const isIndoorNotitficationEnabled: (value: number, type: IndoorS350NotificationTypes) => boolean;
|
||||||
|
export declare const getIndoorNotification: (value: number, type: IndoorS350NotificationTypes, enable: boolean) => number;
|
||||||
|
export declare const isFloodlightT8425NotitficationEnabled: (value: number, type: FloodlightT8425NotificationTypes) => boolean;
|
||||||
|
export declare const getFloodLightT8425Notification: (value: number, type: FloodlightT8425NotificationTypes, enable: boolean) => number;
|
||||||
|
export declare const getLockEventType: (event: LockPushEvent) => number;
|
||||||
|
export declare const switchSmartLockNotification: (currentValue: number, mode: SmartLockNotification, enable: boolean) => number;
|
||||||
|
export declare const isSmartLockNotification: (value: number, mode: SmartLockNotification) => boolean;
|
||||||
|
export declare const getWaitSeconds: (device: Device) => number;
|
||||||
|
export declare const loadImageOverP2P: (station: Station, device: Device, id: string, p2pTimeouts: Map<string, NodeJS.Timeout>) => void;
|
||||||
|
export declare const loadEventImage: (station: Station, api: HTTPApi, device: Device, message: PushMessage, p2pTimeouts: Map<string, NodeJS.Timeout>) => void;
|
||||||
789
build/http/utils.js
Normal file
789
build/http/utils.js
Normal file
@ -0,0 +1,789 @@
|
|||||||
|
"use strict";
|
||||||
|
var __importDefault = (this && this.__importDefault) || function (mod) {
|
||||||
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.loadEventImage = exports.loadImageOverP2P = exports.getWaitSeconds = exports.isSmartLockNotification = exports.switchSmartLockNotification = exports.getLockEventType = exports.getFloodLightT8425Notification = exports.isFloodlightT8425NotitficationEnabled = exports.getIndoorNotification = exports.isIndoorNotitficationEnabled = exports.getIndoorS350DetectionMode = exports.isIndoorS350DetectionModeEnabled = exports.getT8170DetectionMode = exports.isT8170DetectionModeEnabled = exports.decryptTrackerData = exports.isPrioritySourceType = exports.getImage = exports.getImagePath = exports.decodeImage = exports.getImageKey = exports.getImageSeed = exports.getImageBaseCode = exports.getIdSuffix = exports.randomNumber = exports.hexStringScheduleToSchedule = exports.hexWeek = exports.hexTime = exports.hexDate = exports.encodePasscode = exports.ParsePayload = exports.WritePayload = exports.getAdvancedLockTimezone = exports.getEufyTimezone = exports.getHB3DetectionMode = exports.isHB3DetectionModeEnabled = exports.getDistances = exports.getBlocklist = exports.decryptAPIData = exports.encryptAPIData = exports.calculateCellularSignalLevel = exports.calculateWifiSignalLevel = exports.switchNotificationMode = exports.isNotificationSwitchMode = exports.getImageFilePath = exports.getAbsoluteFilePath = exports.getTimezoneGMTString = exports.pad = exports.isGreaterEqualMinVersion = void 0;
|
||||||
|
const crypto_1 = require("crypto");
|
||||||
|
const const_1 = require("./const");
|
||||||
|
const md5_1 = __importDefault(require("crypto-js/md5"));
|
||||||
|
const enc_hex_1 = __importDefault(require("crypto-js/enc-hex"));
|
||||||
|
const sha256_1 = __importDefault(require("crypto-js/sha256"));
|
||||||
|
const types_1 = require("./types");
|
||||||
|
const error_1 = require("../error");
|
||||||
|
const error_2 = require("./error");
|
||||||
|
const types_2 = require("./../push/types");
|
||||||
|
const logging_1 = require("../logging");
|
||||||
|
const utils_1 = require("../utils");
|
||||||
|
const normalizeVersionString = function (version) {
|
||||||
|
const trimmed = version ? version.replace(/^\s*(\S*(\s+\S+)*)\s*$/, "$1") : "";
|
||||||
|
const pieces = trimmed.split(RegExp("\\."));
|
||||||
|
const parts = [];
|
||||||
|
let value, piece, num, i;
|
||||||
|
for (i = 0; i < pieces.length; i += 1) {
|
||||||
|
piece = pieces[i].replace(RegExp("\\D"), "");
|
||||||
|
num = parseInt(piece, 10);
|
||||||
|
if (isNaN(num)) {
|
||||||
|
num = 0;
|
||||||
|
}
|
||||||
|
parts.push(num);
|
||||||
|
}
|
||||||
|
const partsLength = parts.length;
|
||||||
|
for (i = partsLength - 1; i >= 0; i -= 1) {
|
||||||
|
value = parts[i];
|
||||||
|
if (value === 0) {
|
||||||
|
parts.length -= 1;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return parts;
|
||||||
|
};
|
||||||
|
const isGreaterEqualMinVersion = function (minimal_version, current_version) {
|
||||||
|
const x = normalizeVersionString(minimal_version);
|
||||||
|
const y = normalizeVersionString(current_version);
|
||||||
|
const size = Math.min(x.length, y.length);
|
||||||
|
let i;
|
||||||
|
for (i = 0; i < size; i += 1) {
|
||||||
|
if (x[i] !== y[i]) {
|
||||||
|
return x[i] < y[i] ? true : false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (x.length === y.length) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return (x.length < y.length) ? true : false;
|
||||||
|
};
|
||||||
|
exports.isGreaterEqualMinVersion = isGreaterEqualMinVersion;
|
||||||
|
const pad = function (num) {
|
||||||
|
const norm = Math.floor(Math.abs(num));
|
||||||
|
return (norm < 10 ? "0" : "") + norm;
|
||||||
|
};
|
||||||
|
exports.pad = pad;
|
||||||
|
const getTimezoneGMTString = function () {
|
||||||
|
const tzo = -new Date().getTimezoneOffset();
|
||||||
|
const dif = tzo >= 0 ? "+" : "-";
|
||||||
|
return `GMT${dif}${(0, exports.pad)(tzo / 60)}:${(0, exports.pad)(tzo % 60)}`;
|
||||||
|
};
|
||||||
|
exports.getTimezoneGMTString = getTimezoneGMTString;
|
||||||
|
const getAbsoluteFilePath = function (device_type, channel, filename) {
|
||||||
|
if (device_type === types_1.DeviceType.FLOODLIGHT) {
|
||||||
|
return `/mnt/data/Camera${String(channel).padStart(2, "0")}/${filename}.dat`;
|
||||||
|
}
|
||||||
|
return `/media/mmcblk0p1/Camera${String(channel).padStart(2, "0")}/${filename}.dat`;
|
||||||
|
};
|
||||||
|
exports.getAbsoluteFilePath = getAbsoluteFilePath;
|
||||||
|
const getImageFilePath = function (device_type, channel, filename) {
|
||||||
|
if (device_type === types_1.DeviceType.FLOODLIGHT) {
|
||||||
|
return `/mnt/data/video/${filename}_c${String(channel).padStart(2, "0")}.jpg`;
|
||||||
|
}
|
||||||
|
return `/media/mmcblk0p1/video/${filename}_c${String(channel).padStart(2, "0")}.jpg`;
|
||||||
|
};
|
||||||
|
exports.getImageFilePath = getImageFilePath;
|
||||||
|
const isNotificationSwitchMode = function (value, mode) {
|
||||||
|
if (value === 1)
|
||||||
|
value = 240;
|
||||||
|
return (value & mode) !== 0;
|
||||||
|
};
|
||||||
|
exports.isNotificationSwitchMode = isNotificationSwitchMode;
|
||||||
|
const switchNotificationMode = function (currentValue, mode, enable) {
|
||||||
|
let result = 0;
|
||||||
|
if (!enable && currentValue === 1 /* ALL */) {
|
||||||
|
currentValue = 240;
|
||||||
|
}
|
||||||
|
if (enable) {
|
||||||
|
result = mode | currentValue;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = ~mode & currentValue;
|
||||||
|
}
|
||||||
|
if ((0, exports.isNotificationSwitchMode)(result, types_1.NotificationSwitchMode.SCHEDULE) && (0, exports.isNotificationSwitchMode)(result, types_1.NotificationSwitchMode.APP) && (0, exports.isNotificationSwitchMode)(result, types_1.NotificationSwitchMode.GEOFENCE) && (0, exports.isNotificationSwitchMode)(result, types_1.NotificationSwitchMode.KEYPAD)) {
|
||||||
|
result = 1; /* ALL */
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.switchNotificationMode = switchNotificationMode;
|
||||||
|
const calculateWifiSignalLevel = function (device, rssi) {
|
||||||
|
if (device.isWiredDoorbell()) {
|
||||||
|
if (rssi >= -65) {
|
||||||
|
return types_1.SignalLevel.FULL;
|
||||||
|
}
|
||||||
|
if (rssi >= -75) {
|
||||||
|
return types_1.SignalLevel.STRONG;
|
||||||
|
}
|
||||||
|
return rssi >= -80 ? types_1.SignalLevel.NORMAL : types_1.SignalLevel.WEAK;
|
||||||
|
}
|
||||||
|
else if (device.isCamera2Product()) {
|
||||||
|
if (rssi >= 0) {
|
||||||
|
return types_1.SignalLevel.NO_SIGNAL;
|
||||||
|
}
|
||||||
|
if (rssi >= -65) {
|
||||||
|
return types_1.SignalLevel.FULL;
|
||||||
|
}
|
||||||
|
if (rssi >= -75) {
|
||||||
|
return types_1.SignalLevel.STRONG;
|
||||||
|
}
|
||||||
|
return rssi >= -85 ? types_1.SignalLevel.NORMAL : types_1.SignalLevel.WEAK;
|
||||||
|
}
|
||||||
|
else if (device.isFloodLight()) {
|
||||||
|
if (rssi >= 0) {
|
||||||
|
return types_1.SignalLevel.NO_SIGNAL;
|
||||||
|
}
|
||||||
|
if (rssi >= -60) {
|
||||||
|
return types_1.SignalLevel.FULL;
|
||||||
|
}
|
||||||
|
if (rssi >= -70) {
|
||||||
|
return types_1.SignalLevel.STRONG;
|
||||||
|
}
|
||||||
|
return rssi >= -80 ? types_1.SignalLevel.NORMAL : types_1.SignalLevel.WEAK;
|
||||||
|
}
|
||||||
|
else if (device.isBatteryDoorbell()) {
|
||||||
|
if (rssi >= -65) {
|
||||||
|
return types_1.SignalLevel.FULL;
|
||||||
|
}
|
||||||
|
if (rssi >= -75) {
|
||||||
|
return types_1.SignalLevel.STRONG;
|
||||||
|
}
|
||||||
|
return rssi >= -85 ? types_1.SignalLevel.NORMAL : types_1.SignalLevel.WEAK;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (rssi >= 0) {
|
||||||
|
return types_1.SignalLevel.NO_SIGNAL;
|
||||||
|
}
|
||||||
|
if (rssi >= -65) {
|
||||||
|
return types_1.SignalLevel.FULL;
|
||||||
|
}
|
||||||
|
if (rssi >= -75) {
|
||||||
|
return types_1.SignalLevel.STRONG;
|
||||||
|
}
|
||||||
|
return rssi >= -85 ? types_1.SignalLevel.NORMAL : types_1.SignalLevel.WEAK;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
exports.calculateWifiSignalLevel = calculateWifiSignalLevel;
|
||||||
|
const calculateCellularSignalLevel = function (rssi) {
|
||||||
|
if (rssi >= 0) {
|
||||||
|
return types_1.SignalLevel.NO_SIGNAL;
|
||||||
|
}
|
||||||
|
if (rssi >= -90) {
|
||||||
|
return types_1.SignalLevel.FULL;
|
||||||
|
}
|
||||||
|
if (rssi >= -95) {
|
||||||
|
return types_1.SignalLevel.STRONG;
|
||||||
|
}
|
||||||
|
return rssi >= -105 ? types_1.SignalLevel.NORMAL : types_1.SignalLevel.WEAK;
|
||||||
|
};
|
||||||
|
exports.calculateCellularSignalLevel = calculateCellularSignalLevel;
|
||||||
|
const encryptAPIData = (data, key) => {
|
||||||
|
const cipher = (0, crypto_1.createCipheriv)("aes-256-cbc", key, key.subarray(0, 16));
|
||||||
|
return (cipher.update(data, "utf8", "base64") +
|
||||||
|
cipher.final("base64"));
|
||||||
|
};
|
||||||
|
exports.encryptAPIData = encryptAPIData;
|
||||||
|
const decryptAPIData = (data, key) => {
|
||||||
|
const cipher = (0, crypto_1.createDecipheriv)("aes-256-cbc", key, key.subarray(0, 16));
|
||||||
|
return Buffer.concat([
|
||||||
|
cipher.update(data, "base64"),
|
||||||
|
cipher.final()
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.decryptAPIData = decryptAPIData;
|
||||||
|
const getBlocklist = function (directions) {
|
||||||
|
const result = [];
|
||||||
|
for (let distance = 1; distance <= 5; distance++) {
|
||||||
|
let i = 0;
|
||||||
|
let j = 0;
|
||||||
|
let k = 1;
|
||||||
|
for (const directionDistance of directions) {
|
||||||
|
if (directionDistance >= distance) {
|
||||||
|
j += k;
|
||||||
|
}
|
||||||
|
k <<= 1;
|
||||||
|
}
|
||||||
|
if (j == 0) {
|
||||||
|
i = 65535;
|
||||||
|
}
|
||||||
|
else if (!(j == 255 || j == 65535)) {
|
||||||
|
i = (j ^ 255) + 65280;
|
||||||
|
}
|
||||||
|
result.push(65535 & i);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.getBlocklist = getBlocklist;
|
||||||
|
const getDistances = function (blocklist) {
|
||||||
|
const result = [3, 3, 3, 3, 3, 3, 3, 3];
|
||||||
|
let calcDistance = 0;
|
||||||
|
for (const blockElement of blocklist) {
|
||||||
|
let valueOf = blockElement ^ 65535;
|
||||||
|
calcDistance++;
|
||||||
|
if (valueOf !== 0) {
|
||||||
|
for (let i = 0; i < result.length; i++) {
|
||||||
|
const intValue = valueOf & 1;
|
||||||
|
if (intValue > 0) {
|
||||||
|
result[i] = calcDistance;
|
||||||
|
}
|
||||||
|
valueOf = valueOf >> 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.getDistances = getDistances;
|
||||||
|
const isHB3DetectionModeEnabled = function (value, type) {
|
||||||
|
if (type === types_1.HB3DetectionTypes.HUMAN_RECOGNITION) {
|
||||||
|
return (type & value) == type && (value & 65536) == 65536;
|
||||||
|
}
|
||||||
|
else if (type === types_1.HB3DetectionTypes.HUMAN_DETECTION) {
|
||||||
|
return (type & value) == type && (value & 1) == 1;
|
||||||
|
}
|
||||||
|
return (type & value) == type;
|
||||||
|
};
|
||||||
|
exports.isHB3DetectionModeEnabled = isHB3DetectionModeEnabled;
|
||||||
|
const getHB3DetectionMode = function (value, type, enable) {
|
||||||
|
let result = 0;
|
||||||
|
if (!enable) {
|
||||||
|
if (type === types_1.HB3DetectionTypes.HUMAN_RECOGNITION) {
|
||||||
|
const tmp = (type & value) == type ? type ^ value : value;
|
||||||
|
result = (value & 65536) == 65536 ? tmp ^ 65536 : tmp;
|
||||||
|
}
|
||||||
|
else if (type === types_1.HB3DetectionTypes.HUMAN_DETECTION) {
|
||||||
|
const tmp = (type & value) == type ? type ^ value : value;
|
||||||
|
result = (value & 1) == 1 ? tmp ^ 1 : tmp;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = type ^ value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (type === types_1.HB3DetectionTypes.HUMAN_RECOGNITION) {
|
||||||
|
result = type | value | 65536;
|
||||||
|
}
|
||||||
|
else if (type === types_1.HB3DetectionTypes.HUMAN_DETECTION) {
|
||||||
|
result = type | value | 1;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = type | value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.getHB3DetectionMode = getHB3DetectionMode;
|
||||||
|
const getEufyTimezone = function () {
|
||||||
|
for (const timezone of const_1.timeZoneData) {
|
||||||
|
if (timezone.timeId === Intl.DateTimeFormat().resolvedOptions().timeZone) {
|
||||||
|
return timezone;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return undefined;
|
||||||
|
};
|
||||||
|
exports.getEufyTimezone = getEufyTimezone;
|
||||||
|
const getAdvancedLockTimezone = function (stationSN) {
|
||||||
|
const timezone = (0, exports.getEufyTimezone)();
|
||||||
|
if (timezone !== undefined) {
|
||||||
|
if (stationSN.startsWith("T8520") && (0, exports.isGreaterEqualMinVersion)("1.2.8.6", stationSN))
|
||||||
|
return `${timezone.timeZoneGMT}|1.${timezone.timeSn}`;
|
||||||
|
else
|
||||||
|
return timezone.timeZoneGMT;
|
||||||
|
}
|
||||||
|
return "";
|
||||||
|
};
|
||||||
|
exports.getAdvancedLockTimezone = getAdvancedLockTimezone;
|
||||||
|
class WritePayload {
|
||||||
|
split_byte = -95;
|
||||||
|
data = Buffer.from([]);
|
||||||
|
write(bytes) {
|
||||||
|
const tmp_data = Buffer.from(bytes);
|
||||||
|
this.data = Buffer.concat([this.data, Buffer.from([this.split_byte]), Buffer.from([tmp_data.length & 255]), tmp_data]);
|
||||||
|
this.split_byte += 1;
|
||||||
|
}
|
||||||
|
getData() {
|
||||||
|
return this.data;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.WritePayload = WritePayload;
|
||||||
|
class ParsePayload {
|
||||||
|
data;
|
||||||
|
constructor(data) {
|
||||||
|
this.data = data;
|
||||||
|
}
|
||||||
|
readUint32BE(indexValue) {
|
||||||
|
return this.readData(indexValue).readUint32BE();
|
||||||
|
}
|
||||||
|
readUint32LE(indexValue) {
|
||||||
|
return this.readData(indexValue).readUint32LE();
|
||||||
|
}
|
||||||
|
readUint16BE(indexValue) {
|
||||||
|
return this.readData(indexValue).readUint16BE();
|
||||||
|
}
|
||||||
|
readUint16LE(indexValue) {
|
||||||
|
return this.readData(indexValue).readUint16LE();
|
||||||
|
}
|
||||||
|
readString(indexValue) {
|
||||||
|
return this.readData(indexValue).toString();
|
||||||
|
}
|
||||||
|
readStringHex(indexValue) {
|
||||||
|
return this.readData(indexValue).toString("hex");
|
||||||
|
}
|
||||||
|
readInt8(indexValue) {
|
||||||
|
let dataPosition = this.getDataPosition(indexValue);
|
||||||
|
if (dataPosition == -1) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
dataPosition = dataPosition + 2;
|
||||||
|
if (dataPosition >= this.data.length) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return this.data.readInt8(dataPosition);
|
||||||
|
}
|
||||||
|
readData(indexValue) {
|
||||||
|
let dataPosition = this.getDataPosition(indexValue);
|
||||||
|
if (dataPosition == -1) {
|
||||||
|
return Buffer.from("");
|
||||||
|
}
|
||||||
|
dataPosition++;
|
||||||
|
if (dataPosition >= this.data.length) {
|
||||||
|
return Buffer.from("");
|
||||||
|
}
|
||||||
|
const nextStep = this.getNextStep(indexValue, dataPosition, this.data);
|
||||||
|
let tmp;
|
||||||
|
if (nextStep == 1) {
|
||||||
|
tmp = this.data.readInt8(dataPosition);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
tmp = this.data.readUint16LE(dataPosition);
|
||||||
|
}
|
||||||
|
if (dataPosition + nextStep + tmp > this.data.length) {
|
||||||
|
return Buffer.from("");
|
||||||
|
}
|
||||||
|
return this.data.subarray(dataPosition + nextStep, dataPosition + nextStep + tmp);
|
||||||
|
}
|
||||||
|
getDataPosition(indexValue) {
|
||||||
|
if (this.data && this.data.length >= 1) {
|
||||||
|
for (let currentPosition = 0; currentPosition < this.data.length;) {
|
||||||
|
if (this.data.readInt8(currentPosition) == indexValue) {
|
||||||
|
return currentPosition;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
const value = this.data.readInt8(currentPosition);
|
||||||
|
currentPosition++;
|
||||||
|
if (currentPosition >= this.data.length) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
const nextStep = this.getNextStep(value, currentPosition, this.data);
|
||||||
|
if ((currentPosition + nextStep) >= this.data.length) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (nextStep == 1) {
|
||||||
|
currentPosition = this.data.readInt8(currentPosition) + currentPosition + nextStep;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
currentPosition = this.data.readUint16LE(currentPosition) + currentPosition + nextStep;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
getNextStep(indexValue, position, data) {
|
||||||
|
const newPosition = position + 1 + data.readUInt8(position);
|
||||||
|
return (newPosition == data.length || newPosition > data.length || data.readInt8(newPosition) == indexValue + 1) ? 1 : 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ParsePayload = ParsePayload;
|
||||||
|
/*export const generateHash = function(data: Buffer): number {
|
||||||
|
let result = 0;
|
||||||
|
for (const value of data) {
|
||||||
|
result = result ^ value;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const encodeSmartSafeData = function(command: number, payload: Buffer): Buffer {
|
||||||
|
const header = Buffer.from(SmartSafe.DATA_HEADER);
|
||||||
|
const size = Buffer.allocUnsafe(2);
|
||||||
|
size.writeInt16LE(payload.length + 9);
|
||||||
|
const versionCode = Buffer.from([SmartSafe.VERSION_CODE]);
|
||||||
|
const dataType = Buffer.from([-1]);
|
||||||
|
const commandCode = Buffer.from([command]);
|
||||||
|
const packageFlag = Buffer.from([-64]);
|
||||||
|
const data = Buffer.concat([header, size, versionCode, dataType, commandCode, packageFlag, payload]);
|
||||||
|
const hash = generateHash(data);
|
||||||
|
return Buffer.concat([data, Buffer.from([hash])]);
|
||||||
|
}*/
|
||||||
|
const encodePasscode = function (pass) {
|
||||||
|
let result = "";
|
||||||
|
for (let i = 0; i < pass.length; i++)
|
||||||
|
result += pass.charCodeAt(i).toString(16);
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.encodePasscode = encodePasscode;
|
||||||
|
const hexDate = function (date) {
|
||||||
|
const buf = Buffer.allocUnsafe(4);
|
||||||
|
buf.writeUint8(date.getDate());
|
||||||
|
buf.writeUint8(date.getMonth() + 1, 1);
|
||||||
|
buf.writeUint16BE(date.getFullYear(), 2);
|
||||||
|
return buf.readUInt32LE().toString(16).padStart(8, "0");
|
||||||
|
};
|
||||||
|
exports.hexDate = hexDate;
|
||||||
|
const hexTime = function (date) {
|
||||||
|
const buf = Buffer.allocUnsafe(2);
|
||||||
|
buf.writeUint8(date.getHours());
|
||||||
|
buf.writeUint8(date.getMinutes(), 1);
|
||||||
|
return buf.readUInt16BE().toString(16).padStart(4, "0");
|
||||||
|
};
|
||||||
|
exports.hexTime = hexTime;
|
||||||
|
const hexWeek = function (schedule) {
|
||||||
|
const SUNDAY = 1;
|
||||||
|
const MONDAY = 2;
|
||||||
|
const TUESDAY = 4;
|
||||||
|
const WEDNESDAY = 8;
|
||||||
|
const THUERSDAY = 16;
|
||||||
|
const FRIDAY = 32;
|
||||||
|
const SATURDAY = 64;
|
||||||
|
let result = 0;
|
||||||
|
if (schedule.week !== undefined) {
|
||||||
|
if (schedule.week.sunday) {
|
||||||
|
result |= SUNDAY;
|
||||||
|
}
|
||||||
|
if (schedule.week.monday) {
|
||||||
|
result |= MONDAY;
|
||||||
|
}
|
||||||
|
if (schedule.week.tuesday) {
|
||||||
|
result |= TUESDAY;
|
||||||
|
}
|
||||||
|
if (schedule.week.wednesday) {
|
||||||
|
result |= WEDNESDAY;
|
||||||
|
}
|
||||||
|
if (schedule.week.thursday) {
|
||||||
|
result |= THUERSDAY;
|
||||||
|
}
|
||||||
|
if (schedule.week.friday) {
|
||||||
|
result |= FRIDAY;
|
||||||
|
}
|
||||||
|
if (schedule.week.saturday) {
|
||||||
|
result |= SATURDAY;
|
||||||
|
}
|
||||||
|
return result.toString(16);
|
||||||
|
}
|
||||||
|
return "ff";
|
||||||
|
};
|
||||||
|
exports.hexWeek = hexWeek;
|
||||||
|
const hexStringScheduleToSchedule = function (startDay, startTime, endDay, endTime, week) {
|
||||||
|
const SUNDAY = 1;
|
||||||
|
const MONDAY = 2;
|
||||||
|
const TUESDAY = 4;
|
||||||
|
const WEDNESDAY = 8;
|
||||||
|
const THUERSDAY = 16;
|
||||||
|
const FRIDAY = 32;
|
||||||
|
const SATURDAY = 64;
|
||||||
|
const weekNumber = Number.parseInt(week, 16);
|
||||||
|
return {
|
||||||
|
startDateTime: startDay === "00000000" ? undefined : new Date(Number.parseInt(`${startDay.substring(2, 4)}${startDay.substring(0, 2)}`, 16), Number.parseInt(startDay.substring(4, 6), 16) - 1, Number.parseInt(startDay.substring(6, 8), 16), Number.parseInt(startTime.substring(0, 2), 16), Number.parseInt(startTime.substring(2, 4), 16)),
|
||||||
|
endDateTime: endDay === "ffffffff" ? undefined : new Date(Number.parseInt(`${endDay.substring(2, 4)}${endDay.substring(0, 2)}`, 16), Number.parseInt(endDay.substring(4, 6), 16) - 1, Number.parseInt(endDay.substring(6, 8), 16), Number.parseInt(endTime.substring(0, 2), 16), Number.parseInt(endTime.substring(2, 4), 16)),
|
||||||
|
week: {
|
||||||
|
monday: (weekNumber & MONDAY) == MONDAY,
|
||||||
|
tuesday: (weekNumber & TUESDAY) == TUESDAY,
|
||||||
|
wednesday: (weekNumber & WEDNESDAY) == WEDNESDAY,
|
||||||
|
thursday: (weekNumber & THUERSDAY) == THUERSDAY,
|
||||||
|
friday: (weekNumber & FRIDAY) == FRIDAY,
|
||||||
|
saturday: (weekNumber & SATURDAY) == SATURDAY,
|
||||||
|
sunday: (weekNumber & SUNDAY) == SUNDAY,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
};
|
||||||
|
exports.hexStringScheduleToSchedule = hexStringScheduleToSchedule;
|
||||||
|
const randomNumber = function (min, max) {
|
||||||
|
return Math.floor(Math.random() * (max - min + 1)) + min;
|
||||||
|
};
|
||||||
|
exports.randomNumber = randomNumber;
|
||||||
|
const getIdSuffix = function (p2pDid) {
|
||||||
|
let result = 0;
|
||||||
|
const match = p2pDid.match(/^[A-Z]+-(\d+)-[A-Z]+$/);
|
||||||
|
if (match?.length == 2) {
|
||||||
|
const num1 = Number.parseInt(match[1][0]);
|
||||||
|
const num2 = Number.parseInt(match[1][1]);
|
||||||
|
const num3 = Number.parseInt(match[1][3]);
|
||||||
|
const num4 = Number.parseInt(match[1][5]);
|
||||||
|
result = num1 + num2 + num3;
|
||||||
|
if (num3 < 5) {
|
||||||
|
result = result + num3;
|
||||||
|
}
|
||||||
|
result = result + num4;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.getIdSuffix = getIdSuffix;
|
||||||
|
const getImageBaseCode = function (serialnumber, p2pDid) {
|
||||||
|
let nr = 0;
|
||||||
|
try {
|
||||||
|
nr = Number.parseInt(`0x${serialnumber[serialnumber.length - 1]}`);
|
||||||
|
}
|
||||||
|
catch (err) {
|
||||||
|
const error = (0, error_1.ensureError)(err);
|
||||||
|
throw new error_2.ImageBaseCodeError("Error generating image base code", { cause: error, context: { serialnumber: serialnumber, p2pDid: p2pDid } });
|
||||||
|
}
|
||||||
|
nr = (nr + 10) % 10;
|
||||||
|
const base = serialnumber.substring(nr);
|
||||||
|
return `${base}${(0, exports.getIdSuffix)(p2pDid)}`;
|
||||||
|
};
|
||||||
|
exports.getImageBaseCode = getImageBaseCode;
|
||||||
|
const getImageSeed = function (p2pDid, code) {
|
||||||
|
try {
|
||||||
|
const ncode = Number.parseInt(code.substring(2));
|
||||||
|
const prefix = 1000 - (0, exports.getIdSuffix)(p2pDid);
|
||||||
|
return (0, md5_1.default)(`${prefix}${ncode}`).toString(enc_hex_1.default).toUpperCase();
|
||||||
|
}
|
||||||
|
catch (err) {
|
||||||
|
const error = (0, error_1.ensureError)(err);
|
||||||
|
throw new error_2.ImageBaseCodeError("Error generating image seed", { cause: error, context: { p2pDid: p2pDid, code: code } });
|
||||||
|
}
|
||||||
|
};
|
||||||
|
exports.getImageSeed = getImageSeed;
|
||||||
|
const getImageKey = function (serialnumber, p2pDid, code) {
|
||||||
|
const basecode = (0, exports.getImageBaseCode)(serialnumber, p2pDid);
|
||||||
|
const seed = (0, exports.getImageSeed)(p2pDid, code);
|
||||||
|
const data = `01${basecode}${seed}`;
|
||||||
|
const hash = (0, sha256_1.default)(data);
|
||||||
|
const hashBytes = [...Buffer.from(hash.toString(enc_hex_1.default), "hex")];
|
||||||
|
const startByte = hashBytes[10];
|
||||||
|
for (let i = 0; i < 32; i++) {
|
||||||
|
const byte = hashBytes[i];
|
||||||
|
let fixed_byte = startByte;
|
||||||
|
if (i < 31) {
|
||||||
|
fixed_byte = hashBytes[i + 1];
|
||||||
|
}
|
||||||
|
if ((i == 31) || ((i & 1) != 0)) {
|
||||||
|
hashBytes[10] = fixed_byte;
|
||||||
|
if ((126 < byte) || (126 < hashBytes[10])) {
|
||||||
|
if (byte < hashBytes[10] || (byte - hashBytes[10]) == 0) {
|
||||||
|
hashBytes[i] = hashBytes[10] - byte;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
hashBytes[i] = byte - hashBytes[10];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if ((byte < 125) || (fixed_byte < 125)) {
|
||||||
|
hashBytes[i] = fixed_byte + byte;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return `${Buffer.from(hashBytes.slice(16)).toString("hex").toUpperCase()}`;
|
||||||
|
};
|
||||||
|
exports.getImageKey = getImageKey;
|
||||||
|
const decodeImage = function (p2pDid, data) {
|
||||||
|
if (data.length >= 12) {
|
||||||
|
const header = data.subarray(0, 12).toString();
|
||||||
|
if (header === "eufysecurity") {
|
||||||
|
const serialnumber = data.subarray(13, 29).toString();
|
||||||
|
const code = data.subarray(30, 40).toString();
|
||||||
|
const imageKey = (0, exports.getImageKey)(serialnumber, p2pDid, code);
|
||||||
|
const otherData = data.subarray(41);
|
||||||
|
const encryptedData = otherData.subarray(0, 256);
|
||||||
|
const cipher = (0, crypto_1.createDecipheriv)("aes-128-ecb", Buffer.from(imageKey, "utf-8").subarray(0, 16), null);
|
||||||
|
cipher.setAutoPadding(false);
|
||||||
|
const decryptedData = Buffer.concat([
|
||||||
|
cipher.update(encryptedData),
|
||||||
|
cipher.final()
|
||||||
|
]);
|
||||||
|
decryptedData.copy(otherData);
|
||||||
|
return otherData;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return data;
|
||||||
|
};
|
||||||
|
exports.decodeImage = decodeImage;
|
||||||
|
const getImagePath = function (path) {
|
||||||
|
const splittedPath = path.split("~");
|
||||||
|
if (splittedPath.length === 2) {
|
||||||
|
return splittedPath[1];
|
||||||
|
}
|
||||||
|
return path;
|
||||||
|
};
|
||||||
|
exports.getImagePath = getImagePath;
|
||||||
|
const getImage = async function (api, serial, url) {
|
||||||
|
const { default: imageType } = await import("image-type");
|
||||||
|
const image = await api.getImage(serial, url);
|
||||||
|
const type = await imageType(image);
|
||||||
|
return {
|
||||||
|
data: image,
|
||||||
|
type: type !== null && type !== undefined ? type : { ext: "unknown", mime: "application/octet-stream" }
|
||||||
|
};
|
||||||
|
};
|
||||||
|
exports.getImage = getImage;
|
||||||
|
const isPrioritySourceType = function (current, update) {
|
||||||
|
if (((current === "http" || current === "p2p" || current === "push" || current === "mqtt" || current === undefined) && (update === "p2p" || update === "push" || update === "mqtt")) ||
|
||||||
|
((current === "http" || current === undefined) && update === "http")) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
};
|
||||||
|
exports.isPrioritySourceType = isPrioritySourceType;
|
||||||
|
const decryptTrackerData = (data, key) => {
|
||||||
|
const decipher = (0, crypto_1.createDecipheriv)("aes-128-ecb", key, null);
|
||||||
|
decipher.setAutoPadding(false);
|
||||||
|
return Buffer.concat([
|
||||||
|
decipher.update(data),
|
||||||
|
decipher.final()
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.decryptTrackerData = decryptTrackerData;
|
||||||
|
const isT8170DetectionModeEnabled = function (value, type) {
|
||||||
|
return (type & value) == type;
|
||||||
|
};
|
||||||
|
exports.isT8170DetectionModeEnabled = isT8170DetectionModeEnabled;
|
||||||
|
const getT8170DetectionMode = function (value, type, enable) {
|
||||||
|
let result = 0;
|
||||||
|
if ((Object.values(types_1.T8170DetectionTypes).includes(type) && Object.values(types_1.T8170DetectionTypes).includes(value)) && !enable)
|
||||||
|
return value;
|
||||||
|
if (!enable) {
|
||||||
|
result = type ^ value;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = type | value;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.getT8170DetectionMode = getT8170DetectionMode;
|
||||||
|
const isIndoorS350DetectionModeEnabled = function (value, type) {
|
||||||
|
return (type & value) == type;
|
||||||
|
};
|
||||||
|
exports.isIndoorS350DetectionModeEnabled = isIndoorS350DetectionModeEnabled;
|
||||||
|
const getIndoorS350DetectionMode = function (value, type, enable) {
|
||||||
|
let result = 0;
|
||||||
|
if ((Object.values(types_1.IndoorS350DetectionTypes).includes(type) && Object.values(types_1.IndoorS350DetectionTypes).includes(value)) && !enable)
|
||||||
|
return value;
|
||||||
|
if (!enable) {
|
||||||
|
result = type ^ value;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = type | value;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.getIndoorS350DetectionMode = getIndoorS350DetectionMode;
|
||||||
|
const isIndoorNotitficationEnabled = function (value, type) {
|
||||||
|
return (type & value) == type;
|
||||||
|
};
|
||||||
|
exports.isIndoorNotitficationEnabled = isIndoorNotitficationEnabled;
|
||||||
|
const getIndoorNotification = function (value, type, enable) {
|
||||||
|
let result = 0;
|
||||||
|
if (!enable) {
|
||||||
|
result = (type ^ value) + 800;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = type | value;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.getIndoorNotification = getIndoorNotification;
|
||||||
|
const isFloodlightT8425NotitficationEnabled = function (value, type) {
|
||||||
|
return (type & value) == type;
|
||||||
|
};
|
||||||
|
exports.isFloodlightT8425NotitficationEnabled = isFloodlightT8425NotitficationEnabled;
|
||||||
|
const getFloodLightT8425Notification = function (value, type, enable) {
|
||||||
|
let result = 0;
|
||||||
|
if (!enable) {
|
||||||
|
result = (type ^ value);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = type | value;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.getFloodLightT8425Notification = getFloodLightT8425Notification;
|
||||||
|
const getLockEventType = function (event) {
|
||||||
|
switch (event) {
|
||||||
|
case types_2.LockPushEvent.AUTO_LOCK:
|
||||||
|
case types_2.LockPushEvent.AUTO_UNLOCK:
|
||||||
|
return 1;
|
||||||
|
case types_2.LockPushEvent.MANUAL_LOCK:
|
||||||
|
case types_2.LockPushEvent.MANUAL_UNLOCK:
|
||||||
|
return 2;
|
||||||
|
case types_2.LockPushEvent.APP_LOCK:
|
||||||
|
case types_2.LockPushEvent.APP_UNLOCK:
|
||||||
|
return 3;
|
||||||
|
case types_2.LockPushEvent.PW_LOCK:
|
||||||
|
case types_2.LockPushEvent.PW_UNLOCK:
|
||||||
|
return 4;
|
||||||
|
case types_2.LockPushEvent.FINGER_LOCK:
|
||||||
|
case types_2.LockPushEvent.FINGERPRINT_UNLOCK:
|
||||||
|
return 5;
|
||||||
|
case types_2.LockPushEvent.TEMPORARY_PW_LOCK:
|
||||||
|
case types_2.LockPushEvent.TEMPORARY_PW_UNLOCK:
|
||||||
|
return 6;
|
||||||
|
case types_2.LockPushEvent.KEYPAD_LOCK:
|
||||||
|
return 7;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
};
|
||||||
|
exports.getLockEventType = getLockEventType;
|
||||||
|
const switchSmartLockNotification = function (currentValue, mode, enable) {
|
||||||
|
let result = 0;
|
||||||
|
if (enable) {
|
||||||
|
result = mode | currentValue;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = ~mode & currentValue;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.switchSmartLockNotification = switchSmartLockNotification;
|
||||||
|
const isSmartLockNotification = function (value, mode) {
|
||||||
|
return (value & mode) !== 0;
|
||||||
|
};
|
||||||
|
exports.isSmartLockNotification = isSmartLockNotification;
|
||||||
|
const getWaitSeconds = (device) => {
|
||||||
|
let seconds = 60;
|
||||||
|
const workingMode = device.getPropertyValue(types_1.PropertyName.DevicePowerWorkingMode);
|
||||||
|
if (workingMode !== undefined && workingMode === 2) {
|
||||||
|
const customValue = device.getPropertyValue(types_1.PropertyName.DeviceRecordingClipLength);
|
||||||
|
if (customValue !== undefined) {
|
||||||
|
seconds = customValue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return seconds;
|
||||||
|
};
|
||||||
|
exports.getWaitSeconds = getWaitSeconds;
|
||||||
|
const loadImageOverP2P = function (station, device, id, p2pTimeouts) {
|
||||||
|
if (station.hasCommand(types_1.CommandName.StationDatabaseQueryLatestInfo) && p2pTimeouts.get(id) === undefined) {
|
||||||
|
const seconds = (0, exports.getWaitSeconds)(device);
|
||||||
|
p2pTimeouts.set(id, setTimeout(async () => {
|
||||||
|
station.databaseQueryLatestInfo();
|
||||||
|
p2pTimeouts.delete(id);
|
||||||
|
}, seconds * 1000));
|
||||||
|
}
|
||||||
|
};
|
||||||
|
exports.loadImageOverP2P = loadImageOverP2P;
|
||||||
|
const loadEventImage = function (station, api, device, message, p2pTimeouts) {
|
||||||
|
if (message.notification_style === types_1.NotificationType.MOST_EFFICIENT) {
|
||||||
|
(0, exports.loadImageOverP2P)(station, device, device.getSerial(), p2pTimeouts);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (!(0, utils_1.isEmpty)(message.pic_url)) {
|
||||||
|
(0, exports.getImage)(api, device.getSerial(), message.pic_url).then((image) => {
|
||||||
|
if (image.data.length > 0) {
|
||||||
|
if (p2pTimeouts.get(device.getSerial()) !== undefined) {
|
||||||
|
clearTimeout(p2pTimeouts.get(device.getSerial()));
|
||||||
|
p2pTimeouts.delete(device.getSerial());
|
||||||
|
}
|
||||||
|
device.updateProperty(types_1.PropertyName.DevicePicture, image, true);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
//fallback
|
||||||
|
(0, exports.loadImageOverP2P)(station, device, device.getSerial(), p2pTimeouts);
|
||||||
|
}
|
||||||
|
}).catch((err) => {
|
||||||
|
const error = (0, error_1.ensureError)(err);
|
||||||
|
logging_1.rootHTTPLogger.debug(`Device load event image - Fallback Error`, { error: (0, utils_1.getError)(error), stationSN: station.getSerial(), deviceSN: device.getSerial(), message: JSON.stringify(message) });
|
||||||
|
(0, exports.loadImageOverP2P)(station, device, device.getSerial(), p2pTimeouts);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
//fallback
|
||||||
|
(0, exports.loadImageOverP2P)(station, device, device.getSerial(), p2pTimeouts);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
exports.loadEventImage = loadEventImage;
|
||||||
|
//# sourceMappingURL=utils.js.map
|
||||||
1
build/http/utils.js.map
Normal file
1
build/http/utils.js.map
Normal file
File diff suppressed because one or more lines are too long
8
build/index.d.ts
vendored
Normal file
8
build/index.d.ts
vendored
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
export * from "./http";
|
||||||
|
export * from "./p2p";
|
||||||
|
export * from "./push";
|
||||||
|
export * from "./interfaces";
|
||||||
|
export * from "./eufysecurity";
|
||||||
|
export * from "./error";
|
||||||
|
export { LoggingCategories, LogLevel, Logger, dummyLogger } from "./logging";
|
||||||
|
export declare const libVersion: string;
|
||||||
29
build/index.js
Normal file
29
build/index.js
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
"use strict";
|
||||||
|
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
var desc = Object.getOwnPropertyDescriptor(m, k);
|
||||||
|
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
||||||
|
desc = { enumerable: true, get: function() { return m[k]; } };
|
||||||
|
}
|
||||||
|
Object.defineProperty(o, k2, desc);
|
||||||
|
}) : (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
o[k2] = m[k];
|
||||||
|
}));
|
||||||
|
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
||||||
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.libVersion = exports.dummyLogger = exports.LogLevel = void 0;
|
||||||
|
__exportStar(require("./http"), exports);
|
||||||
|
__exportStar(require("./p2p"), exports);
|
||||||
|
__exportStar(require("./push"), exports);
|
||||||
|
__exportStar(require("./interfaces"), exports);
|
||||||
|
__exportStar(require("./eufysecurity"), exports);
|
||||||
|
__exportStar(require("./error"), exports);
|
||||||
|
var logging_1 = require("./logging");
|
||||||
|
Object.defineProperty(exports, "LogLevel", { enumerable: true, get: function () { return logging_1.LogLevel; } });
|
||||||
|
Object.defineProperty(exports, "dummyLogger", { enumerable: true, get: function () { return logging_1.dummyLogger; } });
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
||||||
|
exports.libVersion = require("../package.json").version;
|
||||||
|
//# sourceMappingURL=index.js.map
|
||||||
1
build/index.js.map
Normal file
1
build/index.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAAA,yCAAuB;AACvB,wCAAsB;AACtB,yCAAuB;AACvB,+CAA6B;AAC7B,iDAA+B;AAC/B,0CAAwB;AACxB,qCAA6E;AAAjD,mGAAA,QAAQ,OAAA;AAAU,sGAAA,WAAW,OAAA;AAEzD,8DAA8D;AACjD,QAAA,UAAU,GAAW,OAAO,CAAC,iBAAiB,CAAC,CAAC,OAAO,CAAC"}
|
||||||
142
build/interfaces.d.ts
vendored
Normal file
142
build/interfaces.d.ts
vendored
Normal file
@ -0,0 +1,142 @@
|
|||||||
|
import { Readable } from "stream";
|
||||||
|
import { Device } from "./http/device";
|
||||||
|
import { HTTPApiPersistentData, Picture, PropertyValue, Schedule } from "./http/interfaces";
|
||||||
|
import { Station } from "./http/station";
|
||||||
|
import { DeviceSmartLockMessage } from "./mqtt/model";
|
||||||
|
import { DatabaseCountByDate, DatabaseQueryLatestInfo, DatabaseQueryLocal, StreamMetadata } from "./p2p/interfaces";
|
||||||
|
import { CommandResult } from "./p2p/models";
|
||||||
|
import { TalkbackStream } from "./p2p/talkback";
|
||||||
|
import { AlarmEvent, DatabaseReturnCode, SmartSafeAlarm911Event, SmartSafeShakeAlarmEvent } from "./p2p/types";
|
||||||
|
import { Credentials, PushMessage } from "./push/models";
|
||||||
|
import { Jsonable, LoggingCategories } from ".";
|
||||||
|
import { LogLevel } from "typescript-logging";
|
||||||
|
export interface StationIPAddresses {
|
||||||
|
[index: string]: string;
|
||||||
|
}
|
||||||
|
export interface EufySecurityConfig {
|
||||||
|
username: string;
|
||||||
|
password: string;
|
||||||
|
country?: string;
|
||||||
|
language?: string;
|
||||||
|
trustedDeviceName?: string;
|
||||||
|
persistentDir?: string;
|
||||||
|
persistentData?: string;
|
||||||
|
p2pConnectionSetup: number;
|
||||||
|
pollingIntervalMinutes: number;
|
||||||
|
eventDurationSeconds: number;
|
||||||
|
acceptInvitations?: boolean;
|
||||||
|
stationIPAddresses?: StationIPAddresses;
|
||||||
|
enableEmbeddedPKCS1Support?: boolean;
|
||||||
|
deviceConfig?: {
|
||||||
|
simultaneousDetections?: boolean;
|
||||||
|
};
|
||||||
|
logging?: {
|
||||||
|
level?: LogLevel;
|
||||||
|
categories?: Array<{
|
||||||
|
category: LoggingCategories;
|
||||||
|
level: LogLevel;
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface EufySecurityPersistentData {
|
||||||
|
country: string;
|
||||||
|
login_hash: string;
|
||||||
|
openudid: string;
|
||||||
|
serial_number: string;
|
||||||
|
cloud_token?: string;
|
||||||
|
cloud_token_expiration?: number;
|
||||||
|
push_credentials: Credentials | undefined;
|
||||||
|
push_persistentIds: string[];
|
||||||
|
version: string;
|
||||||
|
httpApi?: HTTPApiPersistentData;
|
||||||
|
fallbackTrustedDeviceName?: string;
|
||||||
|
}
|
||||||
|
export interface EufySecurityEvents {
|
||||||
|
"device added": (device: Device) => void;
|
||||||
|
"device removed": (device: Device) => void;
|
||||||
|
"device property changed": (device: Device, name: string, value: PropertyValue) => void;
|
||||||
|
"device raw property changed": (device: Device, type: number, value: string) => void;
|
||||||
|
"device crying detected": (device: Device, state: boolean) => void;
|
||||||
|
"device sound detected": (device: Device, state: boolean) => void;
|
||||||
|
"device pet detected": (device: Device, state: boolean) => void;
|
||||||
|
"device vehicle detected": (device: Device, state: boolean) => void;
|
||||||
|
"device motion detected": (device: Device, state: boolean) => void;
|
||||||
|
"device person detected": (device: Device, state: boolean, person: string) => void;
|
||||||
|
"device stranger person detected": (device: Device, state: boolean) => void;
|
||||||
|
"device dog detected": (device: Device, state: boolean) => void;
|
||||||
|
"device dog lick detected": (device: Device, state: boolean) => void;
|
||||||
|
"device dog poop detected": (device: Device, state: boolean) => void;
|
||||||
|
"device rings": (device: Device, state: boolean) => void;
|
||||||
|
"device locked": (device: Device, state: boolean) => void;
|
||||||
|
"device open": (device: Device, state: boolean) => void;
|
||||||
|
"device package delivered": (device: Device, state: boolean) => void;
|
||||||
|
"device package stranded": (device: Device, state: boolean) => void;
|
||||||
|
"device package taken": (device: Device, state: boolean) => void;
|
||||||
|
"device someone loitering": (device: Device, state: boolean) => void;
|
||||||
|
"device radar motion detected": (device: Device, state: boolean) => void;
|
||||||
|
"device 911 alarm": (device: Device, state: boolean, detail: SmartSafeAlarm911Event) => void;
|
||||||
|
"device shake alarm": (device: Device, state: boolean, detail: SmartSafeShakeAlarmEvent) => void;
|
||||||
|
"device wrong try-protect alarm": (device: Device, state: boolean) => void;
|
||||||
|
"device long time not close": (device: Device, state: boolean) => void;
|
||||||
|
"device low battery": (device: Device, state: boolean) => void;
|
||||||
|
"device jammed": (device: Device, state: boolean) => void;
|
||||||
|
"device pin verified": (device: Device, successfull: boolean) => void;
|
||||||
|
"device tampering": (device: Device, state: boolean) => void;
|
||||||
|
"device low temperature": (device: Device, state: boolean) => void;
|
||||||
|
"device high temperature": (device: Device, state: boolean) => void;
|
||||||
|
"device pin incorrect": (device: Device, state: boolean) => void;
|
||||||
|
"device lid stuck": (device: Device, state: boolean) => void;
|
||||||
|
"device battery fully charged": (device: Device, state: boolean) => void;
|
||||||
|
"station added": (station: Station) => void;
|
||||||
|
"station removed": (station: Station) => void;
|
||||||
|
"station livestream start": (station: Station, device: Device, metadata: StreamMetadata, videostream: Readable, audiostream: Readable) => void;
|
||||||
|
"station livestream stop": (station: Station, device: Device) => void;
|
||||||
|
"station download start": (station: Station, device: Device, metadata: StreamMetadata, videoStream: Readable, audioStream: Readable) => void;
|
||||||
|
"station download finish": (station: Station, device: Device) => void;
|
||||||
|
"station command result": (station: Station, result: CommandResult) => void;
|
||||||
|
"station rtsp livestream start": (station: Station, device: Device) => void;
|
||||||
|
"station rtsp livestream stop": (station: Station, device: Device) => void;
|
||||||
|
"station rtsp url": (station: Station, device: Device, value: string) => void;
|
||||||
|
"station guard mode": (station: Station, guardMode: number) => void;
|
||||||
|
"station current mode": (station: Station, currentMode: number) => void;
|
||||||
|
"station property changed": (station: Station, name: string, value: PropertyValue) => void;
|
||||||
|
"station raw property changed": (station: Station, type: number, value: string) => void;
|
||||||
|
"station alarm event": (station: Station, alarmEvent: AlarmEvent) => void;
|
||||||
|
"station alarm delay event": (station: Station, alarmDelayEvent: AlarmEvent, alarmDelay: number) => void;
|
||||||
|
"station alarm armed": (station: Station) => void;
|
||||||
|
"station alarm arm delay event": (station: Station, armDelay: number) => void;
|
||||||
|
"station connect": (station: Station) => void;
|
||||||
|
"station connection error": (station: Station, error: Error) => void;
|
||||||
|
"station close": (station: Station) => void;
|
||||||
|
"station talkback start": (station: Station, device: Device, talkbackStream: TalkbackStream) => void;
|
||||||
|
"station talkback stop": (station: Station, device: Device) => void;
|
||||||
|
"station image download": (station: Station, file: string, image: Picture) => void;
|
||||||
|
"station database query latest": (station: Station, returnCode: DatabaseReturnCode, data: Array<DatabaseQueryLatestInfo>) => void;
|
||||||
|
"station database query local": (station: Station, returnCode: DatabaseReturnCode, data: Array<DatabaseQueryLocal>) => void;
|
||||||
|
"station database count by date": (station: Station, returnCode: DatabaseReturnCode, data: Array<DatabaseCountByDate>) => void;
|
||||||
|
"station database delete": (station: Station, returnCode: DatabaseReturnCode, failedIds: Array<unknown>) => void;
|
||||||
|
"push connect": () => void;
|
||||||
|
"push close": () => void;
|
||||||
|
"push message": (message: PushMessage) => void;
|
||||||
|
"connect": () => void;
|
||||||
|
"close": () => void;
|
||||||
|
"connection error": (error: Error) => void;
|
||||||
|
"tfa request": () => void;
|
||||||
|
"captcha request": (id: string, captcha: string) => void;
|
||||||
|
"persistent data": (data: string) => void;
|
||||||
|
"mqtt connect": () => void;
|
||||||
|
"mqtt close": () => void;
|
||||||
|
"mqtt lock message": (message: DeviceSmartLockMessage) => void;
|
||||||
|
"user added": (device: Device, username: string, schedule?: Schedule) => void;
|
||||||
|
"user deleted": (device: Device, username: string) => void;
|
||||||
|
"user error": (device: Device, username: string, error: Error) => void;
|
||||||
|
"user username updated": (device: Device, username: string) => void;
|
||||||
|
"user schedule updated": (device: Device, username: string, schedule: Schedule) => void;
|
||||||
|
"user passcode updated": (device: Device, username: string) => void;
|
||||||
|
}
|
||||||
|
export interface ErrorObject {
|
||||||
|
cause: unknown;
|
||||||
|
message: string;
|
||||||
|
context: Jsonable;
|
||||||
|
stacktrace?: string;
|
||||||
|
}
|
||||||
3
build/interfaces.js
Normal file
3
build/interfaces.js
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
//# sourceMappingURL=interfaces.js.map
|
||||||
1
build/interfaces.js.map
Normal file
1
build/interfaces.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"interfaces.js","sourceRoot":"","sources":["../src/interfaces.ts"],"names":[],"mappings":""}
|
||||||
22
build/logging.d.ts
vendored
Normal file
22
build/logging.d.ts
vendored
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
import { LogLevel } from "typescript-logging";
|
||||||
|
export type LoggingCategories = "all" | "main" | "http" | "p2p" | "push" | "mqtt";
|
||||||
|
export { LogLevel };
|
||||||
|
export interface Logger {
|
||||||
|
trace(message: unknown, ...args: unknown[]): void;
|
||||||
|
debug(message: unknown, ...args: unknown[]): void;
|
||||||
|
info(message: unknown, ...args: unknown[]): void;
|
||||||
|
warn(message: unknown, ...args: unknown[]): void;
|
||||||
|
error(message: unknown, ...args: unknown[]): void;
|
||||||
|
fatal?(message: unknown, ...args: unknown[]): void;
|
||||||
|
}
|
||||||
|
export declare const dummyLogger: Logger;
|
||||||
|
export declare class InternalLogger {
|
||||||
|
static logger: Logger | undefined;
|
||||||
|
}
|
||||||
|
export declare const rootMainLogger: import("typescript-logging-category-style").Category;
|
||||||
|
export declare const rootHTTPLogger: import("typescript-logging-category-style").Category;
|
||||||
|
export declare const rootMQTTLogger: import("typescript-logging-category-style").Category;
|
||||||
|
export declare const rootPushLogger: import("typescript-logging-category-style").Category;
|
||||||
|
export declare const rootP2PLogger: import("typescript-logging-category-style").Category;
|
||||||
|
export declare const setLoggingLevel: (category?: LoggingCategories, level?: LogLevel) => void;
|
||||||
|
export declare const getLoggingLevel: (category?: LoggingCategories) => number;
|
||||||
116
build/logging.js
Normal file
116
build/logging.js
Normal file
@ -0,0 +1,116 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.getLoggingLevel = exports.setLoggingLevel = exports.rootP2PLogger = exports.rootPushLogger = exports.rootMQTTLogger = exports.rootHTTPLogger = exports.rootMainLogger = exports.InternalLogger = exports.LogLevel = void 0;
|
||||||
|
const typescript_logging_1 = require("typescript-logging");
|
||||||
|
Object.defineProperty(exports, "LogLevel", { enumerable: true, get: function () { return typescript_logging_1.LogLevel; } });
|
||||||
|
const typescript_logging_category_style_1 = require("typescript-logging-category-style");
|
||||||
|
class InternalLogger {
|
||||||
|
static logger;
|
||||||
|
}
|
||||||
|
exports.InternalLogger = InternalLogger;
|
||||||
|
const getMethodName = function () {
|
||||||
|
const matches = new Error("").stack?.split("\n")[6].match(/ at( new){0,1} ([a-zA-Z0-9_\.]+) /);
|
||||||
|
if (matches !== null && matches !== undefined && matches[2] !== undefined && matches[2] !== "eval") {
|
||||||
|
return matches[2];
|
||||||
|
}
|
||||||
|
return undefined;
|
||||||
|
};
|
||||||
|
const provider = typescript_logging_category_style_1.CategoryProvider.createProvider("EufySecurityClientProvider", {
|
||||||
|
level: typescript_logging_1.LogLevel.Off,
|
||||||
|
channel: {
|
||||||
|
type: "RawLogChannel",
|
||||||
|
write: (msg, _formatArg) => {
|
||||||
|
const methodName = getMethodName();
|
||||||
|
const method = methodName ? `[${methodName}] ` : "";
|
||||||
|
switch (msg.level) {
|
||||||
|
case typescript_logging_1.LogLevel.Trace:
|
||||||
|
if (msg.args)
|
||||||
|
InternalLogger.logger?.trace(`[${msg.logNames}] ${method}${msg.message}`, ...msg.args);
|
||||||
|
else
|
||||||
|
InternalLogger.logger?.trace(`[${msg.logNames}] ${method}${msg.message}`);
|
||||||
|
break;
|
||||||
|
case typescript_logging_1.LogLevel.Debug:
|
||||||
|
if (msg.args)
|
||||||
|
InternalLogger.logger?.debug(`[${msg.logNames}] ${method}${msg.message}`, ...msg.args);
|
||||||
|
else
|
||||||
|
InternalLogger.logger?.debug(`[${msg.logNames}] ${method}${msg.message}`);
|
||||||
|
break;
|
||||||
|
case typescript_logging_1.LogLevel.Info:
|
||||||
|
if (msg.args)
|
||||||
|
InternalLogger.logger?.info(`[${msg.logNames}] ${method}${msg.message}`, ...msg.args);
|
||||||
|
else
|
||||||
|
InternalLogger.logger?.info(`[${msg.logNames}] ${method}${msg.message}`);
|
||||||
|
break;
|
||||||
|
case typescript_logging_1.LogLevel.Warn:
|
||||||
|
if (msg.args)
|
||||||
|
InternalLogger.logger?.warn(`[${msg.logNames}] ${method}${msg.message}`, ...msg.args);
|
||||||
|
else
|
||||||
|
InternalLogger.logger?.warn(`[${msg.logNames}] ${method}${msg.message}`);
|
||||||
|
break;
|
||||||
|
case typescript_logging_1.LogLevel.Error:
|
||||||
|
if (msg.args)
|
||||||
|
InternalLogger.logger?.error(`[${msg.logNames}] ${method}${msg.message}`, ...msg.args);
|
||||||
|
else
|
||||||
|
InternalLogger.logger?.error(`[${msg.logNames}] ${method}${msg.message}`);
|
||||||
|
break;
|
||||||
|
case typescript_logging_1.LogLevel.Fatal:
|
||||||
|
if (InternalLogger.logger && InternalLogger.logger.fatal)
|
||||||
|
if (msg.args)
|
||||||
|
InternalLogger.logger.fatal(`[${msg.logNames}] ${method}${msg.message}`, ...msg.args);
|
||||||
|
else
|
||||||
|
InternalLogger.logger.fatal(`[${msg.logNames}] ${method}${msg.message}`);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
exports.rootMainLogger = provider.getCategory("main");
|
||||||
|
exports.rootHTTPLogger = provider.getCategory("http");
|
||||||
|
exports.rootMQTTLogger = provider.getCategory("mqtt");
|
||||||
|
exports.rootPushLogger = provider.getCategory("push");
|
||||||
|
exports.rootP2PLogger = provider.getCategory("p2p");
|
||||||
|
const setLoggingLevel = function (category = "all", level = typescript_logging_1.LogLevel.Off) {
|
||||||
|
switch (category) {
|
||||||
|
case "all":
|
||||||
|
provider.updateRuntimeSettings({
|
||||||
|
level: level
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
case "main":
|
||||||
|
provider.updateRuntimeSettingsCategory(exports.rootMainLogger, {
|
||||||
|
level: level
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
case "http":
|
||||||
|
provider.updateRuntimeSettingsCategory(exports.rootHTTPLogger, {
|
||||||
|
level: level
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
case "mqtt":
|
||||||
|
provider.updateRuntimeSettingsCategory(exports.rootMQTTLogger, {
|
||||||
|
level: level
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
case "p2p":
|
||||||
|
provider.updateRuntimeSettingsCategory(exports.rootP2PLogger, {
|
||||||
|
level: level
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
case "push":
|
||||||
|
provider.updateRuntimeSettingsCategory(exports.rootPushLogger, {
|
||||||
|
level: level
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
exports.setLoggingLevel = setLoggingLevel;
|
||||||
|
const getLoggingLevel = function (category = "all") {
|
||||||
|
switch (category) {
|
||||||
|
case "all":
|
||||||
|
return provider.runtimeConfig.level;
|
||||||
|
default:
|
||||||
|
return provider.getCategory(category).logLevel;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
exports.getLoggingLevel = getLoggingLevel;
|
||||||
|
//# sourceMappingURL=logging.js.map
|
||||||
1
build/logging.js.map
Normal file
1
build/logging.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"logging.js","sourceRoot":"","sources":["../src/logging.ts"],"names":[],"mappings":";;;AAAA,2DAA8C;AAKrC,yFALA,6BAAQ,OAKA;AAJjB,yFAAqE;AAiBrE,MAAa,cAAc;IAEhB,MAAM,CAAC,MAAM,CAAqB;CAE5C;AAJD,wCAIC;AAED,MAAM,aAAa,GAAG;IAClB,MAAM,OAAO,GAAG,IAAI,KAAK,CAAC,EAAE,CAAC,CAAC,KAAK,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,mCAAmC,CAAC,CAAC;IAC/F,IAAI,OAAO,KAAK,IAAI,IAAI,OAAO,KAAK,SAAS,IAAI,OAAO,CAAC,CAAC,CAAC,KAAK,SAAS,IAAI,OAAO,CAAC,CAAC,CAAC,KAAK,MAAM,EAAE,CAAC;QACjG,OAAO,OAAO,CAAC,CAAC,CAAC,CAAC;IACtB,CAAC;IACD,OAAO,SAAS,CAAC;AACrB,CAAC,CAAA;AAED,MAAM,QAAQ,GAAG,oDAAgB,CAAC,cAAc,CAAC,4BAA4B,EAAE;IAC3E,KAAK,EAAE,6BAAQ,CAAC,GAAG;IACnB,OAAO,EAAE;QACL,IAAI,EAAE,eAAe;QACrB,KAAK,EAAE,CAAC,GAAG,EAAE,UAAU,EAAE,EAAE;YACvB,MAAM,UAAU,GAAG,aAAa,EAAE,CAAC;YACnC,MAAM,MAAM,GAAG,UAAU,CAAC,CAAC,CAAC,IAAI,UAAU,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC;YACpD,QAAO,GAAG,CAAC,KAAK,EAAE,CAAC;gBACf,KAAK,6BAAQ,CAAC,KAAK;oBACf,IAAI,GAAG,CAAC,IAAI;wBACR,cAAc,CAAC,MAAM,EAAE,KAAK,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,EAAE,GAAG,GAAG,CAAC,IAAI,CAAC,CAAC;;wBAEvF,cAAc,CAAC,MAAM,EAAE,KAAK,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,CAAC,CAAC;oBAC9E,MAAM;gBACV,KAAK,6BAAQ,CAAC,KAAK;oBACf,IAAI,GAAG,CAAC,IAAI;wBACR,cAAc,CAAC,MAAM,EAAE,KAAK,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,EAAE,GAAG,GAAG,CAAC,IAAI,CAAC,CAAC;;wBAEvF,cAAc,CAAC,MAAM,EAAE,KAAK,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,CAAC,CAAC;oBAC9E,MAAM;gBACV,KAAK,6BAAQ,CAAC,IAAI;oBACd,IAAI,GAAG,CAAC,IAAI;wBACR,cAAc,CAAC,MAAM,EAAE,IAAI,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,EAAE,GAAG,GAAG,CAAC,IAAI,CAAC,CAAC;;wBAEtF,cAAc,CAAC,MAAM,EAAE,IAAI,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,CAAC,CAAC;oBAC7E,MAAM;gBACV,KAAK,6BAAQ,CAAC,IAAI;oBACd,IAAI,GAAG,CAAC,IAAI;wBACR,cAAc,CAAC,MAAM,EAAE,IAAI,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,EAAE,GAAG,GAAG,CAAC,IAAI,CAAC,CAAC;;wBAEtF,cAAc,CAAC,MAAM,EAAE,IAAI,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,CAAC,CAAC;oBAC7E,MAAM;gBACV,KAAK,6BAAQ,CAAC,KAAK;oBACf,IAAI,GAAG,CAAC,IAAI;wBACR,cAAc,CAAC,MAAM,EAAE,KAAK,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,EAAE,GAAG,GAAG,CAAC,IAAI,CAAC,CAAC;;wBAEvF,cAAc,CAAC,MAAM,EAAE,KAAK,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,CAAC,CAAC;oBAC9E,MAAM;gBACV,KAAK,6BAAQ,CAAC,KAAK;oBACf,IAAI,cAAc,CAAC,MAAM,IAAI,cAAc,CAAC,MAAM,CAAC,KAAK;wBACpD,IAAI,GAAG,CAAC,IAAI;4BACR,cAAc,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,EAAE,GAAG,GAAG,CAAC,IAAI,CAAC,CAAC;;4BAEtF,cAAc,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,GAAG,CAAC,QAAQ,KAAK,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,CAAC,CAAC;oBACjF,MAAM;YACd,CAAC;QACL,CAAC;KACJ;CACJ,CAAC,CAAC;AAEU,QAAA,cAAc,GAAG,QAAQ,CAAC,WAAW,CAAC,MAAM,CAAC,CAAC;AAC9C,QAAA,cAAc,GAAG,QAAQ,CAAC,WAAW,CAAC,MAAM,CAAC,CAAC;AAC9C,QAAA,cAAc,GAAG,QAAQ,CAAC,WAAW,CAAC,MAAM,CAAC,CAAC;AAC9C,QAAA,cAAc,GAAG,QAAQ,CAAC,WAAW,CAAC,MAAM,CAAC,CAAC;AAC9C,QAAA,aAAa,GAAG,QAAQ,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC;AAElD,MAAM,eAAe,GAAG,UAAS,WAA8B,KAAK,EAAE,QAAkB,6BAAQ,CAAC,GAAG;IACvG,QAAO,QAAQ,EAAE,CAAC;QACd,KAAK,KAAK;YACN,QAAQ,CAAC,qBAAqB,CAAC;gBAC3B,KAAK,EAAE,KAAK;aACf,CAAC,CAAC;YACH,MAAM;QACV,KAAK,MAAM;YACP,QAAQ,CAAC,6BAA6B,CAAC,sBAAc,EAAE;gBACnD,KAAK,EAAE,KAAK;aACf,CAAC,CAAC;YACH,MAAM;QACV,KAAK,MAAM;YACP,QAAQ,CAAC,6BAA6B,CAAC,sBAAc,EAAE;gBACnD,KAAK,EAAE,KAAK;aACf,CAAC,CAAC;YACH,MAAM;QACV,KAAK,MAAM;YACP,QAAQ,CAAC,6BAA6B,CAAC,sBAAc,EAAE;gBACnD,KAAK,EAAE,KAAK;aACf,CAAC,CAAC;YACH,MAAM;QACV,KAAK,KAAK;YACN,QAAQ,CAAC,6BAA6B,CAAC,qBAAa,EAAE;gBAClD,KAAK,EAAE,KAAK;aACf,CAAC,CAAC;YACH,MAAM;QACV,KAAK,MAAM;YACP,QAAQ,CAAC,6BAA6B,CAAC,sBAAc,EAAE;gBACnD,KAAK,EAAE,KAAK;aACf,CAAC,CAAC;YACH,MAAM;IACd,CAAC;AACL,CAAC,CAAA;AAjCY,QAAA,eAAe,mBAiC3B;AAEM,MAAM,eAAe,GAAG,UAAS,WAA8B,KAAK;IACvE,QAAO,QAAQ,EAAE,CAAC;QACd,KAAK,KAAK;YACN,OAAO,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC;QACxC;YACI,OAAO,QAAQ,CAAC,WAAW,CAAC,QAAQ,CAAC,CAAC,QAAQ,CAAC;IACvD,CAAC;AACL,CAAC,CAAA;AAPY,QAAA,eAAe,mBAO3B"}
|
||||||
6
build/mqtt/interface.d.ts
vendored
Normal file
6
build/mqtt/interface.d.ts
vendored
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
import { DeviceSmartLockMessage } from "./model";
|
||||||
|
export interface MQTTServiceEvents {
|
||||||
|
"connect": () => void;
|
||||||
|
"close": () => void;
|
||||||
|
"lock message": (message: DeviceSmartLockMessage) => void;
|
||||||
|
}
|
||||||
3
build/mqtt/interface.js
Normal file
3
build/mqtt/interface.js
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
//# sourceMappingURL=interface.js.map
|
||||||
1
build/mqtt/interface.js.map
Normal file
1
build/mqtt/interface.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"interface.js","sourceRoot":"","sources":["../../src/mqtt/interface.ts"],"names":[],"mappings":""}
|
||||||
24
build/mqtt/model.d.ts
vendored
Normal file
24
build/mqtt/model.d.ts
vendored
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
export interface DeviceSmartLockNotifyData {
|
||||||
|
stationSn: string;
|
||||||
|
deviceSn: string;
|
||||||
|
eventType: number;
|
||||||
|
eventTime: number;
|
||||||
|
shortUserId: string;
|
||||||
|
unknown1: string;
|
||||||
|
nickName: string;
|
||||||
|
userId: string;
|
||||||
|
unknown2: string;
|
||||||
|
deviceName: string;
|
||||||
|
unknown3: string;
|
||||||
|
lockState: string;
|
||||||
|
}
|
||||||
|
export interface DeviceSmartLockNotify {
|
||||||
|
timestamp: number;
|
||||||
|
uuid: string;
|
||||||
|
data: DeviceSmartLockNotifyData;
|
||||||
|
}
|
||||||
|
export interface DeviceSmartLockMessage {
|
||||||
|
eventType: number;
|
||||||
|
userId: string;
|
||||||
|
data: DeviceSmartLockNotify;
|
||||||
|
}
|
||||||
3
build/mqtt/model.js
Normal file
3
build/mqtt/model.js
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
//# sourceMappingURL=model.js.map
|
||||||
1
build/mqtt/model.js.map
Normal file
1
build/mqtt/model.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"model.js","sourceRoot":"","sources":["../../src/mqtt/model.ts"],"names":[],"mappings":""}
|
||||||
79
build/mqtt/mqtt-eufy.crt
Normal file
79
build/mqtt/mqtt-eufy.crt
Normal file
@ -0,0 +1,79 @@
|
|||||||
|
-----BEGIN CERTIFICATE-----
|
||||||
|
MIIE0DCCA7igAwIBAgIBBzANBgkqhkiG9w0BAQsFADCBgzELMAkGA1UEBhMCVVMx
|
||||||
|
EDAOBgNVBAgTB0FyaXpvbmExEzARBgNVBAcTClNjb3R0c2RhbGUxGjAYBgNVBAoT
|
||||||
|
EUdvRGFkZHkuY29tLCBJbmMuMTEwLwYDVQQDEyhHbyBEYWRkeSBSb290IENlcnRp
|
||||||
|
ZmljYXRlIEF1dGhvcml0eSAtIEcyMB4XDTExMDUwMzA3MDAwMFoXDTMxMDUwMzA3
|
||||||
|
MDAwMFowgbQxCzAJBgNVBAYTAlVTMRAwDgYDVQQIEwdBcml6b25hMRMwEQYDVQQH
|
||||||
|
EwpTY290dHNkYWxlMRowGAYDVQQKExFHb0RhZGR5LmNvbSwgSW5jLjEtMCsGA1UE
|
||||||
|
CxMkaHR0cDovL2NlcnRzLmdvZGFkZHkuY29tL3JlcG9zaXRvcnkvMTMwMQYDVQQD
|
||||||
|
EypHbyBEYWRkeSBTZWN1cmUgQ2VydGlmaWNhdGUgQXV0aG9yaXR5IC0gRzIwggEi
|
||||||
|
MA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQC54MsQ1K92vdSTYuswZLiBCGzD
|
||||||
|
BNliF44v/z5lz4/OYuY8UhzaFkVLVat4a2ODYpDOD2lsmcgaFItMzEUz6ojcnqOv
|
||||||
|
K/6AYZ15V8TPLvQ/MDxdR/yaFrzDN5ZBUY4RS1T4KL7QjL7wMDge87Am+GZHY23e
|
||||||
|
cSZHjzhHU9FGHbTj3ADqRay9vHHZqm8A29vNMDp5T19MR/gd71vCxJ1gO7GyQ5HY
|
||||||
|
pDNO6rPWJ0+tJYqlxvTV0KaudAVkV4i1RFXULSo6Pvi4vekyCgKUZMQWOlDxSq7n
|
||||||
|
eTOvDCAHf+jfBDnCaQJsY1L6d8EbyHSHyLmTGFBUNUtpTrw700kuH9zB0lL7AgMB
|
||||||
|
AAGjggEaMIIBFjAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNV
|
||||||
|
HQ4EFgQUQMK9J47MNIMwojPX+2yz8LQsgM4wHwYDVR0jBBgwFoAUOpqFBxBnKLbv
|
||||||
|
9r0FQW4gwZTaD94wNAYIKwYBBQUHAQEEKDAmMCQGCCsGAQUFBzABhhhodHRwOi8v
|
||||||
|
b2NzcC5nb2RhZGR5LmNvbS8wNQYDVR0fBC4wLDAqoCigJoYkaHR0cDovL2NybC5n
|
||||||
|
b2RhZGR5LmNvbS9nZHJvb3QtZzIuY3JsMEYGA1UdIAQ/MD0wOwYEVR0gADAzMDEG
|
||||||
|
CCsGAQUFBwIBFiVodHRwczovL2NlcnRzLmdvZGFkZHkuY29tL3JlcG9zaXRvcnkv
|
||||||
|
MA0GCSqGSIb3DQEBCwUAA4IBAQAIfmyTEMg4uJapkEv/oV9PBO9sPpyIBslQj6Zz
|
||||||
|
91cxG7685C/b+LrTW+C05+Z5Yg4MotdqY3MxtfWoSKQ7CC2iXZDXtHwlTxFWMMS2
|
||||||
|
RJ17LJ3lXubvDGGqv+QqG+6EnriDfcFDzkSnE3ANkR/0yBOtg2DZ2HKocyQetawi
|
||||||
|
DsoXiWJYRBuriSUBAA/NxBti21G00w9RKpv0vHP8ds42pM3Z2Czqrpv1KrKQ0U11
|
||||||
|
GIo/ikGQI31bS/6kA1ibRrLDYGCD+H1QQc7CoZDDu+8CL9IVVO5EFdkKrqeKM+2x
|
||||||
|
LXY2JtwE65/3YR8V3Idv7kaWKK2hJn0KCacuBKONvPi8BDAB
|
||||||
|
-----END CERTIFICATE-----
|
||||||
|
-----BEGIN CERTIFICATE-----
|
||||||
|
MIIEfTCCA2WgAwIBAgIDG+cVMA0GCSqGSIb3DQEBCwUAMGMxCzAJBgNVBAYTAlVT
|
||||||
|
MSEwHwYDVQQKExhUaGUgR28gRGFkZHkgR3JvdXAsIEluYy4xMTAvBgNVBAsTKEdv
|
||||||
|
IERhZGR5IENsYXNzIDIgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMTQwMTAx
|
||||||
|
MDcwMDAwWhcNMzEwNTMwMDcwMDAwWjCBgzELMAkGA1UEBhMCVVMxEDAOBgNVBAgT
|
||||||
|
B0FyaXpvbmExEzARBgNVBAcTClNjb3R0c2RhbGUxGjAYBgNVBAoTEUdvRGFkZHku
|
||||||
|
Y29tLCBJbmMuMTEwLwYDVQQDEyhHbyBEYWRkeSBSb290IENlcnRpZmljYXRlIEF1
|
||||||
|
dGhvcml0eSAtIEcyMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAv3Fi
|
||||||
|
CPH6WTT3G8kYo/eASVjpIoMTpsUgQwE7hPHmhUmfJ+r2hBtOoLTbcJjHMgGxBT4H
|
||||||
|
Tu70+k8vWTAi56sZVmvigAf88xZ1gDlRe+X5NbZ0TqmNghPktj+pA4P6or6KFWp/
|
||||||
|
3gvDthkUBcrqw6gElDtGfDIN8wBmIsiNaW02jBEYt9OyHGC0OPoCjM7T3UYH3go+
|
||||||
|
6118yHz7sCtTpJJiaVElBWEaRIGMLKlDliPfrDqBmg4pxRyp6V0etp6eMAo5zvGI
|
||||||
|
gPtLXcwy7IViQyU0AlYnAZG0O3AqP26x6JyIAX2f1PnbU21gnb8s51iruF9G/M7E
|
||||||
|
GwM8CetJMVxpRrPgRwIDAQABo4IBFzCCARMwDwYDVR0TAQH/BAUwAwEB/zAOBgNV
|
||||||
|
HQ8BAf8EBAMCAQYwHQYDVR0OBBYEFDqahQcQZyi27/a9BUFuIMGU2g/eMB8GA1Ud
|
||||||
|
IwQYMBaAFNLEsNKR1EwRcbNhyz2h/t2oatTjMDQGCCsGAQUFBwEBBCgwJjAkBggr
|
||||||
|
BgEFBQcwAYYYaHR0cDovL29jc3AuZ29kYWRkeS5jb20vMDIGA1UdHwQrMCkwJ6Al
|
||||||
|
oCOGIWh0dHA6Ly9jcmwuZ29kYWRkeS5jb20vZ2Ryb290LmNybDBGBgNVHSAEPzA9
|
||||||
|
MDsGBFUdIAAwMzAxBggrBgEFBQcCARYlaHR0cHM6Ly9jZXJ0cy5nb2RhZGR5LmNv
|
||||||
|
bS9yZXBvc2l0b3J5LzANBgkqhkiG9w0BAQsFAAOCAQEAWQtTvZKGEacke+1bMc8d
|
||||||
|
H2xwxbhuvk679r6XUOEwf7ooXGKUwuN+M/f7QnaF25UcjCJYdQkMiGVnOQoWCcWg
|
||||||
|
OJekxSOTP7QYpgEGRJHjp2kntFolfzq3Ms3dhP8qOCkzpN1nsoX+oYggHFCJyNwq
|
||||||
|
9kIDN0zmiN/VryTyscPfzLXs4Jlet0lUIDyUGAzHHFIYSaRt4bNYC8nY7NmuHDKO
|
||||||
|
KHAN4v6mF56ED71XcLNa6R+ghlO773z/aQvgSMO3kwvIClTErF0UZzdsyqUvMQg3
|
||||||
|
qm5vjLyb4lddJIGvl5echK1srDdMZvNhkREg5L4wn3qkKQmw4TRfZHcYQFHfjDCm
|
||||||
|
rw==
|
||||||
|
-----END CERTIFICATE-----
|
||||||
|
-----BEGIN CERTIFICATE-----
|
||||||
|
MIIEADCCAuigAwIBAgIBADANBgkqhkiG9w0BAQUFADBjMQswCQYDVQQGEwJVUzEh
|
||||||
|
MB8GA1UEChMYVGhlIEdvIERhZGR5IEdyb3VwLCBJbmMuMTEwLwYDVQQLEyhHbyBE
|
||||||
|
YWRkeSBDbGFzcyAyIENlcnRpZmljYXRpb24gQXV0aG9yaXR5MB4XDTA0MDYyOTE3
|
||||||
|
MDYyMFoXDTM0MDYyOTE3MDYyMFowYzELMAkGA1UEBhMCVVMxITAfBgNVBAoTGFRo
|
||||||
|
ZSBHbyBEYWRkeSBHcm91cCwgSW5jLjExMC8GA1UECxMoR28gRGFkZHkgQ2xhc3Mg
|
||||||
|
MiBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTCCASAwDQYJKoZIhvcNAQEBBQADggEN
|
||||||
|
ADCCAQgCggEBAN6d1+pXGEmhW+vXX0iG6r7d/+TvZxz0ZWizV3GgXne77ZtJ6XCA
|
||||||
|
PVYYYwhv2vLM0D9/AlQiVBDYsoHUwHU9S3/Hd8M+eKsaA7Ugay9qK7HFiH7Eux6w
|
||||||
|
wdhFJ2+qN1j3hybX2C32qRe3H3I2TqYXP2WYktsqbl2i/ojgC95/5Y0V4evLOtXi
|
||||||
|
EqITLdiOr18SPaAIBQi2XKVlOARFmR6jYGB0xUGlcmIbYsUfb18aQr4CUWWoriMY
|
||||||
|
avx4A6lNf4DD+qta/KFApMoZFv6yyO9ecw3ud72a9nmYvLEHZ6IVDd2gWMZEewo+
|
||||||
|
YihfukEHU1jPEX44dMX4/7VpkI+EdOqXG68CAQOjgcAwgb0wHQYDVR0OBBYEFNLE
|
||||||
|
sNKR1EwRcbNhyz2h/t2oatTjMIGNBgNVHSMEgYUwgYKAFNLEsNKR1EwRcbNhyz2h
|
||||||
|
/t2oatTjoWekZTBjMQswCQYDVQQGEwJVUzEhMB8GA1UEChMYVGhlIEdvIERhZGR5
|
||||||
|
IEdyb3VwLCBJbmMuMTEwLwYDVQQLEyhHbyBEYWRkeSBDbGFzcyAyIENlcnRpZmlj
|
||||||
|
YXRpb24gQXV0aG9yaXR5ggEAMAwGA1UdEwQFMAMBAf8wDQYJKoZIhvcNAQEFBQAD
|
||||||
|
ggEBADJL87LKPpH8EsahB4yOd6AzBhRckB4Y9wimPQoZ+YeAEW5p5JYXMP80kWNy
|
||||||
|
OO7MHAGjHZQopDH2esRU1/blMVgDoszOYtuURXO1v0XJJLXVggKtI3lpjbi2Tc7P
|
||||||
|
TMozI+gciKqdi0FuFskg5YmezTvacPd+mSYgFFQlq25zheabIZ0KbIIOqPjCDPoQ
|
||||||
|
HmyW74cNxA9hi63ugyuV+I6ShHI56yDqg+2DzZduCLzrTia2cyvk0/ZM/iZx4mER
|
||||||
|
dEr/VxqHD3VILs9RaRegAhJhldXRQLIQTO7ErBBDpqWeCtWVYpoNz4iCxTIM5Cuf
|
||||||
|
ReYNnyicsbkqWletNw+vHX/bvZ8=
|
||||||
|
-----END CERTIFICATE-----
|
||||||
33
build/mqtt/proto/lock.proto
Normal file
33
build/mqtt/proto/lock.proto
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
// Copyright: (c) 2022-2024, Patrick Broetto <patrick.broetto@gmail.com>
|
||||||
|
// MIT License
|
||||||
|
|
||||||
|
syntax = "proto3";
|
||||||
|
|
||||||
|
package eufy_security_client.lock;
|
||||||
|
|
||||||
|
message DeviceSmartLockMessage {
|
||||||
|
optional uint32 event_type = 1;
|
||||||
|
optional string user_id = 2;
|
||||||
|
optional DeviceSmartLockNotify data = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeviceSmartLockNotify {
|
||||||
|
optional uint64 timestamp = 1;
|
||||||
|
optional string uuid = 2;
|
||||||
|
optional DeviceSmartLockNotifyData data = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DeviceSmartLockNotifyData {
|
||||||
|
optional string station_sn = 1;
|
||||||
|
optional string device_sn = 2;
|
||||||
|
optional uint32 event_type = 3;
|
||||||
|
optional uint64 event_time = 4;
|
||||||
|
optional string short_user_id = 5;
|
||||||
|
optional string unknown1 = 6;
|
||||||
|
optional string nick_name = 7;
|
||||||
|
optional string user_id = 8;
|
||||||
|
optional string unknown2 = 9;
|
||||||
|
optional string device_name = 10;
|
||||||
|
optional string unknown3 = 11;
|
||||||
|
optional string lock_state = 12;
|
||||||
|
}
|
||||||
28
build/mqtt/service.d.ts
vendored
Normal file
28
build/mqtt/service.d.ts
vendored
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
import { TypedEmitter } from "tiny-typed-emitter";
|
||||||
|
import { MQTTServiceEvents } from "./interface";
|
||||||
|
export declare class MQTTService extends TypedEmitter<MQTTServiceEvents> {
|
||||||
|
private readonly CLIENT_ID_FORMAT;
|
||||||
|
private readonly USERNAME_FORMAT;
|
||||||
|
private readonly SUBSCRIBE_NOTICE_FORMAT;
|
||||||
|
private readonly SUBSCRIBE_LOCK_FORMAT;
|
||||||
|
private readonly SUBSCRIBE_DOORBELL_FORMAT;
|
||||||
|
private static proto;
|
||||||
|
private connected;
|
||||||
|
private client;
|
||||||
|
private connecting;
|
||||||
|
private clientID?;
|
||||||
|
private androidID?;
|
||||||
|
private apiBase?;
|
||||||
|
private email?;
|
||||||
|
private subscribeLocks;
|
||||||
|
private deviceSmartLockMessageModel;
|
||||||
|
private constructor();
|
||||||
|
static init(): Promise<MQTTService>;
|
||||||
|
private parseSmartLockMessage;
|
||||||
|
private getMQTTBrokerUrl;
|
||||||
|
connect(clientID: string, androidID: string, apiBase: string, email: string): void;
|
||||||
|
private _subscribeLock;
|
||||||
|
subscribeLock(deviceSN: string): void;
|
||||||
|
isConnected(): boolean;
|
||||||
|
close(): void;
|
||||||
|
}
|
||||||
177
build/mqtt/service.js
Normal file
177
build/mqtt/service.js
Normal file
@ -0,0 +1,177 @@
|
|||||||
|
"use strict";
|
||||||
|
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
var desc = Object.getOwnPropertyDescriptor(m, k);
|
||||||
|
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
||||||
|
desc = { enumerable: true, get: function() { return m[k]; } };
|
||||||
|
}
|
||||||
|
Object.defineProperty(o, k2, desc);
|
||||||
|
}) : (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
o[k2] = m[k];
|
||||||
|
}));
|
||||||
|
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
||||||
|
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
||||||
|
}) : function(o, v) {
|
||||||
|
o["default"] = v;
|
||||||
|
});
|
||||||
|
var __importStar = (this && this.__importStar) || function (mod) {
|
||||||
|
if (mod && mod.__esModule) return mod;
|
||||||
|
var result = {};
|
||||||
|
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
||||||
|
__setModuleDefault(result, mod);
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.MQTTService = void 0;
|
||||||
|
const mqtt = __importStar(require("mqtt"));
|
||||||
|
const tiny_typed_emitter_1 = require("tiny-typed-emitter");
|
||||||
|
const fse = __importStar(require("fs-extra"));
|
||||||
|
const path = __importStar(require("path"));
|
||||||
|
const protobufjs_1 = require("protobufjs");
|
||||||
|
const utils_1 = require("../utils");
|
||||||
|
const logging_1 = require("../logging");
|
||||||
|
const error_1 = require("../error");
|
||||||
|
class MQTTService extends tiny_typed_emitter_1.TypedEmitter {
|
||||||
|
CLIENT_ID_FORMAT = "android_EufySecurity_<user_id>_<android_id>";
|
||||||
|
USERNAME_FORMAT = "eufy_<user_id>";
|
||||||
|
SUBSCRIBE_NOTICE_FORMAT = "/phone/<user_id>/notice";
|
||||||
|
SUBSCRIBE_LOCK_FORMAT = "/phone/smart_lock/<device_sn>/push_message";
|
||||||
|
SUBSCRIBE_DOORBELL_FORMAT = "/phone/doorbell/<device_sn>/push_message";
|
||||||
|
static proto = null;
|
||||||
|
connected = false;
|
||||||
|
client = null;
|
||||||
|
connecting = false;
|
||||||
|
clientID;
|
||||||
|
androidID;
|
||||||
|
apiBase;
|
||||||
|
email;
|
||||||
|
subscribeLocks = [];
|
||||||
|
deviceSmartLockMessageModel;
|
||||||
|
constructor() {
|
||||||
|
super();
|
||||||
|
this.deviceSmartLockMessageModel = MQTTService.proto.lookupType("DeviceSmartLockMessage");
|
||||||
|
}
|
||||||
|
static async init() {
|
||||||
|
try {
|
||||||
|
this.proto = await (0, protobufjs_1.load)(path.join(__dirname, "./proto/lock.proto"));
|
||||||
|
}
|
||||||
|
catch (error) {
|
||||||
|
logging_1.rootMainLogger.error("Error loading MQTT proto lock file", { error: (0, error_1.ensureError)(error) });
|
||||||
|
}
|
||||||
|
return new MQTTService();
|
||||||
|
}
|
||||||
|
parseSmartLockMessage(data) {
|
||||||
|
const message = this.deviceSmartLockMessageModel.decode(data);
|
||||||
|
const object = this.deviceSmartLockMessageModel.toObject(message, {
|
||||||
|
longs: String,
|
||||||
|
enums: String,
|
||||||
|
bytes: String,
|
||||||
|
});
|
||||||
|
return object;
|
||||||
|
}
|
||||||
|
getMQTTBrokerUrl(apiBase) {
|
||||||
|
switch (apiBase) {
|
||||||
|
case "https://security-app.eufylife.com":
|
||||||
|
return "mqtts://security-mqtt.eufylife.com";
|
||||||
|
case "https://security-app-ci.eufylife.com":
|
||||||
|
return "mqtts://security-mqtt-ci.eufylife.com";
|
||||||
|
case "https://security-app-qa.eufylife.com":
|
||||||
|
case "https://security-app-cn-qa.anker-in.com":
|
||||||
|
return "mqtts://security-mqtt-qa.eufylife.com";
|
||||||
|
case "https://security-app-eu.eufylife.com":
|
||||||
|
return "mqtts://security-mqtt-eu.eufylife.com";
|
||||||
|
case "https://security-app-short-qa.eufylife.com":
|
||||||
|
return "mqtts://security-mqtt-short-qa.eufylife.com";
|
||||||
|
default:
|
||||||
|
return "mqtts://security-mqtt.eufylife.com";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
connect(clientID, androidID, apiBase, email) {
|
||||||
|
this.clientID = clientID;
|
||||||
|
this.androidID = androidID;
|
||||||
|
this.apiBase = apiBase;
|
||||||
|
this.email = email;
|
||||||
|
if (!this.connected && !this.connecting && this.clientID && this.androidID && this.apiBase && this.email && this.subscribeLocks.length > 0) {
|
||||||
|
this.connecting = true;
|
||||||
|
this.client = mqtt.connect(this.getMQTTBrokerUrl(apiBase), {
|
||||||
|
keepalive: 60,
|
||||||
|
clean: true,
|
||||||
|
reschedulePings: true,
|
||||||
|
resubscribe: true,
|
||||||
|
port: 8789,
|
||||||
|
username: this.USERNAME_FORMAT.replace("<user_id>", clientID),
|
||||||
|
password: email,
|
||||||
|
ca: fse.readFileSync(path.join(__dirname, "./mqtt-eufy.crt")),
|
||||||
|
clientId: this.CLIENT_ID_FORMAT.replace("<user_id>", clientID).replace("<android_id>", androidID),
|
||||||
|
rejectUnauthorized: false // Some eufy mqtt servers have an expired certificate :(
|
||||||
|
});
|
||||||
|
this.client.on("connect", (_connack) => {
|
||||||
|
this.connected = true;
|
||||||
|
this.connecting = false;
|
||||||
|
this.emit("connect");
|
||||||
|
this.client.subscribe(this.SUBSCRIBE_NOTICE_FORMAT.replace("<user_id>", clientID), { qos: 1 });
|
||||||
|
if (this.subscribeLocks.length > 0) {
|
||||||
|
let lock;
|
||||||
|
while ((lock = this.subscribeLocks.shift()) !== undefined) {
|
||||||
|
this._subscribeLock(lock);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
this.client.on("close", () => {
|
||||||
|
this.connected = false;
|
||||||
|
this.emit("close");
|
||||||
|
});
|
||||||
|
this.client.on("error", (error) => {
|
||||||
|
this.connecting = false;
|
||||||
|
logging_1.rootMQTTLogger.error("MQTT Error", { error: (0, utils_1.getError)(error) });
|
||||||
|
if (error.code === 1 || error.code === 2 || error.code === 4 || error.code === 5)
|
||||||
|
this.client?.end();
|
||||||
|
});
|
||||||
|
this.client.on("message", (topic, message, _packet) => {
|
||||||
|
if (topic.includes("smart_lock")) {
|
||||||
|
const parsedMessage = this.parseSmartLockMessage(message);
|
||||||
|
logging_1.rootMQTTLogger.debug("Received a smart lock message over MQTT", { message: parsedMessage });
|
||||||
|
this.emit("lock message", parsedMessage);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
logging_1.rootMQTTLogger.debug("MQTT message received", { topic: topic, message: message.toString("hex") });
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_subscribeLock(deviceSN) {
|
||||||
|
this.client?.subscribe(this.SUBSCRIBE_LOCK_FORMAT.replace("<device_sn>", deviceSN), { qos: 1 }, (error, granted) => {
|
||||||
|
if (error) {
|
||||||
|
logging_1.rootMQTTLogger.error(`Subscribe error for lock ${deviceSN}`, { error: (0, utils_1.getError)(error), deviceSN: deviceSN });
|
||||||
|
}
|
||||||
|
if (granted) {
|
||||||
|
logging_1.rootMQTTLogger.info(`Successfully registered to MQTT notifications for lock ${deviceSN}`);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
subscribeLock(deviceSN) {
|
||||||
|
if (this.connected) {
|
||||||
|
this._subscribeLock(deviceSN);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (!this.subscribeLocks.includes(deviceSN)) {
|
||||||
|
this.subscribeLocks.push(deviceSN);
|
||||||
|
}
|
||||||
|
if (this.clientID && this.androidID && this.apiBase && this.email)
|
||||||
|
this.connect(this.clientID, this.androidID, this.apiBase, this.email);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
isConnected() {
|
||||||
|
return this.connected;
|
||||||
|
}
|
||||||
|
close() {
|
||||||
|
if (this.connected) {
|
||||||
|
this.client?.end(true);
|
||||||
|
this.connected = false;
|
||||||
|
this.connecting = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.MQTTService = MQTTService;
|
||||||
|
//# sourceMappingURL=service.js.map
|
||||||
1
build/mqtt/service.js.map
Normal file
1
build/mqtt/service.js.map
Normal file
File diff suppressed because one or more lines are too long
59
build/p2p/ble.d.ts
vendored
Normal file
59
build/p2p/ble.d.ts
vendored
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
export declare enum BleParameterIndex {
|
||||||
|
ZERO = -96,
|
||||||
|
ONE = -95,
|
||||||
|
TWO = -94,
|
||||||
|
THREE = -93,
|
||||||
|
FOUR = -92,
|
||||||
|
FIVE = -91,
|
||||||
|
SIX = -90,
|
||||||
|
SEVEN = -89,
|
||||||
|
EIGHT = -88,
|
||||||
|
NINE = -87,
|
||||||
|
TEN = -86,
|
||||||
|
ELEVEN = -85,
|
||||||
|
TWELVE = -84,
|
||||||
|
THIRTEEN = -83
|
||||||
|
}
|
||||||
|
export declare class BleCommandFactory {
|
||||||
|
private static readonly HEADER;
|
||||||
|
private data?;
|
||||||
|
private commandCode?;
|
||||||
|
private versionCode?;
|
||||||
|
private dataType?;
|
||||||
|
private packageFlag?;
|
||||||
|
private unknown?;
|
||||||
|
private additionalDataSeparatorByte?;
|
||||||
|
private additionalData?;
|
||||||
|
private responseCode?;
|
||||||
|
private encrypted?;
|
||||||
|
private partial?;
|
||||||
|
static parseLockV12(data: string | Buffer): BleCommandFactory;
|
||||||
|
static parseSmartSafe(data: string | Buffer): BleCommandFactory;
|
||||||
|
static parseSmartLock(data: string | Buffer): BleCommandFactory;
|
||||||
|
toString: () => string;
|
||||||
|
private setResponseCode;
|
||||||
|
getResponseCode(): number | undefined;
|
||||||
|
setVersionCode(version: number): BleCommandFactory;
|
||||||
|
getVersionCode(): number | undefined;
|
||||||
|
setCommandCode(command: number): BleCommandFactory;
|
||||||
|
getCommandCode(): number | undefined;
|
||||||
|
setDataType(type: number): BleCommandFactory;
|
||||||
|
getDataType(): number | undefined;
|
||||||
|
setPackageFlag(flag: number): BleCommandFactory;
|
||||||
|
getPackageFlag(): number | undefined;
|
||||||
|
setAdditionalDataSeparator(separator: number): BleCommandFactory;
|
||||||
|
getAdditionalDataSeparator(): Buffer | undefined;
|
||||||
|
setAdditionalData(data: Buffer): BleCommandFactory;
|
||||||
|
getAdditionalData(): Buffer | undefined;
|
||||||
|
setData(data: Buffer): BleCommandFactory;
|
||||||
|
getData(): Buffer | undefined;
|
||||||
|
setUnknown(data: Buffer): BleCommandFactory;
|
||||||
|
static generateHash(data: Buffer): number;
|
||||||
|
isEncrypted(): boolean | undefined;
|
||||||
|
setEncrypted(encrypted: boolean): BleCommandFactory;
|
||||||
|
isPartial(): boolean | undefined;
|
||||||
|
setPartial(partial: boolean): BleCommandFactory;
|
||||||
|
getLockV12Command(): Buffer;
|
||||||
|
getSmartSafeCommand(): Buffer;
|
||||||
|
getSmartLockCommand(): Buffer;
|
||||||
|
}
|
||||||
280
build/p2p/ble.js
Normal file
280
build/p2p/ble.js
Normal file
@ -0,0 +1,280 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.BleCommandFactory = exports.BleParameterIndex = void 0;
|
||||||
|
const error_1 = require("./error");
|
||||||
|
var BleParameterIndex;
|
||||||
|
(function (BleParameterIndex) {
|
||||||
|
BleParameterIndex[BleParameterIndex["ZERO"] = -96] = "ZERO";
|
||||||
|
BleParameterIndex[BleParameterIndex["ONE"] = -95] = "ONE";
|
||||||
|
BleParameterIndex[BleParameterIndex["TWO"] = -94] = "TWO";
|
||||||
|
BleParameterIndex[BleParameterIndex["THREE"] = -93] = "THREE";
|
||||||
|
BleParameterIndex[BleParameterIndex["FOUR"] = -92] = "FOUR";
|
||||||
|
BleParameterIndex[BleParameterIndex["FIVE"] = -91] = "FIVE";
|
||||||
|
BleParameterIndex[BleParameterIndex["SIX"] = -90] = "SIX";
|
||||||
|
BleParameterIndex[BleParameterIndex["SEVEN"] = -89] = "SEVEN";
|
||||||
|
BleParameterIndex[BleParameterIndex["EIGHT"] = -88] = "EIGHT";
|
||||||
|
BleParameterIndex[BleParameterIndex["NINE"] = -87] = "NINE";
|
||||||
|
BleParameterIndex[BleParameterIndex["TEN"] = -86] = "TEN";
|
||||||
|
BleParameterIndex[BleParameterIndex["ELEVEN"] = -85] = "ELEVEN";
|
||||||
|
BleParameterIndex[BleParameterIndex["TWELVE"] = -84] = "TWELVE";
|
||||||
|
BleParameterIndex[BleParameterIndex["THIRTEEN"] = -83] = "THIRTEEN";
|
||||||
|
})(BleParameterIndex || (exports.BleParameterIndex = BleParameterIndex = {}));
|
||||||
|
class BleCommandFactory {
|
||||||
|
static HEADER = Buffer.from([-1, 9]);
|
||||||
|
data;
|
||||||
|
commandCode;
|
||||||
|
versionCode;
|
||||||
|
dataType;
|
||||||
|
packageFlag;
|
||||||
|
unknown;
|
||||||
|
additionalDataSeparatorByte;
|
||||||
|
additionalData;
|
||||||
|
responseCode;
|
||||||
|
encrypted;
|
||||||
|
partial;
|
||||||
|
static parseLockV12(data) {
|
||||||
|
if (typeof data === "string") {
|
||||||
|
data = Buffer.from(data, "hex");
|
||||||
|
}
|
||||||
|
if (data.readInt8(0) !== BleCommandFactory.HEADER[0] && data.readInt8(1) !== BleCommandFactory.HEADER[1]) {
|
||||||
|
throw new error_1.BleInvalidDataHeaderError("Invalid BLE data header");
|
||||||
|
}
|
||||||
|
const fac = new BleCommandFactory();
|
||||||
|
fac.setVersionCode(data.readUint8(4));
|
||||||
|
fac.setCommandCode(data.readUint8(6));
|
||||||
|
fac.setDataType(data.readUint8());
|
||||||
|
fac.setPackageFlag(data.readInt8(7));
|
||||||
|
fac.setResponseCode(fac.getPackageFlag() === -64 ? data.readUint8(8) : data.readUint8(12));
|
||||||
|
fac.setData(data.subarray(fac.getPackageFlag() === -64 ? 8 : 12, data.length - 1)); //TODO: Verify if position 8 is correct for data (i think it should be 9 or 13)...
|
||||||
|
if (BleCommandFactory.generateHash(data.subarray(0, data.length - 1)) !== data.readUint8(data.length - 1)) {
|
||||||
|
throw new error_1.BleInvalidChecksumError("Invalid BLE data, checksum mismatch");
|
||||||
|
}
|
||||||
|
return fac;
|
||||||
|
}
|
||||||
|
static parseSmartSafe(data) {
|
||||||
|
return BleCommandFactory.parseLockV12(data);
|
||||||
|
}
|
||||||
|
static parseSmartLock(data) {
|
||||||
|
if (typeof data === "string") {
|
||||||
|
data = Buffer.from(data, "hex");
|
||||||
|
}
|
||||||
|
if (data.length < 9 || (data.readInt8(0) !== BleCommandFactory.HEADER[0] && data.readInt8(1) !== BleCommandFactory.HEADER[1])) {
|
||||||
|
throw new error_1.BleInvalidDataHeaderError("Invalid BLE data header");
|
||||||
|
}
|
||||||
|
if (BleCommandFactory.generateHash(data.subarray(0, data.length - 1)) !== data.readUint8(data.length - 1)) {
|
||||||
|
throw new error_1.BleInvalidChecksumError("Invalid BLE data, checksum mismatch");
|
||||||
|
}
|
||||||
|
const fac = new BleCommandFactory();
|
||||||
|
const flags = data.readUint16BE(7);
|
||||||
|
fac.setVersionCode(data.readUint8(4));
|
||||||
|
fac.setDataType(data.readUint8(6));
|
||||||
|
fac.setPartial((flags >> 15) === 1);
|
||||||
|
fac.setEncrypted(((flags << 1) >> 15) === 1);
|
||||||
|
fac.setCommandCode(((flags << 4) & 32767) >> 4);
|
||||||
|
fac.setData(data.subarray(9, data.length - 1));
|
||||||
|
return fac;
|
||||||
|
}
|
||||||
|
toString = () => {
|
||||||
|
return `BleCommandFactory (versionCode: ${this.versionCode} commandCode: ${this.commandCode} dataType: ${this.dataType} partial: ${this.partial} encrypted: ${this.encrypted} data: ${this.data?.toString("hex")} packageFlag: ${this.packageFlag} responseCode: ${this.responseCode})`;
|
||||||
|
};
|
||||||
|
setResponseCode(code) {
|
||||||
|
this.responseCode = code;
|
||||||
|
}
|
||||||
|
getResponseCode() {
|
||||||
|
return this.responseCode;
|
||||||
|
}
|
||||||
|
setVersionCode(version) {
|
||||||
|
this.versionCode = version;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
getVersionCode() {
|
||||||
|
return this.versionCode;
|
||||||
|
}
|
||||||
|
setCommandCode(command) {
|
||||||
|
this.commandCode = command;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
getCommandCode() {
|
||||||
|
return this.commandCode;
|
||||||
|
}
|
||||||
|
setDataType(type) {
|
||||||
|
this.dataType = type;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
getDataType() {
|
||||||
|
return this.dataType;
|
||||||
|
}
|
||||||
|
setPackageFlag(flag) {
|
||||||
|
this.packageFlag = flag;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
getPackageFlag() {
|
||||||
|
return this.packageFlag;
|
||||||
|
}
|
||||||
|
setAdditionalDataSeparator(separator) {
|
||||||
|
this.additionalDataSeparatorByte = Buffer.from([separator]);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
getAdditionalDataSeparator() {
|
||||||
|
return this.additionalDataSeparatorByte;
|
||||||
|
}
|
||||||
|
setAdditionalData(data) {
|
||||||
|
this.additionalData = data;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
getAdditionalData() {
|
||||||
|
return this.additionalData;
|
||||||
|
}
|
||||||
|
setData(data) {
|
||||||
|
this.data = data;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
getData() {
|
||||||
|
return this.data;
|
||||||
|
}
|
||||||
|
setUnknown(data) {
|
||||||
|
this.unknown = data;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
static generateHash(data) {
|
||||||
|
let result = 0;
|
||||||
|
for (const value of data) {
|
||||||
|
result = result ^ value;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
isEncrypted() {
|
||||||
|
return this.encrypted;
|
||||||
|
}
|
||||||
|
setEncrypted(encrypted) {
|
||||||
|
this.encrypted = encrypted;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
isPartial() {
|
||||||
|
return this.partial;
|
||||||
|
}
|
||||||
|
setPartial(partial) {
|
||||||
|
this.partial = partial;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
getLockV12Command() {
|
||||||
|
if (this.versionCode === undefined)
|
||||||
|
throw new error_1.BleVersionCodeError("BleCommandFactory version code value missing");
|
||||||
|
if (this.dataType === undefined)
|
||||||
|
throw new error_1.BleDataTypeError("BleCommandFactory data type value missing");
|
||||||
|
if (this.commandCode === undefined)
|
||||||
|
throw new error_1.BleCommandCodeError("BleCommandFactory command code value missing");
|
||||||
|
if (this.data === undefined)
|
||||||
|
throw new error_1.BleDataError("BleCommandFactory data value missing");
|
||||||
|
if (this.additionalData === undefined)
|
||||||
|
throw new error_1.BleAdditionalDataError("BleCommandFactory additional data value missing");
|
||||||
|
this.setAdditionalDataSeparator(BleParameterIndex.ZERO);
|
||||||
|
const bVersionCode = Buffer.from([this.versionCode]);
|
||||||
|
const bDataType = Buffer.from([this.dataType]);
|
||||||
|
const bCommandCode = Buffer.from([this.commandCode]);
|
||||||
|
const bPackageFlag = this.packageFlag === undefined ? Buffer.from([-64]) : Buffer.from([this.packageFlag]);
|
||||||
|
const bAdditionalDataLength = Buffer.from([this.additionalData.length]);
|
||||||
|
const size = Buffer.allocUnsafe(2);
|
||||||
|
size.writeInt16LE(BleCommandFactory.HEADER.length +
|
||||||
|
size.length +
|
||||||
|
bVersionCode.length +
|
||||||
|
bDataType.length +
|
||||||
|
bCommandCode.length +
|
||||||
|
bPackageFlag.length +
|
||||||
|
this.additionalDataSeparatorByte.length +
|
||||||
|
bAdditionalDataLength.length +
|
||||||
|
this.additionalData.length +
|
||||||
|
this.data.length +
|
||||||
|
1 // Hash
|
||||||
|
);
|
||||||
|
const data = Buffer.concat([
|
||||||
|
BleCommandFactory.HEADER,
|
||||||
|
size,
|
||||||
|
bVersionCode,
|
||||||
|
bDataType,
|
||||||
|
bCommandCode,
|
||||||
|
bPackageFlag,
|
||||||
|
this.additionalDataSeparatorByte,
|
||||||
|
bAdditionalDataLength,
|
||||||
|
this.additionalData,
|
||||||
|
this.data
|
||||||
|
]);
|
||||||
|
const hash = BleCommandFactory.generateHash(data);
|
||||||
|
return Buffer.concat([data, Buffer.from([hash])]);
|
||||||
|
}
|
||||||
|
getSmartSafeCommand() {
|
||||||
|
if (this.versionCode === undefined)
|
||||||
|
throw new error_1.BleVersionCodeError("BleCommandFactory version code value missing");
|
||||||
|
if (this.dataType === undefined)
|
||||||
|
throw new error_1.BleDataTypeError("BleCommandFactory data type value missing");
|
||||||
|
if (this.commandCode === undefined)
|
||||||
|
throw new error_1.BleCommandCodeError("BleCommandFactory command code value missing");
|
||||||
|
if (this.data === undefined)
|
||||||
|
throw new error_1.BleDataError("BleCommandFactory data value missing");
|
||||||
|
const bVersionCode = Buffer.from([this.versionCode]);
|
||||||
|
const bDataType = Buffer.from([this.dataType]);
|
||||||
|
const bCommandCode = Buffer.from([this.commandCode]);
|
||||||
|
const bPackageFlag = this.packageFlag === undefined ? Buffer.from([-64]) : Buffer.from([this.packageFlag]);
|
||||||
|
const size = Buffer.allocUnsafe(2);
|
||||||
|
size.writeInt16LE(BleCommandFactory.HEADER.length +
|
||||||
|
size.length +
|
||||||
|
bVersionCode.length +
|
||||||
|
bDataType.length +
|
||||||
|
bCommandCode.length +
|
||||||
|
bPackageFlag.length +
|
||||||
|
this.data.length +
|
||||||
|
1 // Hash
|
||||||
|
);
|
||||||
|
const data = Buffer.concat([
|
||||||
|
BleCommandFactory.HEADER,
|
||||||
|
size,
|
||||||
|
bVersionCode,
|
||||||
|
bDataType,
|
||||||
|
bCommandCode,
|
||||||
|
bPackageFlag,
|
||||||
|
this.data
|
||||||
|
]);
|
||||||
|
const hash = BleCommandFactory.generateHash(data);
|
||||||
|
return Buffer.concat([data, Buffer.from([hash])]);
|
||||||
|
}
|
||||||
|
getSmartLockCommand() {
|
||||||
|
if (this.versionCode === undefined)
|
||||||
|
throw new error_1.BleVersionCodeError("BleCommandFactory version code value missing");
|
||||||
|
if (this.dataType === undefined)
|
||||||
|
throw new error_1.BleDataTypeError("BleCommandFactory data type value missing");
|
||||||
|
if (this.commandCode === undefined)
|
||||||
|
throw new error_1.BleCommandCodeError("BleCommandFactory command code value missing");
|
||||||
|
if (this.data === undefined)
|
||||||
|
throw new error_1.BleDataError("BleCommandFactory data value missing");
|
||||||
|
const bVersionCode = Buffer.from([this.versionCode]);
|
||||||
|
const bDataType = Buffer.from([this.dataType]);
|
||||||
|
const unknown = Buffer.alloc(1);
|
||||||
|
const partial = false;
|
||||||
|
const encrypted = true;
|
||||||
|
const commandCodeEncoded = Buffer.allocUnsafe(2);
|
||||||
|
commandCodeEncoded.writeInt16BE(((partial ? 1 : 0) << 15) + ((encrypted ? 1 : 0) << 14) + this.commandCode);
|
||||||
|
const size = Buffer.allocUnsafe(2);
|
||||||
|
size.writeInt16LE(BleCommandFactory.HEADER.length +
|
||||||
|
size.length +
|
||||||
|
bVersionCode.length +
|
||||||
|
unknown.length +
|
||||||
|
bDataType.length +
|
||||||
|
commandCodeEncoded.length +
|
||||||
|
this.data.length +
|
||||||
|
1 // Hash
|
||||||
|
);
|
||||||
|
const data = Buffer.concat([
|
||||||
|
BleCommandFactory.HEADER,
|
||||||
|
size,
|
||||||
|
bVersionCode,
|
||||||
|
unknown,
|
||||||
|
bDataType,
|
||||||
|
commandCodeEncoded,
|
||||||
|
this.data
|
||||||
|
]);
|
||||||
|
const hash = BleCommandFactory.generateHash(data);
|
||||||
|
return Buffer.concat([data, Buffer.from([hash])]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleCommandFactory = BleCommandFactory;
|
||||||
|
//# sourceMappingURL=ble.js.map
|
||||||
1
build/p2p/ble.js.map
Normal file
1
build/p2p/ble.js.map
Normal file
File diff suppressed because one or more lines are too long
49
build/p2p/error.d.ts
vendored
Normal file
49
build/p2p/error.d.ts
vendored
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
import { BaseError, Jsonable } from "../error";
|
||||||
|
export declare class BleVersionCodeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BleCommandCodeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BleDataTypeError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BleDataError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BleAdditionalDataError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BleAdditionalDataSeparatorError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BleInvalidDataHeaderError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BleInvalidChecksumError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
69
build/p2p/error.js
Normal file
69
build/p2p/error.js
Normal file
@ -0,0 +1,69 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.BleInvalidChecksumError = exports.BleInvalidDataHeaderError = exports.BleAdditionalDataSeparatorError = exports.BleAdditionalDataError = exports.BleDataError = exports.BleDataTypeError = exports.BleCommandCodeError = exports.BleVersionCodeError = void 0;
|
||||||
|
const error_1 = require("../error");
|
||||||
|
class BleVersionCodeError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BleVersionCodeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleVersionCodeError = BleVersionCodeError;
|
||||||
|
class BleCommandCodeError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BleCommandCodeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleCommandCodeError = BleCommandCodeError;
|
||||||
|
class BleDataTypeError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BleDataTypeError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleDataTypeError = BleDataTypeError;
|
||||||
|
class BleDataError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BleDataError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleDataError = BleDataError;
|
||||||
|
class BleAdditionalDataError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BleAdditionalDataError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleAdditionalDataError = BleAdditionalDataError;
|
||||||
|
class BleAdditionalDataSeparatorError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BleAdditionalDataSeparatorError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleAdditionalDataSeparatorError = BleAdditionalDataSeparatorError;
|
||||||
|
class BleInvalidDataHeaderError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BleInvalidDataHeaderError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleInvalidDataHeaderError = BleInvalidDataHeaderError;
|
||||||
|
class BleInvalidChecksumError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BleInvalidChecksumError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BleInvalidChecksumError = BleInvalidChecksumError;
|
||||||
|
//# sourceMappingURL=error.js.map
|
||||||
1
build/p2p/error.js.map
Normal file
1
build/p2p/error.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"error.js","sourceRoot":"","sources":["../../src/p2p/error.ts"],"names":[],"mappings":";;;AAAA,oCAA+C;AAC/C,MAAa,mBAAoB,SAAQ,iBAAS;IAC9C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,mBAAmB,CAAC,IAAI,CAAC;IACzC,CAAC;CACJ;AAND,kDAMC;AAED,MAAa,mBAAoB,SAAQ,iBAAS;IAC9C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,mBAAmB,CAAC,IAAI,CAAC;IACzC,CAAC;CACJ;AAND,kDAMC;AAED,MAAa,gBAAiB,SAAQ,iBAAS;IAC3C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,gBAAgB,CAAC,IAAI,CAAC;IACtC,CAAC;CACJ;AAND,4CAMC;AAED,MAAa,YAAa,SAAQ,iBAAS;IACvC,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,YAAY,CAAC,IAAI,CAAC;IAClC,CAAC;CACJ;AAND,oCAMC;AAED,MAAa,sBAAuB,SAAQ,iBAAS;IACjD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,sBAAsB,CAAC,IAAI,CAAC;IAC5C,CAAC;CACJ;AAND,wDAMC;AAED,MAAa,+BAAgC,SAAQ,iBAAS;IAC1D,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,+BAA+B,CAAC,IAAI,CAAC;IACrD,CAAC;CACJ;AAND,0EAMC;AAED,MAAa,yBAA0B,SAAQ,iBAAS;IACpD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,yBAAyB,CAAC,IAAI,CAAC;IAC/C,CAAC;CACJ;AAND,8DAMC;AAED,MAAa,uBAAwB,SAAQ,iBAAS;IAClD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,uBAAuB,CAAC,IAAI,CAAC;IAC7C,CAAC;CACJ;AAND,0DAMC"}
|
||||||
8
build/p2p/index.d.ts
vendored
Normal file
8
build/p2p/index.d.ts
vendored
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
export * from "./interfaces";
|
||||||
|
export * from "./models";
|
||||||
|
export * from "./session";
|
||||||
|
export * from "./types";
|
||||||
|
export * from "./talkback";
|
||||||
|
export * from "./ble";
|
||||||
|
export * from "./error";
|
||||||
|
export { isPrivateIp, getLocalIpAddress } from "./utils";
|
||||||
28
build/p2p/index.js
Normal file
28
build/p2p/index.js
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
"use strict";
|
||||||
|
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
var desc = Object.getOwnPropertyDescriptor(m, k);
|
||||||
|
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
||||||
|
desc = { enumerable: true, get: function() { return m[k]; } };
|
||||||
|
}
|
||||||
|
Object.defineProperty(o, k2, desc);
|
||||||
|
}) : (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
o[k2] = m[k];
|
||||||
|
}));
|
||||||
|
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
||||||
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.getLocalIpAddress = exports.isPrivateIp = void 0;
|
||||||
|
__exportStar(require("./interfaces"), exports);
|
||||||
|
__exportStar(require("./models"), exports);
|
||||||
|
__exportStar(require("./session"), exports);
|
||||||
|
__exportStar(require("./types"), exports);
|
||||||
|
__exportStar(require("./talkback"), exports);
|
||||||
|
__exportStar(require("./ble"), exports);
|
||||||
|
__exportStar(require("./error"), exports);
|
||||||
|
var utils_1 = require("./utils");
|
||||||
|
Object.defineProperty(exports, "isPrivateIp", { enumerable: true, get: function () { return utils_1.isPrivateIp; } });
|
||||||
|
Object.defineProperty(exports, "getLocalIpAddress", { enumerable: true, get: function () { return utils_1.getLocalIpAddress; } });
|
||||||
|
//# sourceMappingURL=index.js.map
|
||||||
1
build/p2p/index.js.map
Normal file
1
build/p2p/index.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/p2p/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAAA,+CAA6B;AAC7B,2CAAyB;AACzB,4CAA0B;AAC1B,0CAAwB;AACxB,6CAA2B;AAC3B,wCAAsB;AACtB,0CAAwB;AACxB,iCAAyD;AAAhD,oGAAA,WAAW,OAAA;AAAE,0GAAA,iBAAiB,OAAA"}
|
||||||
388
build/p2p/interfaces.d.ts
vendored
Normal file
388
build/p2p/interfaces.d.ts
vendored
Normal file
@ -0,0 +1,388 @@
|
|||||||
|
import * as NodeRSA from "node-rsa";
|
||||||
|
import { Readable } from "stream";
|
||||||
|
import { SortedMap } from "sweet-collections";
|
||||||
|
import { AlarmMode, DeviceType, MicStatus, ParamType, TriggerType, VideoType } from "../http/types";
|
||||||
|
import { Address, CmdCameraInfoResponse, CommandResult, CustomData, StorageInfoBodyHB3 } from "./models";
|
||||||
|
import { TalkbackStream } from "./talkback";
|
||||||
|
import { AlarmEvent, AudioCodec, CommandType, DatabaseReturnCode, IndoorSoloSmartdropCommandType, P2PDataType, SmartSafeAlarm911Event, SmartSafeShakeAlarmEvent, P2PStorageType, TFCardStatus, VideoCodec, InternalP2PCommandType } from "./types";
|
||||||
|
export interface P2PClientProtocolEvents {
|
||||||
|
"alarm mode": (mode: AlarmMode) => void;
|
||||||
|
"camera info": (cameraInfo: CmdCameraInfoResponse) => void;
|
||||||
|
"connect": (address: Address) => void;
|
||||||
|
"close": () => void;
|
||||||
|
"command": (result: CommandResult) => void;
|
||||||
|
"download started": (channel: number, metadata: StreamMetadata, videoStream: Readable, audioStream: Readable) => void;
|
||||||
|
"download finished": (channel: number) => void;
|
||||||
|
"livestream started": (channel: number, metadata: StreamMetadata, videoStream: Readable, audioStream: Readable) => void;
|
||||||
|
"livestream stopped": (channel: number) => void;
|
||||||
|
"livestream error": (channel: number, error: Error) => void;
|
||||||
|
"wifi rssi": (channel: number, rssi: number) => void;
|
||||||
|
"rtsp url": (channel: number, rtspUrl: string) => void;
|
||||||
|
"parameter": (channel: number, param: number, value: string) => void;
|
||||||
|
"timeout": () => void;
|
||||||
|
"runtime state": (channel: number, batteryLevel: number, temperature: number) => void;
|
||||||
|
"charging state": (channel: number, chargeType: number, batteryLevel: number) => void;
|
||||||
|
"rtsp livestream started": (channel: number) => void;
|
||||||
|
"rtsp livestream stopped": (channel: number) => void;
|
||||||
|
"floodlight manual switch": (channel: number, enabled: boolean) => void;
|
||||||
|
"alarm delay": (alarmDelayEvent: AlarmEvent, alarmDelay: number) => void;
|
||||||
|
"alarm armed": () => void;
|
||||||
|
"alarm event": (alarmEvent: AlarmEvent) => void;
|
||||||
|
"talkback started": (channel: number, talkbackStream: TalkbackStream) => void;
|
||||||
|
"talkback stopped": (channel: number) => void;
|
||||||
|
"talkback error": (channel: number, error: Error) => void;
|
||||||
|
"secondary command": (result: CommandResult) => void;
|
||||||
|
"jammed": (channel: number) => void;
|
||||||
|
"low battery": (channel: number) => void;
|
||||||
|
"shake alarm": (channel: number, detail: SmartSafeShakeAlarmEvent) => void;
|
||||||
|
"911 alarm": (channel: number, detail: SmartSafeAlarm911Event) => void;
|
||||||
|
"wrong try-protect alarm": (channel: number) => void;
|
||||||
|
"sd info ex": (sdStatus: TFCardStatus, sdCapacity: number, sdCapacityAvailable: number) => void;
|
||||||
|
"image download": (file: string, image: Buffer) => void;
|
||||||
|
"tfcard status": (channel: number, status: TFCardStatus) => void;
|
||||||
|
"database query latest": (returnCode: DatabaseReturnCode, data: Array<DatabaseQueryLatestInfo>) => void;
|
||||||
|
"database query local": (returnCode: DatabaseReturnCode, data: Array<DatabaseQueryLocal>) => void;
|
||||||
|
"database count by date": (returnCode: DatabaseReturnCode, data: Array<DatabaseCountByDate>) => void;
|
||||||
|
"database delete": (returnCode: DatabaseReturnCode, failedIds: Array<unknown>) => void;
|
||||||
|
"sensor status": (channel: number, status: number) => void;
|
||||||
|
"garage door status": (channel: number, doorId: number, status: number) => void;
|
||||||
|
"storage info hb3": (channel: number, storageInfo: StorageInfoBodyHB3) => void;
|
||||||
|
"sequence error": (channel: number, command: number, sequence: number, serialnumber: string) => void;
|
||||||
|
}
|
||||||
|
export interface P2PQueueMessage {
|
||||||
|
p2pCommandType: InternalP2PCommandType;
|
||||||
|
p2pCommand: P2PCommand;
|
||||||
|
nestedCommandType?: CommandType;
|
||||||
|
nestedCommandType2?: number;
|
||||||
|
timestamp: number;
|
||||||
|
customData?: CustomData;
|
||||||
|
}
|
||||||
|
export interface P2PMessageState {
|
||||||
|
sequence: number;
|
||||||
|
commandType: CommandType;
|
||||||
|
nestedCommandType?: CommandType | IndoorSoloSmartdropCommandType | ParamType;
|
||||||
|
nestedCommandType2?: number;
|
||||||
|
channel: number;
|
||||||
|
data: Buffer;
|
||||||
|
retries: number;
|
||||||
|
acknowledged: boolean;
|
||||||
|
returnCode?: number;
|
||||||
|
retryTimeout?: NodeJS.Timeout;
|
||||||
|
timeout?: NodeJS.Timeout;
|
||||||
|
customData?: CustomData;
|
||||||
|
}
|
||||||
|
export interface P2PMessageParts {
|
||||||
|
[index: number]: Buffer;
|
||||||
|
}
|
||||||
|
export interface P2PMessage {
|
||||||
|
bytesToRead: number;
|
||||||
|
type: P2PDataType;
|
||||||
|
seqNo: number;
|
||||||
|
data: Buffer;
|
||||||
|
}
|
||||||
|
export interface P2PDataHeader {
|
||||||
|
commandId: number;
|
||||||
|
bytesToRead: number;
|
||||||
|
channel: number;
|
||||||
|
signCode: number;
|
||||||
|
type: number;
|
||||||
|
}
|
||||||
|
export interface P2PDataMessage extends P2PDataHeader {
|
||||||
|
seqNo: number;
|
||||||
|
dataType: P2PDataType;
|
||||||
|
data: Buffer;
|
||||||
|
}
|
||||||
|
export interface P2PDataMessageBuilder {
|
||||||
|
header: P2PDataHeader;
|
||||||
|
bytesRead: number;
|
||||||
|
messages: P2PMessageParts;
|
||||||
|
}
|
||||||
|
export interface P2PDataMessageState {
|
||||||
|
leftoverData: Buffer;
|
||||||
|
queuedData: SortedMap<number, P2PMessage>;
|
||||||
|
rsaKey: NodeRSA | null;
|
||||||
|
videoStream: Readable | null;
|
||||||
|
audioStream: Readable | null;
|
||||||
|
invalidStream: boolean;
|
||||||
|
p2pStreaming: boolean;
|
||||||
|
p2pStreamNotStarted: boolean;
|
||||||
|
p2pStreamChannel: number;
|
||||||
|
p2pStreamFirstAudioDataReceived: boolean;
|
||||||
|
p2pStreamFirstVideoDataReceived: boolean;
|
||||||
|
p2pStreamMetadata: StreamMetadata;
|
||||||
|
p2pStreamingTimeout?: NodeJS.Timeout;
|
||||||
|
rtspStream: {
|
||||||
|
[index: number]: boolean;
|
||||||
|
};
|
||||||
|
rtspStreaming: {
|
||||||
|
[index: number]: boolean;
|
||||||
|
};
|
||||||
|
waitForSeqNoTimeout?: NodeJS.Timeout;
|
||||||
|
waitForAudioData?: NodeJS.Timeout;
|
||||||
|
receivedFirstIFrame: boolean;
|
||||||
|
preFrameVideoData: Buffer;
|
||||||
|
p2pTalkback: boolean;
|
||||||
|
p2pTalkbackChannel: number;
|
||||||
|
}
|
||||||
|
export interface P2PDataMessageVideo {
|
||||||
|
streamType: number;
|
||||||
|
videoSeqNo: number;
|
||||||
|
videoFPS: number;
|
||||||
|
videoWidth: number;
|
||||||
|
videoHeight: number;
|
||||||
|
videoTimestamp: number;
|
||||||
|
videoDataLength: number;
|
||||||
|
aesKey: string;
|
||||||
|
}
|
||||||
|
export interface P2PDataMessageAudio {
|
||||||
|
audioType: number;
|
||||||
|
audioSeqNo: number;
|
||||||
|
audioTimestamp: number;
|
||||||
|
audioDataLength: number;
|
||||||
|
}
|
||||||
|
export interface StreamMetadata {
|
||||||
|
videoCodec: VideoCodec;
|
||||||
|
videoFPS: number;
|
||||||
|
videoWidth: number;
|
||||||
|
videoHeight: number;
|
||||||
|
audioCodec: AudioCodec;
|
||||||
|
}
|
||||||
|
export interface DeviceSerial {
|
||||||
|
[index: number]: {
|
||||||
|
sn: string;
|
||||||
|
adminUserId: string;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface P2PCommand {
|
||||||
|
commandType: CommandType;
|
||||||
|
value?: number | string;
|
||||||
|
valueSub?: number;
|
||||||
|
strValue?: string;
|
||||||
|
strValueSub?: string;
|
||||||
|
channel?: number;
|
||||||
|
}
|
||||||
|
export interface P2PVideoMessageState {
|
||||||
|
sequence: number;
|
||||||
|
channel: number;
|
||||||
|
data: Buffer;
|
||||||
|
retries: number;
|
||||||
|
timeout?: NodeJS.Timeout;
|
||||||
|
}
|
||||||
|
export interface P2PDatabaseQueryLatestInfoResponse {
|
||||||
|
device_sn: string;
|
||||||
|
payload: {
|
||||||
|
event_count: number;
|
||||||
|
crop_hb3_path: string;
|
||||||
|
crop_cloud_path: string;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface P2PDatabaseCountByDateResponse {
|
||||||
|
days: string;
|
||||||
|
count: number;
|
||||||
|
}
|
||||||
|
export interface P2PDatabaseQueryLocalHistoryRecordInfo {
|
||||||
|
record_id: number;
|
||||||
|
account: string;
|
||||||
|
station_sn: string;
|
||||||
|
device_sn: string;
|
||||||
|
device_type: DeviceType;
|
||||||
|
start_time: string;
|
||||||
|
end_time: string;
|
||||||
|
frame_num: number;
|
||||||
|
storage_type: P2PStorageType;
|
||||||
|
storage_cloud: boolean;
|
||||||
|
cipher_id: number;
|
||||||
|
vision: number;
|
||||||
|
video_type: VideoType;
|
||||||
|
has_lock: boolean;
|
||||||
|
automation_id: number;
|
||||||
|
trigger_type: TriggerType;
|
||||||
|
push_mode: number;
|
||||||
|
mic_status: MicStatus;
|
||||||
|
res_change: number;
|
||||||
|
res_best_width: number;
|
||||||
|
res_best_height: number;
|
||||||
|
self_learning: number;
|
||||||
|
int_reserve: number;
|
||||||
|
int_extra: number;
|
||||||
|
storage_path: string;
|
||||||
|
thumb_path: string;
|
||||||
|
write_status: number;
|
||||||
|
str_extra: string;
|
||||||
|
cloud_path: string;
|
||||||
|
folder_size: number;
|
||||||
|
storage_status: number;
|
||||||
|
storage_label: string;
|
||||||
|
time_zone: string;
|
||||||
|
mp4_cloud: string;
|
||||||
|
snapshot_cloud: string;
|
||||||
|
table_version: string;
|
||||||
|
update_time: string;
|
||||||
|
}
|
||||||
|
export interface P2PDatabaseQueryLocalRecordCropPictureInfo {
|
||||||
|
picture_id: number;
|
||||||
|
record_id: number;
|
||||||
|
station_sn: string;
|
||||||
|
device_sn: string;
|
||||||
|
detection_type: number;
|
||||||
|
person_id: number;
|
||||||
|
crop_path: string;
|
||||||
|
event_time: string;
|
||||||
|
str_reserve: string;
|
||||||
|
person_recog_flag: boolean;
|
||||||
|
crop_pic_quality: number;
|
||||||
|
pic_marking_flag: boolean;
|
||||||
|
group_id: number;
|
||||||
|
int_reserve: number;
|
||||||
|
crop_id: number;
|
||||||
|
start_time: string;
|
||||||
|
reserve2_int: number;
|
||||||
|
reserve2_date: string;
|
||||||
|
reserve2_string: string;
|
||||||
|
storage_type: P2PStorageType;
|
||||||
|
storage_status: number;
|
||||||
|
storage_label: string;
|
||||||
|
table_version: string;
|
||||||
|
update_time: string;
|
||||||
|
}
|
||||||
|
export interface P2PDatabaseQueryLocalResponse {
|
||||||
|
payload: Array<P2PDatabaseQueryLocalHistoryRecordInfo> | Array<P2PDatabaseQueryLocalRecordCropPictureInfo>;
|
||||||
|
table_name: string;
|
||||||
|
}
|
||||||
|
export interface P2PDatabaseDeleteResponse {
|
||||||
|
failed_delete: Array<unknown>;
|
||||||
|
}
|
||||||
|
export interface P2PDatabaseResponse {
|
||||||
|
data: Array<P2PDatabaseQueryLatestInfoResponse> | Array<P2PDatabaseCountByDateResponse> | Array<P2PDatabaseQueryLocalResponse> | P2PDatabaseDeleteResponse;
|
||||||
|
start_id?: number;
|
||||||
|
end_id?: number;
|
||||||
|
count?: number;
|
||||||
|
transaction: string;
|
||||||
|
table: string;
|
||||||
|
cmd: number;
|
||||||
|
mIntRet: DatabaseReturnCode;
|
||||||
|
version: string;
|
||||||
|
msg: string;
|
||||||
|
}
|
||||||
|
export interface DatabaseQueryLatestInfoBase {
|
||||||
|
device_sn: string;
|
||||||
|
event_count: number;
|
||||||
|
}
|
||||||
|
export interface DatabaseQueryLatestInfoCloud extends DatabaseQueryLatestInfoBase {
|
||||||
|
crop_cloud_path: string;
|
||||||
|
}
|
||||||
|
export interface DatabaseQueryLatestInfoLocal extends DatabaseQueryLatestInfoBase {
|
||||||
|
crop_local_path: string;
|
||||||
|
}
|
||||||
|
export type DatabaseQueryLatestInfo = DatabaseQueryLatestInfoCloud | DatabaseQueryLatestInfoLocal;
|
||||||
|
export interface DatabaseCountByDate {
|
||||||
|
day: Date;
|
||||||
|
count: number;
|
||||||
|
}
|
||||||
|
export interface HistoryRecordInfo {
|
||||||
|
device_type: DeviceType;
|
||||||
|
account: string;
|
||||||
|
start_time: Date;
|
||||||
|
end_time: Date;
|
||||||
|
frame_num: number;
|
||||||
|
storage_type: P2PStorageType;
|
||||||
|
storage_cloud: boolean;
|
||||||
|
cipher_id: number;
|
||||||
|
vision: number;
|
||||||
|
video_type: VideoType;
|
||||||
|
has_lock: boolean;
|
||||||
|
automation_id: number;
|
||||||
|
trigger_type: TriggerType;
|
||||||
|
push_mode: number;
|
||||||
|
mic_status: MicStatus;
|
||||||
|
res_change: number;
|
||||||
|
res_best_width: number;
|
||||||
|
res_best_height: number;
|
||||||
|
self_learning: number;
|
||||||
|
storage_path: string;
|
||||||
|
thumb_path: string;
|
||||||
|
write_status: number;
|
||||||
|
cloud_path: string;
|
||||||
|
folder_size: number;
|
||||||
|
storage_status: number;
|
||||||
|
storage_label: string;
|
||||||
|
time_zone: string;
|
||||||
|
mp4_cloud: string;
|
||||||
|
snapshot_cloud: string;
|
||||||
|
table_version: string;
|
||||||
|
}
|
||||||
|
export interface CropPictureInfo {
|
||||||
|
picture_id: number;
|
||||||
|
detection_type: number;
|
||||||
|
person_id: number;
|
||||||
|
crop_path: string;
|
||||||
|
event_time: Date | null;
|
||||||
|
person_recog_flag: boolean;
|
||||||
|
crop_pic_quality: number;
|
||||||
|
pic_marking_flag: boolean;
|
||||||
|
group_id: number;
|
||||||
|
crop_id: number;
|
||||||
|
start_time: Date;
|
||||||
|
storage_type: P2PStorageType;
|
||||||
|
storage_status: number;
|
||||||
|
storage_label: string;
|
||||||
|
table_version: string;
|
||||||
|
update_time: string;
|
||||||
|
}
|
||||||
|
export interface DatabaseQueryLocal {
|
||||||
|
record_id: number;
|
||||||
|
station_sn: string;
|
||||||
|
device_sn?: string;
|
||||||
|
history: HistoryRecordInfo;
|
||||||
|
picture: Array<CropPictureInfo>;
|
||||||
|
}
|
||||||
|
export interface RGBColor {
|
||||||
|
red: number;
|
||||||
|
green: number;
|
||||||
|
blue: number;
|
||||||
|
}
|
||||||
|
export interface InternalColoredLighting {
|
||||||
|
color: number;
|
||||||
|
}
|
||||||
|
export interface DynamicLighting {
|
||||||
|
name: string;
|
||||||
|
mode: number;
|
||||||
|
speed: number;
|
||||||
|
colors: Array<RGBColor>;
|
||||||
|
}
|
||||||
|
export interface InternalDynamicLighting {
|
||||||
|
name: string;
|
||||||
|
mode: number;
|
||||||
|
id: number;
|
||||||
|
speed: number;
|
||||||
|
colors: Array<number>;
|
||||||
|
}
|
||||||
|
export interface MotionZonePoint {
|
||||||
|
x: number;
|
||||||
|
y: number;
|
||||||
|
}
|
||||||
|
export interface MotionZonePoints {
|
||||||
|
points: Array<MotionZonePoint>;
|
||||||
|
}
|
||||||
|
export interface MotionZone {
|
||||||
|
polygens: Array<MotionZonePoints>;
|
||||||
|
}
|
||||||
|
export interface VideoStreamingRecordingQuality {
|
||||||
|
mode_0: {
|
||||||
|
quality: number;
|
||||||
|
};
|
||||||
|
mode_1: {
|
||||||
|
quality: number;
|
||||||
|
};
|
||||||
|
cur_mode: number;
|
||||||
|
}
|
||||||
|
export interface CrossTrackingGroupEntry {
|
||||||
|
value: Array<string>;
|
||||||
|
}
|
||||||
|
export interface CustomDataType {
|
||||||
|
[index: number]: {
|
||||||
|
channel: number;
|
||||||
|
customData: CustomData;
|
||||||
|
timestamp: number;
|
||||||
|
};
|
||||||
|
}
|
||||||
3
build/p2p/interfaces.js
Normal file
3
build/p2p/interfaces.js
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
//# sourceMappingURL=interfaces.js.map
|
||||||
1
build/p2p/interfaces.js.map
Normal file
1
build/p2p/interfaces.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"interfaces.js","sourceRoot":"","sources":["../../src/p2p/interfaces.ts"],"names":[],"mappings":""}
|
||||||
284
build/p2p/models.d.ts
vendored
Normal file
284
build/p2p/models.d.ts
vendored
Normal file
@ -0,0 +1,284 @@
|
|||||||
|
import { PropertyValue } from "../http";
|
||||||
|
import { CommandName, PropertyName } from "../http/types";
|
||||||
|
import { SmartSafeEventValueDetail } from "../push/models";
|
||||||
|
import { CommandType } from "./types";
|
||||||
|
export interface Address {
|
||||||
|
host: string;
|
||||||
|
port: number;
|
||||||
|
}
|
||||||
|
export interface CmdCameraInfoResponse {
|
||||||
|
params: Array<{
|
||||||
|
dev_type: number;
|
||||||
|
param_type: number;
|
||||||
|
param_value: string;
|
||||||
|
}>;
|
||||||
|
main_sw_version: string;
|
||||||
|
sec_sw_version: string;
|
||||||
|
db_bypass_str?: Array<{
|
||||||
|
channel: number;
|
||||||
|
param_type: number;
|
||||||
|
param_value: string;
|
||||||
|
}>;
|
||||||
|
}
|
||||||
|
export interface PropertyData {
|
||||||
|
name: PropertyName;
|
||||||
|
value: PropertyValue;
|
||||||
|
}
|
||||||
|
export interface CommandData {
|
||||||
|
name: CommandName;
|
||||||
|
value?: any;
|
||||||
|
}
|
||||||
|
export interface CustomData {
|
||||||
|
property?: PropertyData;
|
||||||
|
command?: CommandData;
|
||||||
|
onSuccess?: () => void;
|
||||||
|
onFailure?: () => void;
|
||||||
|
}
|
||||||
|
export interface CommandResult {
|
||||||
|
customData?: CustomData;
|
||||||
|
command_type: CommandType;
|
||||||
|
channel: number;
|
||||||
|
return_code: number;
|
||||||
|
}
|
||||||
|
export interface CmdNotifyPayload {
|
||||||
|
cmd: number;
|
||||||
|
payload: ESLStationP2PThroughData | ESLAdvancedLockStatusNotification | SmartSafeSettingsNotification | SmartSafeStatusNotification | ESLBleV12P2PThroughData | EntrySensorStatus | GarageDoorStatus | StorageInfoHB3 | SmartLockP2PSequenceData | string;
|
||||||
|
payloadLen?: number;
|
||||||
|
}
|
||||||
|
export interface ESLStationP2PThroughData {
|
||||||
|
channel?: number;
|
||||||
|
lock_cmd: number;
|
||||||
|
lock_payload: string;
|
||||||
|
seq_num?: number;
|
||||||
|
stationSn?: string;
|
||||||
|
}
|
||||||
|
export interface ESLAdvancedLockStatusNotification {
|
||||||
|
code: number;
|
||||||
|
slBattery: string;
|
||||||
|
slState: string;
|
||||||
|
trigger: number;
|
||||||
|
}
|
||||||
|
export interface ESLAdvancedLockStatusNotificationT8530 extends ESLAdvancedLockStatusNotification {
|
||||||
|
slOpenDirection: string;
|
||||||
|
}
|
||||||
|
export interface SmartSafeSettingsNotification {
|
||||||
|
data: string;
|
||||||
|
prj_id: number;
|
||||||
|
}
|
||||||
|
export interface SmartSafeStatusNotification {
|
||||||
|
event_type: number;
|
||||||
|
event_time: number;
|
||||||
|
event_value: number | SmartSafeEventValueDetail;
|
||||||
|
}
|
||||||
|
export interface SmartSafeNotificationResponse {
|
||||||
|
versionCode: number;
|
||||||
|
commandCode: number;
|
||||||
|
packageFlag: number;
|
||||||
|
dataType: number;
|
||||||
|
responseCode: number;
|
||||||
|
data: Buffer;
|
||||||
|
}
|
||||||
|
export interface LockAdvancedOnOffRequestBasePayload {
|
||||||
|
shortUserId: string;
|
||||||
|
slOperation: number;
|
||||||
|
userId: string;
|
||||||
|
userName: string;
|
||||||
|
}
|
||||||
|
export interface LockAdvancedOnOffRequestPayload extends LockAdvancedOnOffRequestBasePayload {
|
||||||
|
seq_num: number;
|
||||||
|
}
|
||||||
|
export interface AdvancedLockSetParamsType {
|
||||||
|
[index: string]: unknown;
|
||||||
|
autoLockTime: number;
|
||||||
|
isAutoLock: number;
|
||||||
|
isLockNotification: number;
|
||||||
|
isNotification: number;
|
||||||
|
isOneTouchLock: number;
|
||||||
|
isSchedule: number;
|
||||||
|
isScramblePasscode: number;
|
||||||
|
isUnLockNotification: number;
|
||||||
|
isWrongTryProtect: number;
|
||||||
|
lockDownTime: number;
|
||||||
|
lockSound: number;
|
||||||
|
paramType: number;
|
||||||
|
scheduleEnd: string;
|
||||||
|
scheduleStart: string;
|
||||||
|
wrongTryTime: number;
|
||||||
|
seq_num: number;
|
||||||
|
}
|
||||||
|
export interface AdvancedLockSetParamsTypeT8520 {
|
||||||
|
[index: string]: unknown;
|
||||||
|
autoLockTime: number;
|
||||||
|
isAutoLock: number;
|
||||||
|
isLockNotification: number;
|
||||||
|
isNotification: number;
|
||||||
|
isOneTouchLock: number;
|
||||||
|
isSchedule: number;
|
||||||
|
isScramblePasscode: number;
|
||||||
|
isUnLockNotification: number;
|
||||||
|
isWrongTryProtect: number;
|
||||||
|
lockDownTime: number;
|
||||||
|
lockOpenDirection: number;
|
||||||
|
lockVolume: number;
|
||||||
|
nightVisionEnhance: number;
|
||||||
|
openLeftAlarmEnable: number;
|
||||||
|
openLeftAlarmScheduleEnd: string;
|
||||||
|
openLeftAlarmScheduleStart: string;
|
||||||
|
openLeftAlarmScheduled: number;
|
||||||
|
openLeftAlarmTimer: number;
|
||||||
|
openLeftAlarmWays: number;
|
||||||
|
paramType: number;
|
||||||
|
scheduleEnd: string;
|
||||||
|
scheduleStart: string;
|
||||||
|
tamperAlarmEnable: number;
|
||||||
|
tamperAlarmScheduleEnd: string;
|
||||||
|
tamperAlarmScheduleStart: string;
|
||||||
|
tamperAlarmScheduled: number;
|
||||||
|
tamperAlarmWays: number;
|
||||||
|
wrongTryTime: number;
|
||||||
|
}
|
||||||
|
export interface LockP2PCommandType {
|
||||||
|
commandType: CommandType;
|
||||||
|
value: string;
|
||||||
|
channel: number;
|
||||||
|
aesKey: string;
|
||||||
|
}
|
||||||
|
export interface LockP2PCommandPayloadType {
|
||||||
|
key: string;
|
||||||
|
account_id: string;
|
||||||
|
cmd: CommandType;
|
||||||
|
mChannel: number;
|
||||||
|
mValue3: number;
|
||||||
|
payload: string;
|
||||||
|
}
|
||||||
|
export interface ESLBleV12P2PThroughData {
|
||||||
|
dev_sn: string;
|
||||||
|
lock_payload: string;
|
||||||
|
}
|
||||||
|
export interface LockV12P2PCommandPayloadType {
|
||||||
|
account_id: string;
|
||||||
|
cmd: CommandType;
|
||||||
|
mChannel: number;
|
||||||
|
mValue3: number;
|
||||||
|
payload: {
|
||||||
|
apiCommand: number;
|
||||||
|
lock_payload: string;
|
||||||
|
seq_num: number;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface LockV12P2PCommandType {
|
||||||
|
commandType: CommandType;
|
||||||
|
value: string;
|
||||||
|
}
|
||||||
|
export interface SmartSafeP2PCommandPayloadType {
|
||||||
|
account_id: string;
|
||||||
|
cmd: CommandType;
|
||||||
|
mChannel: number;
|
||||||
|
mValue3: number;
|
||||||
|
payload: {
|
||||||
|
data: string;
|
||||||
|
prj_id: CommandType;
|
||||||
|
seq_num: number;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface SmartSafeP2PCommandType {
|
||||||
|
commandType: CommandType;
|
||||||
|
value: string;
|
||||||
|
channel: number;
|
||||||
|
}
|
||||||
|
export interface CmdDatabaseImageResponse {
|
||||||
|
file: string;
|
||||||
|
content: string;
|
||||||
|
}
|
||||||
|
export interface EntrySensorStatus {
|
||||||
|
status: number;
|
||||||
|
}
|
||||||
|
export interface GarageDoorStatus {
|
||||||
|
type: number;
|
||||||
|
notify_tag: string;
|
||||||
|
door_id: number;
|
||||||
|
}
|
||||||
|
export interface StorageInfoHB3 {
|
||||||
|
cmd: number;
|
||||||
|
version: number;
|
||||||
|
mIntRet: number;
|
||||||
|
msg: string;
|
||||||
|
old_storage_label: string;
|
||||||
|
cur_storage_label: string;
|
||||||
|
body: StorageInfoBodyHB3;
|
||||||
|
}
|
||||||
|
export interface StorageInfoBodyHB3 {
|
||||||
|
body_version: number;
|
||||||
|
storage_days: number;
|
||||||
|
storage_events: number;
|
||||||
|
con_video_hours: number;
|
||||||
|
format_transaction: string;
|
||||||
|
format_errcode: number;
|
||||||
|
hdd_info: StorageInfoHddHB3;
|
||||||
|
move_disk_info: StorageInfoMoveDiskInfoHB3;
|
||||||
|
emmc_info: StorageInfoEmmcHB3;
|
||||||
|
}
|
||||||
|
export interface StorageInfoHddHB3 {
|
||||||
|
serial_number: string;
|
||||||
|
disk_path: string;
|
||||||
|
disk_size: number;
|
||||||
|
system_size: number;
|
||||||
|
disk_used: number;
|
||||||
|
video_used: number;
|
||||||
|
video_size: number;
|
||||||
|
cur_temperate: number;
|
||||||
|
parted_status: number;
|
||||||
|
work_status: number;
|
||||||
|
hdd_label: string;
|
||||||
|
health: number;
|
||||||
|
device_module: string;
|
||||||
|
hdd_type: number;
|
||||||
|
}
|
||||||
|
export interface StorageInfoMoveDiskInfoHB3 {
|
||||||
|
disk_path: string;
|
||||||
|
disk_size: number;
|
||||||
|
disk_used: number;
|
||||||
|
part_layout_arr: string[];
|
||||||
|
data: string[];
|
||||||
|
}
|
||||||
|
export interface StorageInfoEmmcHB3 {
|
||||||
|
disk_nominal: number;
|
||||||
|
disk_size: number;
|
||||||
|
system_size: number;
|
||||||
|
disk_used: number;
|
||||||
|
data_used_percent: number;
|
||||||
|
swap_size: number;
|
||||||
|
video_size: number;
|
||||||
|
video_used: number;
|
||||||
|
data_partition_size: number;
|
||||||
|
eol_percent: number;
|
||||||
|
work_status: number;
|
||||||
|
health: number;
|
||||||
|
}
|
||||||
|
export interface SmartLockP2PCommandPayloadType {
|
||||||
|
account_id: string;
|
||||||
|
cmd: CommandType;
|
||||||
|
mChannel: number;
|
||||||
|
mValue3: number;
|
||||||
|
payload: {
|
||||||
|
apiCommand: number;
|
||||||
|
lock_payload: string;
|
||||||
|
seq_num: number;
|
||||||
|
time: number;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
export interface SmartLockP2PCommandType {
|
||||||
|
commandType: CommandType;
|
||||||
|
value: string;
|
||||||
|
}
|
||||||
|
export interface SmartLockP2PThroughData {
|
||||||
|
dev_sn: string;
|
||||||
|
lock_payload: string;
|
||||||
|
time: string;
|
||||||
|
}
|
||||||
|
export interface SmartLockP2PSequenceData {
|
||||||
|
lock_cmd: number;
|
||||||
|
seq_num: number;
|
||||||
|
dev_sn: string;
|
||||||
|
bus_type?: number;
|
||||||
|
}
|
||||||
3
build/p2p/models.js
Normal file
3
build/p2p/models.js
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
//# sourceMappingURL=models.js.map
|
||||||
1
build/p2p/models.js.map
Normal file
1
build/p2p/models.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"models.js","sourceRoot":"","sources":["../../src/p2p/models.ts"],"names":[],"mappings":""}
|
||||||
186
build/p2p/session.d.ts
vendored
Normal file
186
build/p2p/session.d.ts
vendored
Normal file
@ -0,0 +1,186 @@
|
|||||||
|
import { TypedEmitter } from "tiny-typed-emitter";
|
||||||
|
import * as NodeRSA from "node-rsa";
|
||||||
|
import { Address, CustomData } from "./models";
|
||||||
|
import { CommandType, P2PDataType, P2PConnectionType } from "./types";
|
||||||
|
import { P2PClientProtocolEvents, P2PCommand } from "./interfaces";
|
||||||
|
import { StationListResponse } from "../http/models";
|
||||||
|
import { HTTPApi } from "../http/api";
|
||||||
|
export declare class P2PClientProtocol extends TypedEmitter<P2PClientProtocolEvents> {
|
||||||
|
private readonly MAX_RETRIES;
|
||||||
|
private readonly MAX_COMMAND_RESULT_WAIT;
|
||||||
|
private readonly MAX_GATEWAY_COMMAND_RESULT_WAIT;
|
||||||
|
private readonly MAX_CONNECTION_TIMEOUT;
|
||||||
|
private readonly MAX_AKNOWLEDGE_TIMEOUT;
|
||||||
|
private readonly MAX_LOOKUP_TIMEOUT;
|
||||||
|
private readonly LOCAL_LOOKUP_RETRY_TIMEOUT;
|
||||||
|
private readonly LOOKUP_RETRY_TIMEOUT;
|
||||||
|
private readonly LOOKUP2_TIMEOUT;
|
||||||
|
private readonly LOOKUP2_RETRY_TIMEOUT;
|
||||||
|
private readonly MAX_EXPECTED_SEQNO_WAIT;
|
||||||
|
private readonly HEARTBEAT_INTERVAL;
|
||||||
|
private readonly MAX_COMMAND_QUEUE_TIMEOUT;
|
||||||
|
private readonly AUDIO_CODEC_ANALYZE_TIMEOUT;
|
||||||
|
private readonly KEEPALIVE_INTERVAL;
|
||||||
|
private readonly ESD_DISCONNECT_TIMEOUT;
|
||||||
|
private readonly MAX_STREAM_DATA_WAIT;
|
||||||
|
private readonly RESEND_NOT_ACKNOWLEDGED_COMMAND;
|
||||||
|
private readonly UDP_RECVBUFFERSIZE_BYTES;
|
||||||
|
private readonly MAX_PAYLOAD_BYTES;
|
||||||
|
private readonly MAX_PACKET_BYTES;
|
||||||
|
private readonly MAX_VIDEO_PACKET_BYTES;
|
||||||
|
private readonly P2P_DATA_HEADER_BYTES;
|
||||||
|
private readonly MAX_SEQUENCE_NUMBER;
|
||||||
|
private readonly LOOP_RUNAWAY_LIMIT;
|
||||||
|
private readonly SEQUENCE_PROCESSING_BOUNDARY;
|
||||||
|
private socket;
|
||||||
|
private binded;
|
||||||
|
private connected;
|
||||||
|
private connecting;
|
||||||
|
private terminating;
|
||||||
|
private p2pTurnHandshaking;
|
||||||
|
private p2pTurnConfirmed;
|
||||||
|
private seqNumber;
|
||||||
|
private offsetDataSeqNumber;
|
||||||
|
private videoSeqNumber;
|
||||||
|
private lockSeqNumber;
|
||||||
|
private expectedSeqNo;
|
||||||
|
private currentMessageBuilder;
|
||||||
|
private currentMessageState;
|
||||||
|
private talkbackStream?;
|
||||||
|
private downloadTotalBytes;
|
||||||
|
private downloadReceivedBytes;
|
||||||
|
private cloudAddresses;
|
||||||
|
private messageStates;
|
||||||
|
private messageVideoStates;
|
||||||
|
private sendQueue;
|
||||||
|
private connectTimeout?;
|
||||||
|
private lookupTimeout?;
|
||||||
|
private localLookupRetryTimeout?;
|
||||||
|
private lookupRetryTimeout?;
|
||||||
|
private lookup2Timeout?;
|
||||||
|
private lookup2RetryTimeout?;
|
||||||
|
private heartbeatTimeout?;
|
||||||
|
private keepaliveTimeout?;
|
||||||
|
private esdDisconnectTimeout?;
|
||||||
|
private secondaryCommandTimeout?;
|
||||||
|
private connectTime;
|
||||||
|
private lastPong;
|
||||||
|
private lastPongData;
|
||||||
|
private connectionType;
|
||||||
|
private energySavingDevice;
|
||||||
|
private p2pSeqMapping;
|
||||||
|
private p2pDataSeqNumber;
|
||||||
|
private connectAddress;
|
||||||
|
private localIPAddress;
|
||||||
|
private preferredIPAddress;
|
||||||
|
private listeningPort;
|
||||||
|
private dskKey;
|
||||||
|
private dskExpiration;
|
||||||
|
private deviceSNs;
|
||||||
|
private api;
|
||||||
|
private rawStation;
|
||||||
|
private customDataStaging;
|
||||||
|
private lockPublicKey;
|
||||||
|
private lockAESKeys;
|
||||||
|
private channel;
|
||||||
|
private encryption;
|
||||||
|
private p2pKey?;
|
||||||
|
private enableEmbeddedPKCS1Support;
|
||||||
|
constructor(rawStation: StationListResponse, api: HTTPApi, ipAddress?: string, listeningPort?: number, publicKey?: string, enableEmbeddedPKCS1Support?: boolean);
|
||||||
|
private _incrementSequence;
|
||||||
|
private _isBetween;
|
||||||
|
private _wasSequenceNumberAlreadyProcessed;
|
||||||
|
private _initialize;
|
||||||
|
private initializeMessageBuilder;
|
||||||
|
private initializeMessageState;
|
||||||
|
private _clearTimeout;
|
||||||
|
private _clearMessageStateTimeouts;
|
||||||
|
private _clearMessageVideoStateTimeouts;
|
||||||
|
private _clearHeartbeatTimeout;
|
||||||
|
private _clearKeepaliveTimeout;
|
||||||
|
private _clearConnectTimeout;
|
||||||
|
private _clearLookupTimeout;
|
||||||
|
private _clearLocalLookupRetryTimeout;
|
||||||
|
private _clearLookupRetryTimeout;
|
||||||
|
private _clearLookup2RetryTimeout;
|
||||||
|
private _clearLookup2Timeout;
|
||||||
|
private _clearESDDisconnectTimeout;
|
||||||
|
private _clearSecondaryCommandTimeout;
|
||||||
|
private sendMessage;
|
||||||
|
private _disconnected;
|
||||||
|
private closeEnergySavingDevice;
|
||||||
|
private renewDSKKey;
|
||||||
|
private localLookup;
|
||||||
|
private cloudLookup;
|
||||||
|
private cloudLookup2;
|
||||||
|
private cloudLookupWithTurnServer;
|
||||||
|
private localLookupByAddress;
|
||||||
|
private cloudLookupByAddress;
|
||||||
|
private cloudLookupByAddress2;
|
||||||
|
private cloudLookupByAddressWithTurnServer;
|
||||||
|
isConnected(): boolean;
|
||||||
|
private _startConnectTimeout;
|
||||||
|
private _connect;
|
||||||
|
private lookup;
|
||||||
|
connect(host?: string): Promise<void>;
|
||||||
|
private sendCamCheck;
|
||||||
|
private sendCamCheck2;
|
||||||
|
sendPing(address: Address): Promise<void>;
|
||||||
|
sendCommandWithIntString(p2pcommand: P2PCommand, customData?: CustomData): void;
|
||||||
|
sendCommandWithInt(p2pcommand: P2PCommand, customData?: CustomData): void;
|
||||||
|
sendCommandWithStringPayload(p2pcommand: P2PCommand, customData?: CustomData): void;
|
||||||
|
sendCommandWithString(p2pcommand: P2PCommand, customData?: CustomData): void;
|
||||||
|
sendCommandPing(channel?: number): void;
|
||||||
|
sendCommandDevicePing(channel?: number): void;
|
||||||
|
sendCommandWithoutData(commandType: CommandType, channel?: number): void;
|
||||||
|
private sendQueuedMessage;
|
||||||
|
private sendCommand;
|
||||||
|
private resendNotAcknowledgedCommand;
|
||||||
|
private _sendCommand;
|
||||||
|
private handleMsg;
|
||||||
|
private parseDataMessage;
|
||||||
|
private handleData;
|
||||||
|
private isIFrame;
|
||||||
|
private waitForStreamData;
|
||||||
|
private handleDataBinaryAndVideo;
|
||||||
|
private handleDataControl;
|
||||||
|
private sendAck;
|
||||||
|
private getDataType;
|
||||||
|
close(): Promise<void>;
|
||||||
|
private getHeartbeatInterval;
|
||||||
|
private onClose;
|
||||||
|
private onError;
|
||||||
|
private scheduleHeartbeat;
|
||||||
|
private scheduleP2PKeepalive;
|
||||||
|
getDownloadRSAPrivateKey(): NodeRSA;
|
||||||
|
setDownloadRSAPrivateKeyPem(pem: string): void;
|
||||||
|
getRSAPrivateKey(): NodeRSA | null;
|
||||||
|
private initializeStream;
|
||||||
|
private endStream;
|
||||||
|
private endRTSPStream;
|
||||||
|
private emitStreamStartEvent;
|
||||||
|
private emitStreamStopEvent;
|
||||||
|
isStreaming(channel: number, datatype: P2PDataType): boolean;
|
||||||
|
isLiveStreaming(channel: number): boolean;
|
||||||
|
private isCurrentlyStreaming;
|
||||||
|
isRTSPLiveStreaming(channel: number): boolean;
|
||||||
|
isDownloading(channel: number): boolean;
|
||||||
|
getLockSequenceNumber(): number;
|
||||||
|
incLockSequenceNumber(): number;
|
||||||
|
setConnectionType(type: P2PConnectionType): void;
|
||||||
|
getConnectionType(): P2PConnectionType;
|
||||||
|
isEnergySavingDevice(): boolean;
|
||||||
|
private getDSKKeys;
|
||||||
|
updateRawStation(value: StationListResponse): void;
|
||||||
|
private initializeTalkbackStream;
|
||||||
|
private sendTalkbackAudioFrame;
|
||||||
|
private onTalkbackStreamClose;
|
||||||
|
private onTalkbackStreamError;
|
||||||
|
private _sendVideoData;
|
||||||
|
isTalkbackOngoing(channel: number): boolean;
|
||||||
|
startTalkback(channel?: number): void;
|
||||||
|
stopTalkback(channel?: number): void;
|
||||||
|
setLockAESKey(commandCode: number, aesKey: string): void;
|
||||||
|
getLockAESKey(commandCode: number): string | undefined;
|
||||||
|
isConnecting(): boolean;
|
||||||
|
}
|
||||||
2678
build/p2p/session.js
Normal file
2678
build/p2p/session.js
Normal file
File diff suppressed because it is too large
Load Diff
1
build/p2p/session.js.map
Normal file
1
build/p2p/session.js.map
Normal file
File diff suppressed because one or more lines are too long
8
build/p2p/talkback.d.ts
vendored
Normal file
8
build/p2p/talkback.d.ts
vendored
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
import { Transform } from "stream";
|
||||||
|
export declare class TalkbackStream extends Transform {
|
||||||
|
private isStreaming;
|
||||||
|
constructor();
|
||||||
|
_transform(data: Buffer, _encoding: string, callback: (err?: Error | null) => void): void;
|
||||||
|
startTalkback(): void;
|
||||||
|
stopTalkback(): void;
|
||||||
|
}
|
||||||
23
build/p2p/talkback.js
Normal file
23
build/p2p/talkback.js
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.TalkbackStream = void 0;
|
||||||
|
const stream_1 = require("stream");
|
||||||
|
class TalkbackStream extends stream_1.Transform {
|
||||||
|
isStreaming = false;
|
||||||
|
constructor() {
|
||||||
|
super();
|
||||||
|
}
|
||||||
|
_transform(data, _encoding, callback) {
|
||||||
|
if (this.isStreaming)
|
||||||
|
this.push(data);
|
||||||
|
callback();
|
||||||
|
}
|
||||||
|
startTalkback() {
|
||||||
|
this.isStreaming = true;
|
||||||
|
}
|
||||||
|
stopTalkback() {
|
||||||
|
this.isStreaming = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.TalkbackStream = TalkbackStream;
|
||||||
|
//# sourceMappingURL=talkback.js.map
|
||||||
1
build/p2p/talkback.js.map
Normal file
1
build/p2p/talkback.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"talkback.js","sourceRoot":"","sources":["../../src/p2p/talkback.ts"],"names":[],"mappings":";;;AAAA,mCAAmC;AAEnC,MAAa,cAAe,SAAQ,kBAAS;IAEjC,WAAW,GAAG,KAAK,CAAC;IAE5B;QACI,KAAK,EAAE,CAAC;IACZ,CAAC;IAED,UAAU,CAAC,IAAY,EAAE,SAAiB,EAAE,QAAsC;QAC9E,IAAG,IAAI,CAAC,WAAW;YACf,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACpB,QAAQ,EAAE,CAAC;IACf,CAAC;IAEM,aAAa;QAChB,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC;IAC5B,CAAC;IAEM,YAAY;QACf,IAAI,CAAC,WAAW,GAAG,KAAK,CAAC;IAC7B,CAAC;CACJ;AArBD,wCAqBC"}
|
||||||
1164
build/p2p/types.d.ts
vendored
Normal file
1164
build/p2p/types.d.ts
vendored
Normal file
File diff suppressed because it is too large
Load Diff
1219
build/p2p/types.js
Normal file
1219
build/p2p/types.js
Normal file
File diff suppressed because it is too large
Load Diff
1
build/p2p/types.js.map
Normal file
1
build/p2p/types.js.map
Normal file
File diff suppressed because one or more lines are too long
72
build/p2p/utils.d.ts
vendored
Normal file
72
build/p2p/utils.d.ts
vendored
Normal file
@ -0,0 +1,72 @@
|
|||||||
|
import { Socket } from "dgram";
|
||||||
|
import NodeRSA from "node-rsa";
|
||||||
|
import { P2PMessageParts, P2PMessageState, P2PQueueMessage, RGBColor } from "./interfaces";
|
||||||
|
import { CommandType, ESLCommand, LockV12P2PCommand, SmartSafeCommandCode, VideoCodec, EncryptionType, SmartLockP2PCommand, SmartLockFunctionType, SmartLockCommand } from "./types";
|
||||||
|
import { Address, LockP2PCommandType, SmartSafeNotificationResponse, SmartSafeP2PCommandType } from "./models";
|
||||||
|
import { DeviceType } from "../http/types";
|
||||||
|
export declare const MAGIC_WORD = "XZYH";
|
||||||
|
export declare const isPrivateIp: (ip: string) => boolean;
|
||||||
|
export declare const getLocalIpAddress: (init?: string) => string;
|
||||||
|
export declare const isP2PCommandEncrypted: (cmd: CommandType) => boolean;
|
||||||
|
export declare const getP2PCommandEncryptionKey: (serialNumber: string, p2pDid: string) => string;
|
||||||
|
export declare const encryptP2PData: (data: Buffer, key: Buffer) => Buffer;
|
||||||
|
export declare const decryptP2PData: (data: Buffer, key: Buffer) => Buffer;
|
||||||
|
export declare const paddingP2PData: (data: Buffer, blocksize?: number) => Buffer;
|
||||||
|
export declare const buildLookupWithKeyPayload: (socket: Socket, p2pDid: string, dskKey: string) => Buffer;
|
||||||
|
export declare const buildLookupWithKeyPayload2: (p2pDid: string, dskKey: string) => Buffer;
|
||||||
|
export declare const buildLookupWithKeyPayload3: (p2pDid: string, address: Address, data: Buffer) => Buffer;
|
||||||
|
export declare const buildCheckCamPayload: (p2pDid: string) => Buffer;
|
||||||
|
export declare const buildCheckCamPayload2: (p2pDid: string, data: Buffer) => Buffer;
|
||||||
|
export declare const buildIntCommandPayload: (encryptionType: EncryptionType, encryptionKey: Buffer | undefined, serialNumber: string, p2pDid: string, commandType: CommandType, value: number, strValue?: string, channel?: number) => Buffer;
|
||||||
|
export declare const buildStringTypeCommandPayload: (encryptionType: EncryptionType, encryptionKey: Buffer | undefined, serialNumber: string, p2pDid: string, commandType: CommandType, strValue: string, strValueSub: string, channel?: number) => Buffer;
|
||||||
|
export declare const buildIntStringCommandPayload: (encryptionType: EncryptionType, encryptionKey: Buffer | undefined, serialNumber: string, p2pDid: string, commandType: CommandType, value: number, valueSub?: number, strValue?: string, strValueSub?: string, channel?: number) => Buffer;
|
||||||
|
export declare const sendMessage: (socket: Socket, address: {
|
||||||
|
host: string;
|
||||||
|
port: number;
|
||||||
|
}, msgID: Buffer, payload?: Buffer) => Promise<number>;
|
||||||
|
export declare const hasHeader: (msg: Buffer, searchedType: Buffer) => boolean;
|
||||||
|
export declare const buildCommandHeader: (seqNumber: number, commandType: CommandType, p2pDataTypeHeader?: Buffer | null) => Buffer;
|
||||||
|
export declare const buildCommandWithStringTypePayload: (encryptionType: EncryptionType, encryptionKey: Buffer | undefined, serialNumber: string, p2pDid: string, commandType: CommandType, value: string, channel?: number) => Buffer;
|
||||||
|
export declare const sortP2PMessageParts: (messages: P2PMessageParts) => Buffer;
|
||||||
|
export declare const getRSAPrivateKey: (pem: string, enableEmbeddedPKCS1Support?: boolean) => NodeRSA;
|
||||||
|
export declare const getNewRSAPrivateKey: (enableEmbeddedPKCS1Support?: boolean) => NodeRSA;
|
||||||
|
export declare const decryptAESData: (hexkey: string, data: Buffer) => Buffer;
|
||||||
|
export declare const findStartCode: (data: Buffer) => boolean;
|
||||||
|
export declare const isIFrame: (data: Buffer) => boolean;
|
||||||
|
export declare const decryptLockAESData: (key: string, iv: string, data: Buffer) => Buffer;
|
||||||
|
export declare const encryptLockAESData: (key: string, iv: string, data: Buffer) => Buffer;
|
||||||
|
export declare const generateBasicLockAESKey: (adminID: string, stationSN: string) => string;
|
||||||
|
export declare const getCurrentTimeInSeconds: () => number;
|
||||||
|
export declare const generateLockSequence: (deviceType?: DeviceType, serialnumber?: string) => number;
|
||||||
|
export declare const encodeLockPayload: (data: string) => Buffer;
|
||||||
|
export declare const getLockVectorBytes: (data: string) => string;
|
||||||
|
export declare const decodeLockPayload: (data: Buffer) => string;
|
||||||
|
export declare const decodeBase64: (data: string) => Buffer;
|
||||||
|
export declare const eslTimestamp: (timestamp_in_sec?: number) => number[];
|
||||||
|
export declare const generateAdvancedLockAESKey: () => string;
|
||||||
|
export declare const getVideoCodec: (data: Buffer) => VideoCodec;
|
||||||
|
export declare const checkT8420: (serialNumber: string) => boolean;
|
||||||
|
export declare const buildVoidCommandPayload: (channel?: number) => Buffer;
|
||||||
|
export declare function isP2PQueueMessage(type: P2PQueueMessage | P2PMessageState): type is P2PQueueMessage;
|
||||||
|
export declare const encryptPayloadData: (data: string | Buffer, key: Buffer, iv: Buffer) => Buffer;
|
||||||
|
export declare const decryptPayloadData: (data: Buffer, key: Buffer, iv: Buffer) => Buffer;
|
||||||
|
export declare const eufyKDF: (key: Buffer) => Buffer;
|
||||||
|
export declare const getAdvancedLockKey: (key: string, publicKey: string) => string;
|
||||||
|
export declare const getLockV12Key: (key: string, publicKey: string) => string;
|
||||||
|
export declare const buildTalkbackAudioFrameHeader: (audioData: Buffer, channel?: number) => Buffer;
|
||||||
|
export declare const decodeP2PCloudIPs: (data: string) => Array<Address>;
|
||||||
|
export declare const decodeSmartSafeData: (deviceSN: string, data: Buffer) => SmartSafeNotificationResponse;
|
||||||
|
export declare const getSmartSafeP2PCommand: (deviceSN: string, user_id: string, command: CommandType, intCommand: SmartSafeCommandCode, channel: number, sequence: number, data: Buffer) => SmartSafeP2PCommandType;
|
||||||
|
export declare const getLockP2PCommand: (deviceSN: string, user_id: string, command: CommandType, channel: number, lockPublicKey: string, payload: any) => LockP2PCommandType;
|
||||||
|
export declare const getLockV12P2PCommand: (deviceSN: string, user_id: string, command: CommandType | ESLCommand, channel: number, lockPublicKey: string, sequence: number, data: Buffer) => LockV12P2PCommand;
|
||||||
|
export declare const DecimalToRGBColor: (color: number) => RGBColor;
|
||||||
|
export declare const RGBColorToDecimal: (color: RGBColor) => number;
|
||||||
|
export declare const getNullTerminatedString: (data: Buffer, encoding?: BufferEncoding) => string;
|
||||||
|
export declare const isUsbCharging: (value: number) => boolean;
|
||||||
|
export declare const isSolarCharging: (value: number) => boolean;
|
||||||
|
export declare const isPlugSolarCharging: (value: number) => boolean;
|
||||||
|
export declare const isCharging: (value: number) => boolean;
|
||||||
|
export declare const getSmartLockCurrentTimeInSeconds: () => number;
|
||||||
|
export declare const generateSmartLockAESKey: (adminUserId: string, time: number) => Buffer;
|
||||||
|
export declare const getSmartLockP2PCommand: (deviceSN: string, user_id: string, command: CommandType | SmartLockCommand, channel: number, sequence: number, data: Buffer, functionType?: SmartLockFunctionType) => SmartLockP2PCommand;
|
||||||
|
export declare const readNullTerminatedBuffer: (input: Buffer) => Buffer;
|
||||||
824
build/p2p/utils.js
Normal file
824
build/p2p/utils.js
Normal file
@ -0,0 +1,824 @@
|
|||||||
|
"use strict";
|
||||||
|
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
var desc = Object.getOwnPropertyDescriptor(m, k);
|
||||||
|
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
||||||
|
desc = { enumerable: true, get: function() { return m[k]; } };
|
||||||
|
}
|
||||||
|
Object.defineProperty(o, k2, desc);
|
||||||
|
}) : (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
o[k2] = m[k];
|
||||||
|
}));
|
||||||
|
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
||||||
|
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
||||||
|
}) : function(o, v) {
|
||||||
|
o["default"] = v;
|
||||||
|
});
|
||||||
|
var __importStar = (this && this.__importStar) || function (mod) {
|
||||||
|
if (mod && mod.__esModule) return mod;
|
||||||
|
var result = {};
|
||||||
|
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
||||||
|
__setModuleDefault(result, mod);
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
var __importDefault = (this && this.__importDefault) || function (mod) {
|
||||||
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.getLockP2PCommand = exports.getSmartSafeP2PCommand = exports.decodeSmartSafeData = exports.decodeP2PCloudIPs = exports.buildTalkbackAudioFrameHeader = exports.getLockV12Key = exports.getAdvancedLockKey = exports.eufyKDF = exports.decryptPayloadData = exports.encryptPayloadData = exports.buildVoidCommandPayload = exports.checkT8420 = exports.getVideoCodec = exports.generateAdvancedLockAESKey = exports.eslTimestamp = exports.decodeBase64 = exports.decodeLockPayload = exports.getLockVectorBytes = exports.encodeLockPayload = exports.generateLockSequence = exports.getCurrentTimeInSeconds = exports.generateBasicLockAESKey = exports.encryptLockAESData = exports.decryptLockAESData = exports.isIFrame = exports.findStartCode = exports.decryptAESData = exports.getNewRSAPrivateKey = exports.getRSAPrivateKey = exports.sortP2PMessageParts = exports.buildCommandWithStringTypePayload = exports.buildCommandHeader = exports.hasHeader = exports.sendMessage = exports.buildIntStringCommandPayload = exports.buildStringTypeCommandPayload = exports.buildIntCommandPayload = exports.buildCheckCamPayload2 = exports.buildCheckCamPayload = exports.buildLookupWithKeyPayload3 = exports.buildLookupWithKeyPayload2 = exports.buildLookupWithKeyPayload = exports.paddingP2PData = exports.decryptP2PData = exports.encryptP2PData = exports.getP2PCommandEncryptionKey = exports.isP2PCommandEncrypted = exports.getLocalIpAddress = exports.isPrivateIp = exports.MAGIC_WORD = void 0;
|
||||||
|
exports.readNullTerminatedBuffer = exports.getSmartLockP2PCommand = exports.generateSmartLockAESKey = exports.getSmartLockCurrentTimeInSeconds = exports.isCharging = exports.isPlugSolarCharging = exports.isSolarCharging = exports.isUsbCharging = exports.getNullTerminatedString = exports.RGBColorToDecimal = exports.DecimalToRGBColor = exports.getLockV12P2PCommand = void 0;
|
||||||
|
exports.isP2PQueueMessage = isP2PQueueMessage;
|
||||||
|
const node_rsa_1 = __importDefault(require("node-rsa"));
|
||||||
|
const CryptoJS = __importStar(require("crypto-js"));
|
||||||
|
const crypto_1 = require("crypto");
|
||||||
|
const os = __importStar(require("os"));
|
||||||
|
const types_1 = require("./types");
|
||||||
|
const device_1 = require("../http/device");
|
||||||
|
const ble_1 = require("./ble");
|
||||||
|
const logging_1 = require("../logging");
|
||||||
|
exports.MAGIC_WORD = "XZYH";
|
||||||
|
const isPrivateIp = (ip) => /^(::f{4}:)?10\.([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})$/i.test(ip) ||
|
||||||
|
/^(::f{4}:)?192\.168\.([0-9]{1,3})\.([0-9]{1,3})$/i.test(ip) ||
|
||||||
|
/^(::f{4}:)?172\.(1[6-9]|2\d|30|31)\.([0-9]{1,3})\.([0-9]{1,3})$/i.test(ip) ||
|
||||||
|
/^(::f{4}:)?127\.([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})$/i.test(ip) ||
|
||||||
|
/^(::f{4}:)?169\.254\.([0-9]{1,3})\.([0-9]{1,3})$/i.test(ip) ||
|
||||||
|
/^f[cd][0-9a-f]{2}:/i.test(ip) ||
|
||||||
|
/^fe80:/i.test(ip) ||
|
||||||
|
/^::1$/.test(ip) ||
|
||||||
|
/^::$/.test(ip);
|
||||||
|
exports.isPrivateIp = isPrivateIp;
|
||||||
|
const stringWithLength = (input, chunkLength = 128) => {
|
||||||
|
const stringAsBuffer = Buffer.from(input);
|
||||||
|
const bufferSize = stringAsBuffer.byteLength < chunkLength ? chunkLength : Math.ceil(stringAsBuffer.byteLength / chunkLength) * chunkLength;
|
||||||
|
const result = Buffer.alloc(bufferSize);
|
||||||
|
stringAsBuffer.copy(result);
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
const getLocalIpAddress = (init = "") => {
|
||||||
|
const ifaces = os.networkInterfaces();
|
||||||
|
let localAddress = init;
|
||||||
|
for (const name in ifaces) {
|
||||||
|
const iface = ifaces[name].filter(function (details) {
|
||||||
|
return details.family === "IPv4" && details.internal === false;
|
||||||
|
});
|
||||||
|
if (iface.length > 0) {
|
||||||
|
localAddress = iface[0].address;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return localAddress;
|
||||||
|
};
|
||||||
|
exports.getLocalIpAddress = getLocalIpAddress;
|
||||||
|
const p2pDidToBuffer = (p2pDid) => {
|
||||||
|
const p2pArray = p2pDid.split("-");
|
||||||
|
const buf1 = stringWithLength(p2pArray[0], 8);
|
||||||
|
const buf2 = Buffer.allocUnsafe(4);
|
||||||
|
buf2.writeUInt32BE(Number.parseInt(p2pArray[1]), 0);
|
||||||
|
const buf3 = stringWithLength(p2pArray[2], 8);
|
||||||
|
return Buffer.concat([buf1, buf2, buf3], 20);
|
||||||
|
};
|
||||||
|
const isP2PCommandEncrypted = function (cmd) {
|
||||||
|
return [1001, 1002, 1004, 1005, 1006, 1007, 1008, 1009, 1010, 1011, 1015, 1017, 1019, 1035, 1045, 1056, 1145, 1146, 1152, 1200, 1207, 1210, 1213, 1214, 1226, 1227, 1229, 1230, 1233, 1236, 1240, 1241, 1243, 1246, 1272, 1273, 1275, 1400, 1401, 1402, 1403, 1408, 1409, 1410, 1412, 1413, 1506, 1507, 1607, 1609, 1610, 1611, 1702, 1703, 1704, 1705, 1706, 1707, 1708, 1709, 1013, 1202, 1205, 1206, 1024, 1025, 1132, 1215, 1216, 1217, 1414, 1026, 1164, 1201, 1027, 1047, 1048, 1029, 1034, 1036, 1043, 1057, 1203, 1218, 1219, 1220, 1221, 1222, 1223, 1224, 1232, 1234, 1235, 1237, 1238, 1248, 1253, 1257, 1269, 1800, 1037, 1040, 1038, 1049, 1050, 1051, 1054, 1060, 1204, 1254, 1255, 1256, 1258, 1259, 1260, 1261, 1262, 1264, 1271, 1350, 1404, 1101, 1106, 1108, 1110, 1111, 1112, 1113, 1114, 1116, 1117, 1118, 1119, 1121, 1103, 1129, 1211, 1228, 1231, 1242, 1249, 1250, 1251, 1252, 1405, 1406, 1407, 1700].includes(cmd);
|
||||||
|
};
|
||||||
|
exports.isP2PCommandEncrypted = isP2PCommandEncrypted;
|
||||||
|
const getP2PCommandEncryptionKey = function (serialNumber, p2pDid) {
|
||||||
|
return `${serialNumber.slice(-7)}${p2pDid.substring(p2pDid.indexOf("-"), p2pDid.indexOf("-") + 9)}`;
|
||||||
|
};
|
||||||
|
exports.getP2PCommandEncryptionKey = getP2PCommandEncryptionKey;
|
||||||
|
const encryptP2PData = (data, key) => {
|
||||||
|
const cipher = (0, crypto_1.createCipheriv)("aes-128-ecb", key, null);
|
||||||
|
cipher.setAutoPadding(false);
|
||||||
|
return Buffer.concat([
|
||||||
|
cipher.update(data),
|
||||||
|
cipher.final()
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.encryptP2PData = encryptP2PData;
|
||||||
|
const decryptP2PData = (data, key) => {
|
||||||
|
const decipher = (0, crypto_1.createDecipheriv)("aes-128-ecb", key, null);
|
||||||
|
decipher.setAutoPadding(false);
|
||||||
|
return Buffer.concat([
|
||||||
|
decipher.update(data),
|
||||||
|
decipher.final()
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.decryptP2PData = decryptP2PData;
|
||||||
|
const paddingP2PData = (data, blocksize = 16) => {
|
||||||
|
const bufferSize = data.byteLength < blocksize ? blocksize : Math.ceil(data.byteLength / blocksize) * blocksize;
|
||||||
|
const result = Buffer.alloc(bufferSize);
|
||||||
|
data.copy(result);
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.paddingP2PData = paddingP2PData;
|
||||||
|
const buildLookupWithKeyPayload = (socket, p2pDid, dskKey) => {
|
||||||
|
const p2pDidBuffer = p2pDidToBuffer(p2pDid);
|
||||||
|
const addressInfo = socket.address();
|
||||||
|
const port = addressInfo.port;
|
||||||
|
const portAsBuffer = Buffer.allocUnsafe(2);
|
||||||
|
portAsBuffer.writeUInt16LE(port, 0);
|
||||||
|
//const ip = socket.address().address;
|
||||||
|
const ip = (0, exports.getLocalIpAddress)(addressInfo.address);
|
||||||
|
const temp_buff = [];
|
||||||
|
ip.split(".").reverse().forEach(element => {
|
||||||
|
temp_buff.push(Number.parseInt(element));
|
||||||
|
});
|
||||||
|
const ipAsBuffer = Buffer.from(temp_buff);
|
||||||
|
const splitter = Buffer.from([0x00, 0x02]);
|
||||||
|
const magic = Buffer.from([0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x04, 0x00, 0x00]);
|
||||||
|
const dskKeyAsBuffer = Buffer.from(dskKey);
|
||||||
|
const fourEmpty = Buffer.from([0x00, 0x00, 0x00, 0x00]);
|
||||||
|
return Buffer.concat([p2pDidBuffer, splitter, portAsBuffer, ipAsBuffer, magic, dskKeyAsBuffer, fourEmpty]);
|
||||||
|
};
|
||||||
|
exports.buildLookupWithKeyPayload = buildLookupWithKeyPayload;
|
||||||
|
const buildLookupWithKeyPayload2 = (p2pDid, dskKey) => {
|
||||||
|
const p2pDidBuffer = p2pDidToBuffer(p2pDid);
|
||||||
|
const dskKeyAsBuffer = Buffer.from(dskKey);
|
||||||
|
const fourEmpty = Buffer.from([0x00, 0x00, 0x00, 0x00]);
|
||||||
|
return Buffer.concat([p2pDidBuffer, dskKeyAsBuffer, fourEmpty]);
|
||||||
|
};
|
||||||
|
exports.buildLookupWithKeyPayload2 = buildLookupWithKeyPayload2;
|
||||||
|
const buildLookupWithKeyPayload3 = (p2pDid, address, data) => {
|
||||||
|
const p2pDidBuffer = p2pDidToBuffer(p2pDid);
|
||||||
|
const portAsBuffer = Buffer.allocUnsafe(2);
|
||||||
|
portAsBuffer.writeUInt16LE(address.port, 0);
|
||||||
|
const temp_buff = [];
|
||||||
|
address.host.split(".").reverse().forEach(element => {
|
||||||
|
temp_buff.push(Number.parseInt(element));
|
||||||
|
});
|
||||||
|
const ipAsBuffer = Buffer.from(temp_buff);
|
||||||
|
const splitter = Buffer.from([0x00, 0x02]);
|
||||||
|
const eightEmpty = Buffer.from([0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00]);
|
||||||
|
return Buffer.concat([p2pDidBuffer, splitter, portAsBuffer, ipAsBuffer, eightEmpty, data]);
|
||||||
|
};
|
||||||
|
exports.buildLookupWithKeyPayload3 = buildLookupWithKeyPayload3;
|
||||||
|
const buildCheckCamPayload = (p2pDid) => {
|
||||||
|
const p2pDidBuffer = p2pDidToBuffer(p2pDid);
|
||||||
|
const magic = Buffer.from([0x00, 0x00, 0x00]);
|
||||||
|
return Buffer.concat([p2pDidBuffer, magic]);
|
||||||
|
};
|
||||||
|
exports.buildCheckCamPayload = buildCheckCamPayload;
|
||||||
|
const buildCheckCamPayload2 = (p2pDid, data) => {
|
||||||
|
const p2pDidBuffer = p2pDidToBuffer(p2pDid);
|
||||||
|
const magic = Buffer.from([0x00, 0x00, 0x00, 0x00]);
|
||||||
|
return Buffer.concat([data, p2pDidBuffer, magic]);
|
||||||
|
};
|
||||||
|
exports.buildCheckCamPayload2 = buildCheckCamPayload2;
|
||||||
|
const buildIntCommandPayload = (encryptionType, encryptionKey, serialNumber, p2pDid, commandType, value, strValue = "", channel = 255) => {
|
||||||
|
const emptyBuffer = Buffer.from([0x00, 0x00]);
|
||||||
|
const magicBuffer = Buffer.from([0x01, 0x00]);
|
||||||
|
const encrypted = (0, exports.isP2PCommandEncrypted)(commandType) && encryptionType !== types_1.EncryptionType.NONE && encryptionKey?.length === 16;
|
||||||
|
const channelBuffer = Buffer.from([channel, encrypted ? encryptionType : 0]);
|
||||||
|
const valueBuffer = Buffer.allocUnsafe(4);
|
||||||
|
valueBuffer.writeUInt32LE(value, 0);
|
||||||
|
const headerBuffer = Buffer.allocUnsafe(2);
|
||||||
|
const strValueBuffer = strValue.length === 0 ? Buffer.from([]) : stringWithLength(strValue);
|
||||||
|
const tmpDataBuffer = Buffer.concat([
|
||||||
|
valueBuffer,
|
||||||
|
strValueBuffer
|
||||||
|
]);
|
||||||
|
const dataBuffer = encrypted ? (0, exports.paddingP2PData)(tmpDataBuffer) : tmpDataBuffer;
|
||||||
|
headerBuffer.writeUInt16LE(dataBuffer.length, 0);
|
||||||
|
return Buffer.concat([
|
||||||
|
headerBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
magicBuffer,
|
||||||
|
channelBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
encrypted ? (0, exports.encryptP2PData)(dataBuffer, encryptionKey) : dataBuffer
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.buildIntCommandPayload = buildIntCommandPayload;
|
||||||
|
const buildStringTypeCommandPayload = (encryptionType, encryptionKey, serialNumber, p2pDid, commandType, strValue, strValueSub, channel = 255) => {
|
||||||
|
const emptyBuffer = Buffer.from([0x00, 0x00]);
|
||||||
|
const magicBuffer = Buffer.from([0x01, 0x00]);
|
||||||
|
const encrypted = (0, exports.isP2PCommandEncrypted)(commandType) && encryptionType !== types_1.EncryptionType.NONE && encryptionKey?.length === 16;
|
||||||
|
const channelBuffer = Buffer.from([channel, encrypted ? encryptionType : 0]);
|
||||||
|
const someBuffer = Buffer.from([0x00, 0x00, 0x00, 0x00, 0x00]);
|
||||||
|
const strValueBuffer = stringWithLength(strValue);
|
||||||
|
const strValueSubBuffer = stringWithLength(strValueSub);
|
||||||
|
const headerBuffer = Buffer.allocUnsafe(2);
|
||||||
|
const tmpDataBuffer = Buffer.concat([
|
||||||
|
someBuffer,
|
||||||
|
strValueBuffer,
|
||||||
|
strValueSubBuffer
|
||||||
|
]);
|
||||||
|
const dataBuffer = encrypted ? (0, exports.paddingP2PData)(tmpDataBuffer) : tmpDataBuffer;
|
||||||
|
headerBuffer.writeUInt16LE(dataBuffer.length, 0);
|
||||||
|
return Buffer.concat([
|
||||||
|
headerBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
magicBuffer,
|
||||||
|
channelBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
encrypted ? (0, exports.encryptP2PData)(dataBuffer, encryptionKey) : dataBuffer
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.buildStringTypeCommandPayload = buildStringTypeCommandPayload;
|
||||||
|
const buildIntStringCommandPayload = (encryptionType, encryptionKey, serialNumber, p2pDid, commandType, value, valueSub = 0, strValue = "", strValueSub = "", channel = 0) => {
|
||||||
|
const emptyBuffer = Buffer.from([0x00, 0x00]);
|
||||||
|
const magicBuffer = Buffer.from([0x01, 0x00]);
|
||||||
|
const encrypted = (0, exports.isP2PCommandEncrypted)(commandType) && encryptionType !== types_1.EncryptionType.NONE && encryptionKey?.length === 16;
|
||||||
|
const channelBuffer = Buffer.from([channel, encrypted ? encryptionType : 0]);
|
||||||
|
const someintBuffer = Buffer.allocUnsafe(4);
|
||||||
|
someintBuffer.writeUInt32LE(valueSub, 0);
|
||||||
|
const valueBuffer = Buffer.allocUnsafe(4);
|
||||||
|
valueBuffer.writeUInt32LE(value, 0);
|
||||||
|
const strValueBuffer = strValue.length === 0 ? Buffer.from([]) : stringWithLength(strValue);
|
||||||
|
const strValueSubBuffer = strValueSub.length === 0 ? Buffer.from([]) : stringWithLength(strValueSub);
|
||||||
|
const headerBuffer = Buffer.allocUnsafe(2);
|
||||||
|
const tmpDataBuffer = Buffer.concat([
|
||||||
|
someintBuffer,
|
||||||
|
valueBuffer,
|
||||||
|
strValueBuffer,
|
||||||
|
strValueSubBuffer
|
||||||
|
]);
|
||||||
|
const dataBuffer = encrypted ? (0, exports.paddingP2PData)(tmpDataBuffer) : tmpDataBuffer;
|
||||||
|
headerBuffer.writeUInt16LE(dataBuffer.length, 0);
|
||||||
|
return Buffer.concat([
|
||||||
|
headerBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
magicBuffer,
|
||||||
|
channelBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
encrypted ? (0, exports.encryptP2PData)(dataBuffer, encryptionKey) : dataBuffer
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.buildIntStringCommandPayload = buildIntStringCommandPayload;
|
||||||
|
const sendMessage = async (socket, address, msgID, payload) => {
|
||||||
|
if (!payload)
|
||||||
|
payload = Buffer.from([]);
|
||||||
|
const payloadLen = Buffer.allocUnsafe(2);
|
||||||
|
payloadLen.writeUInt16BE(payload.length, 0);
|
||||||
|
const message = Buffer.concat([msgID, payloadLen, payload], 4 + payload.length);
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
socket.send(message, address.port, address.host, (err, bytes) => {
|
||||||
|
return err ? reject(err) : resolve(bytes);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
exports.sendMessage = sendMessage;
|
||||||
|
const hasHeader = (msg, searchedType) => {
|
||||||
|
const header = Buffer.allocUnsafe(2);
|
||||||
|
msg.copy(header, 0, 0, 2);
|
||||||
|
return Buffer.compare(header, searchedType) === 0;
|
||||||
|
};
|
||||||
|
exports.hasHeader = hasHeader;
|
||||||
|
const buildCommandHeader = (seqNumber, commandType, p2pDataTypeHeader = null) => {
|
||||||
|
let dataTypeBuffer = types_1.P2PDataTypeHeader.DATA;
|
||||||
|
if (p2pDataTypeHeader !== null &&
|
||||||
|
(Buffer.compare(p2pDataTypeHeader, types_1.P2PDataTypeHeader.DATA) === 0 ||
|
||||||
|
Buffer.compare(p2pDataTypeHeader, types_1.P2PDataTypeHeader.BINARY) === 0 ||
|
||||||
|
Buffer.compare(p2pDataTypeHeader, types_1.P2PDataTypeHeader.CONTROL) === 0 ||
|
||||||
|
Buffer.compare(p2pDataTypeHeader, types_1.P2PDataTypeHeader.VIDEO) === 0)) {
|
||||||
|
dataTypeBuffer = p2pDataTypeHeader;
|
||||||
|
}
|
||||||
|
const seqAsBuffer = Buffer.allocUnsafe(2);
|
||||||
|
seqAsBuffer.writeUInt16BE(seqNumber, 0);
|
||||||
|
const magicString = Buffer.from(exports.MAGIC_WORD);
|
||||||
|
const commandTypeBuffer = Buffer.allocUnsafe(2);
|
||||||
|
commandTypeBuffer.writeUInt16LE(commandType, 0);
|
||||||
|
return Buffer.concat([dataTypeBuffer, seqAsBuffer, magicString, commandTypeBuffer]);
|
||||||
|
};
|
||||||
|
exports.buildCommandHeader = buildCommandHeader;
|
||||||
|
const buildCommandWithStringTypePayload = (encryptionType, encryptionKey, serialNumber, p2pDid, commandType, value, channel = 0) => {
|
||||||
|
const headerBuffer = Buffer.allocUnsafe(2);
|
||||||
|
const emptyBuffer = Buffer.from([0x00, 0x00]);
|
||||||
|
const magicBuffer = Buffer.from([0x01, 0x00]);
|
||||||
|
const encrypted = (0, exports.isP2PCommandEncrypted)(commandType) && encryptionType !== types_1.EncryptionType.NONE && encryptionKey?.length === 16;
|
||||||
|
const channelBuffer = Buffer.from([channel, encrypted ? encryptionType : 0]);
|
||||||
|
const dataBuffer = encrypted ? (0, exports.paddingP2PData)(Buffer.from(value)) : Buffer.from(value);
|
||||||
|
headerBuffer.writeUInt16LE(dataBuffer.length, 0);
|
||||||
|
return Buffer.concat([
|
||||||
|
headerBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
magicBuffer,
|
||||||
|
channelBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
encrypted ? (0, exports.encryptP2PData)(dataBuffer, encryptionKey) : dataBuffer
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.buildCommandWithStringTypePayload = buildCommandWithStringTypePayload;
|
||||||
|
const sortP2PMessageParts = (messages) => {
|
||||||
|
let completeMessage = Buffer.from([]);
|
||||||
|
Object.keys(messages).map(Number)
|
||||||
|
.sort((a, b) => {
|
||||||
|
if (Math.abs(a - b) > 65000) {
|
||||||
|
if (a < b) {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
else if (b < a) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return a - b;
|
||||||
|
}) // assure the seqNumbers are in correct order
|
||||||
|
.forEach((key) => {
|
||||||
|
completeMessage = Buffer.concat([completeMessage, messages[key]]);
|
||||||
|
});
|
||||||
|
return completeMessage;
|
||||||
|
};
|
||||||
|
exports.sortP2PMessageParts = sortP2PMessageParts;
|
||||||
|
const getRSAPrivateKey = (pem, enableEmbeddedPKCS1Support = false) => {
|
||||||
|
const key = new node_rsa_1.default();
|
||||||
|
if (pem.indexOf("\n") !== -1) {
|
||||||
|
pem = pem.replaceAll("\n", "");
|
||||||
|
}
|
||||||
|
if (pem.startsWith("-----BEGIN RSA PRIVATE KEY-----")) {
|
||||||
|
pem = pem.replace("-----BEGIN RSA PRIVATE KEY-----", "").replace("-----END RSA PRIVATE KEY-----", "");
|
||||||
|
}
|
||||||
|
key.importKey(pem, "pkcs8");
|
||||||
|
const options = {
|
||||||
|
encryptionScheme: "pkcs1"
|
||||||
|
};
|
||||||
|
if (enableEmbeddedPKCS1Support) {
|
||||||
|
options.environment = "browser";
|
||||||
|
}
|
||||||
|
key.setOptions(options);
|
||||||
|
return key;
|
||||||
|
};
|
||||||
|
exports.getRSAPrivateKey = getRSAPrivateKey;
|
||||||
|
const getNewRSAPrivateKey = (enableEmbeddedPKCS1Support = false) => {
|
||||||
|
const key = new node_rsa_1.default({ b: 1024 });
|
||||||
|
const options = {
|
||||||
|
encryptionScheme: "pkcs1"
|
||||||
|
};
|
||||||
|
if (enableEmbeddedPKCS1Support) {
|
||||||
|
options.environment = "browser";
|
||||||
|
}
|
||||||
|
key.setOptions(options);
|
||||||
|
return key;
|
||||||
|
};
|
||||||
|
exports.getNewRSAPrivateKey = getNewRSAPrivateKey;
|
||||||
|
const decryptAESData = (hexkey, data) => {
|
||||||
|
const key = CryptoJS.enc.Hex.parse(hexkey);
|
||||||
|
const cipherParams = CryptoJS.lib.CipherParams.create({
|
||||||
|
ciphertext: CryptoJS.enc.Hex.parse(data.toString("hex"))
|
||||||
|
});
|
||||||
|
const decrypted = CryptoJS.AES.decrypt(cipherParams, key, {
|
||||||
|
mode: CryptoJS.mode.ECB,
|
||||||
|
padding: CryptoJS.pad.NoPadding
|
||||||
|
});
|
||||||
|
return Buffer.from(CryptoJS.enc.Hex.stringify(decrypted), "hex");
|
||||||
|
};
|
||||||
|
exports.decryptAESData = decryptAESData;
|
||||||
|
const findStartCode = (data) => {
|
||||||
|
if (data !== undefined && data.length > 0) {
|
||||||
|
if (data.length >= 4) {
|
||||||
|
const startcode = [...data.subarray(0, 4)];
|
||||||
|
if ((startcode[0] === 0 && startcode[1] === 0 && startcode[2] === 1) || (startcode[0] === 0 && startcode[1] === 0 && startcode[2] === 0 && startcode[3] === 1))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else if (data.length === 3) {
|
||||||
|
const startcode = [...data.subarray(0, 3)];
|
||||||
|
if ((startcode[0] === 0 && startcode[1] === 0 && startcode[2] === 1))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
};
|
||||||
|
exports.findStartCode = findStartCode;
|
||||||
|
const isIFrame = (data) => {
|
||||||
|
const validValues = [64, 66, 68, 78, 101, 103];
|
||||||
|
if (data !== undefined && data.length > 0) {
|
||||||
|
if (data.length >= 5) {
|
||||||
|
const startcode = [...data.subarray(0, 5)];
|
||||||
|
if (validValues.includes(startcode[3]) || validValues.includes(startcode[4]))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
};
|
||||||
|
exports.isIFrame = isIFrame;
|
||||||
|
const decryptLockAESData = (key, iv, data) => {
|
||||||
|
const ekey = CryptoJS.enc.Hex.parse(key);
|
||||||
|
const eiv = CryptoJS.enc.Hex.parse(iv);
|
||||||
|
const cipherParams = CryptoJS.lib.CipherParams.create({
|
||||||
|
ciphertext: CryptoJS.enc.Hex.parse(data.toString("hex"))
|
||||||
|
});
|
||||||
|
const decrypted = CryptoJS.AES.decrypt(cipherParams, ekey, {
|
||||||
|
iv: eiv,
|
||||||
|
mode: CryptoJS.mode.CBC,
|
||||||
|
padding: CryptoJS.pad.Pkcs7
|
||||||
|
});
|
||||||
|
return Buffer.from(CryptoJS.enc.Hex.stringify(decrypted), "hex");
|
||||||
|
};
|
||||||
|
exports.decryptLockAESData = decryptLockAESData;
|
||||||
|
const encryptLockAESData = (key, iv, data) => {
|
||||||
|
const ekey = CryptoJS.enc.Hex.parse(key);
|
||||||
|
const eiv = CryptoJS.enc.Hex.parse(iv);
|
||||||
|
const encrypted = CryptoJS.AES.encrypt(CryptoJS.enc.Hex.parse(data.toString("hex")), ekey, {
|
||||||
|
iv: eiv,
|
||||||
|
mode: CryptoJS.mode.CBC,
|
||||||
|
padding: CryptoJS.pad.Pkcs7
|
||||||
|
});
|
||||||
|
return Buffer.from(CryptoJS.enc.Hex.stringify(encrypted.ciphertext), "hex");
|
||||||
|
};
|
||||||
|
exports.encryptLockAESData = encryptLockAESData;
|
||||||
|
const generateBasicLockAESKey = (adminID, stationSN) => {
|
||||||
|
const encoder = new TextEncoder();
|
||||||
|
const encOwnerID = encoder.encode(adminID);
|
||||||
|
const encStationSerial = encoder.encode(stationSN);
|
||||||
|
const array = [104, -83, -72, 38, -107, 99, -110, 17, -95, -121, 54, 57, -46, -98, -111, 89];
|
||||||
|
for (let i = 0; i < 16; i++) {
|
||||||
|
array[i] = (array[i] + encStationSerial[((encStationSerial[i] * 3) + 5) % 16] + encOwnerID[((encOwnerID[i] * 3) + 5) % 40]);
|
||||||
|
}
|
||||||
|
return Buffer.from(array).toString("hex");
|
||||||
|
};
|
||||||
|
exports.generateBasicLockAESKey = generateBasicLockAESKey;
|
||||||
|
const getCurrentTimeInSeconds = function () {
|
||||||
|
return Math.trunc(new Date().getTime() / 1000);
|
||||||
|
};
|
||||||
|
exports.getCurrentTimeInSeconds = getCurrentTimeInSeconds;
|
||||||
|
const generateLockSequence = (deviceType, serialnumber) => {
|
||||||
|
if (deviceType !== undefined && serialnumber !== undefined)
|
||||||
|
if (device_1.Device.isLockWifi(deviceType, serialnumber) || device_1.Device.isLockWifiNoFinger(deviceType))
|
||||||
|
return Math.trunc(Math.random() * 1000);
|
||||||
|
return (0, exports.getCurrentTimeInSeconds)();
|
||||||
|
};
|
||||||
|
exports.generateLockSequence = generateLockSequence;
|
||||||
|
const encodeLockPayload = (data) => {
|
||||||
|
const encoder = new TextEncoder();
|
||||||
|
const encData = encoder.encode(data);
|
||||||
|
const length = encData.length;
|
||||||
|
const old_buffer = Buffer.from(encData);
|
||||||
|
if (length % 16 == 0) {
|
||||||
|
return old_buffer;
|
||||||
|
}
|
||||||
|
const new_length = (Math.trunc(length / 16) + 1) * 16;
|
||||||
|
const new_buffer = Buffer.alloc(new_length);
|
||||||
|
old_buffer.copy(new_buffer, 0);
|
||||||
|
return new_buffer;
|
||||||
|
};
|
||||||
|
exports.encodeLockPayload = encodeLockPayload;
|
||||||
|
const getLockVectorBytes = (data) => {
|
||||||
|
const encoder = new TextEncoder();
|
||||||
|
const encData = encoder.encode(data);
|
||||||
|
const old_buffer = Buffer.from(encData);
|
||||||
|
if (encData.length >= 16)
|
||||||
|
return old_buffer.toString("hex");
|
||||||
|
const new_buffer = Buffer.alloc(16);
|
||||||
|
old_buffer.copy(new_buffer, 0);
|
||||||
|
return new_buffer.toString("hex");
|
||||||
|
};
|
||||||
|
exports.getLockVectorBytes = getLockVectorBytes;
|
||||||
|
const decodeLockPayload = (data) => {
|
||||||
|
const decoder = new TextDecoder();
|
||||||
|
return decoder.decode(data);
|
||||||
|
};
|
||||||
|
exports.decodeLockPayload = decodeLockPayload;
|
||||||
|
const decodeBase64 = (data) => {
|
||||||
|
const base64RegExp = /^(?:[A-Za-z0-9+/]{4})*(?:[A-Za-z0-9+/]{2}==|[A-Za-z0-9+/]{3}=|[A-Za-z0-9+/]{4})$/;
|
||||||
|
if (base64RegExp.test(data))
|
||||||
|
return Buffer.from(data, "base64");
|
||||||
|
return Buffer.from(data);
|
||||||
|
};
|
||||||
|
exports.decodeBase64 = decodeBase64;
|
||||||
|
const eslTimestamp = function (timestamp_in_sec = new Date().getTime() / 1000) {
|
||||||
|
const array = [];
|
||||||
|
for (let pos = 0; pos < 4; pos++) {
|
||||||
|
array[pos] = ((timestamp_in_sec >> (pos * 8)) & 255);
|
||||||
|
}
|
||||||
|
return array;
|
||||||
|
};
|
||||||
|
exports.eslTimestamp = eslTimestamp;
|
||||||
|
const generateAdvancedLockAESKey = () => {
|
||||||
|
const randomBytesArray = [...(0, crypto_1.randomBytes)(16)];
|
||||||
|
let result = "";
|
||||||
|
for (let pos = 0; pos < randomBytesArray.length; pos++) {
|
||||||
|
result += "0123456789ABCDEF".charAt((randomBytesArray[pos] >> 4) & 15);
|
||||||
|
result += "0123456789ABCDEF".charAt(randomBytesArray[pos] & 15);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.generateAdvancedLockAESKey = generateAdvancedLockAESKey;
|
||||||
|
const getVideoCodec = (data) => {
|
||||||
|
if (data !== undefined && data.length > 0) {
|
||||||
|
if (data.length >= 5) {
|
||||||
|
const h265Values = [38, 64, 66, 68, 78];
|
||||||
|
const startcode = [...data.subarray(0, 5)];
|
||||||
|
if (h265Values.includes(startcode[3]) || h265Values.includes(startcode[4])) {
|
||||||
|
return types_1.VideoCodec.H265;
|
||||||
|
}
|
||||||
|
else if (startcode[3] === 103 || startcode[4] === 103) {
|
||||||
|
return types_1.VideoCodec.H264;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return types_1.VideoCodec.H264;
|
||||||
|
}
|
||||||
|
return types_1.VideoCodec.UNKNOWN; // Maybe return h264 as Eufy does?
|
||||||
|
};
|
||||||
|
exports.getVideoCodec = getVideoCodec;
|
||||||
|
const checkT8420 = (serialNumber) => {
|
||||||
|
if (!(serialNumber !== undefined && serialNumber !== null && serialNumber.length > 0 && serialNumber.startsWith("T8420")) || serialNumber.length <= 7 || serialNumber[6] != "6") {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
};
|
||||||
|
exports.checkT8420 = checkT8420;
|
||||||
|
const buildVoidCommandPayload = (channel = 255) => {
|
||||||
|
const headerBuffer = Buffer.from([0x00, 0x00]);
|
||||||
|
const emptyBuffer = Buffer.from([0x00, 0x00]);
|
||||||
|
const magicBuffer = Buffer.from([0x01, 0x00]);
|
||||||
|
const channelBuffer = Buffer.from([channel, 0x00]);
|
||||||
|
return Buffer.concat([
|
||||||
|
headerBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
magicBuffer,
|
||||||
|
channelBuffer,
|
||||||
|
emptyBuffer
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.buildVoidCommandPayload = buildVoidCommandPayload;
|
||||||
|
function isP2PQueueMessage(type) {
|
||||||
|
return type.p2pCommand !== undefined;
|
||||||
|
}
|
||||||
|
const encryptPayloadData = (data, key, iv) => {
|
||||||
|
const cipher = (0, crypto_1.createCipheriv)("aes-128-cbc", key, iv);
|
||||||
|
return Buffer.concat([
|
||||||
|
cipher.update(data),
|
||||||
|
cipher.final()
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.encryptPayloadData = encryptPayloadData;
|
||||||
|
const decryptPayloadData = (data, key, iv) => {
|
||||||
|
const cipher = (0, crypto_1.createDecipheriv)("aes-128-cbc", key, iv);
|
||||||
|
return Buffer.concat([
|
||||||
|
cipher.update(data),
|
||||||
|
cipher.final()
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.decryptPayloadData = decryptPayloadData;
|
||||||
|
const eufyKDF = (key) => {
|
||||||
|
const hash_length = 32;
|
||||||
|
const digest_length = 48;
|
||||||
|
const staticBuffer = Buffer.from("ECIES");
|
||||||
|
const steps = Math.ceil(digest_length / hash_length);
|
||||||
|
const buffer = Buffer.alloc(hash_length * steps);
|
||||||
|
let tmpBuffer = staticBuffer;
|
||||||
|
for (let step = 0; step < steps; ++step) {
|
||||||
|
tmpBuffer = (0, crypto_1.createHmac)("sha256", key).update(tmpBuffer).digest();
|
||||||
|
const digest = (0, crypto_1.createHmac)("sha256", key).update(Buffer.concat([tmpBuffer, staticBuffer])).digest();
|
||||||
|
digest.copy(buffer, hash_length * step);
|
||||||
|
}
|
||||||
|
return buffer.subarray(0, digest_length);
|
||||||
|
};
|
||||||
|
exports.eufyKDF = eufyKDF;
|
||||||
|
const getAdvancedLockKey = (key, publicKey) => {
|
||||||
|
const ecdh = (0, crypto_1.createECDH)("prime256v1");
|
||||||
|
ecdh.generateKeys();
|
||||||
|
const secret = ecdh.computeSecret(Buffer.concat([Buffer.from("04", "hex"), Buffer.from(publicKey, "hex")]));
|
||||||
|
const randomValue = (0, crypto_1.randomBytes)(16);
|
||||||
|
const derivedKey = (0, exports.eufyKDF)(secret);
|
||||||
|
const encryptedData = (0, exports.encryptPayloadData)(key, derivedKey.subarray(0, 16), randomValue);
|
||||||
|
const hmac = (0, crypto_1.createHmac)("sha256", derivedKey.subarray(16));
|
||||||
|
hmac.update(randomValue);
|
||||||
|
hmac.update(encryptedData);
|
||||||
|
const hmacDigest = hmac.digest();
|
||||||
|
return Buffer.concat([Buffer.from(ecdh.getPublicKey("hex", "compressed"), "hex"), randomValue, encryptedData, hmacDigest]).toString("hex");
|
||||||
|
};
|
||||||
|
exports.getAdvancedLockKey = getAdvancedLockKey;
|
||||||
|
const getLockV12Key = (key, publicKey) => {
|
||||||
|
const ecdh = (0, crypto_1.createECDH)("prime256v1");
|
||||||
|
ecdh.generateKeys();
|
||||||
|
const secret = ecdh.computeSecret(Buffer.concat([Buffer.from("04", "hex"), Buffer.from(publicKey, "hex")]));
|
||||||
|
const randomValue = (0, crypto_1.randomBytes)(16);
|
||||||
|
const derivedKey = (0, exports.eufyKDF)(secret);
|
||||||
|
const encryptedData = (0, exports.encryptPayloadData)(Buffer.from(key, "hex"), derivedKey.subarray(0, 16), randomValue);
|
||||||
|
const hmac = (0, crypto_1.createHmac)("sha256", derivedKey.subarray(16));
|
||||||
|
hmac.update(randomValue);
|
||||||
|
hmac.update(encryptedData);
|
||||||
|
const hmacDigest = hmac.digest();
|
||||||
|
return Buffer.concat([Buffer.from(ecdh.getPublicKey("hex", "compressed"), "hex"), randomValue, encryptedData, hmacDigest]).toString("hex");
|
||||||
|
};
|
||||||
|
exports.getLockV12Key = getLockV12Key;
|
||||||
|
const buildTalkbackAudioFrameHeader = (audioData, channel = 0) => {
|
||||||
|
const audioDataLength = Buffer.allocUnsafe(4);
|
||||||
|
audioDataLength.writeUInt32LE(audioData.length);
|
||||||
|
const unknown1 = Buffer.alloc(1);
|
||||||
|
const audioType = Buffer.alloc(1);
|
||||||
|
const audioSeq = Buffer.alloc(2);
|
||||||
|
const audioTimestamp = Buffer.alloc(8);
|
||||||
|
const audioDataHeader = Buffer.concat([audioDataLength, unknown1, audioType, audioSeq, audioTimestamp]);
|
||||||
|
const bytesToRead = Buffer.allocUnsafe(4);
|
||||||
|
bytesToRead.writeUInt32LE(audioData.length + audioDataHeader.length);
|
||||||
|
const magicBuffer = Buffer.from([0x01, 0x00]);
|
||||||
|
const channelBuffer = Buffer.from([channel, 0x00]);
|
||||||
|
const emptyBuffer = Buffer.from([0x00, 0x00]);
|
||||||
|
return Buffer.concat([
|
||||||
|
bytesToRead,
|
||||||
|
magicBuffer,
|
||||||
|
channelBuffer,
|
||||||
|
emptyBuffer,
|
||||||
|
audioDataHeader
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
exports.buildTalkbackAudioFrameHeader = buildTalkbackAudioFrameHeader;
|
||||||
|
const decodeP2PCloudIPs = (data) => {
|
||||||
|
const lookupTable = Buffer.from("4959433db5bf6da347534f6165e371e9677f02030badb3892b2f35c16b8b959711e5a70deff1050783fb9d3bc5c713171d1f2529d3df", "hex");
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
const [encoded, name = "name not included"] = data.split(":");
|
||||||
|
const output = Buffer.alloc(encoded.length / 2);
|
||||||
|
for (let i = 0; i <= data.length / 2; i++) {
|
||||||
|
let z = 0x39; // 57 // '9'
|
||||||
|
for (let j = 0; j < i; j++) {
|
||||||
|
z = z ^ output[j];
|
||||||
|
}
|
||||||
|
const x = (data.charCodeAt(i * 2 + 1) - "A".charCodeAt(0));
|
||||||
|
const y = (data.charCodeAt(i * 2) - "A".charCodeAt(0)) * 0x10;
|
||||||
|
output[i] = z ^ lookupTable[i % lookupTable.length] ^ x + y;
|
||||||
|
}
|
||||||
|
const result = [];
|
||||||
|
output.toString("utf8").split(",").forEach((ip) => {
|
||||||
|
if (ip !== "") {
|
||||||
|
result.push({ host: ip, port: 32100 });
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.decodeP2PCloudIPs = decodeP2PCloudIPs;
|
||||||
|
const decodeSmartSafeData = function (deviceSN, data) {
|
||||||
|
const response = ble_1.BleCommandFactory.parseSmartSafe(data);
|
||||||
|
return {
|
||||||
|
versionCode: response.getVersionCode(),
|
||||||
|
dataType: response.getDataType(),
|
||||||
|
commandCode: response.getCommandCode(),
|
||||||
|
packageFlag: response.getPackageFlag(),
|
||||||
|
responseCode: response.getResponseCode(),
|
||||||
|
data: (0, exports.decryptPayloadData)(response.getData(), Buffer.from(deviceSN), Buffer.from(device_1.SmartSafe.IV, "hex"))
|
||||||
|
};
|
||||||
|
};
|
||||||
|
exports.decodeSmartSafeData = decodeSmartSafeData;
|
||||||
|
const getSmartSafeP2PCommand = function (deviceSN, user_id, command, intCommand, channel, sequence, data) {
|
||||||
|
const encPayload = (0, exports.encryptPayloadData)(data, Buffer.from(deviceSN), Buffer.from(device_1.SmartSafe.IV, "hex"));
|
||||||
|
const bleCommand = new ble_1.BleCommandFactory()
|
||||||
|
.setVersionCode(device_1.SmartSafe.VERSION_CODE)
|
||||||
|
.setCommandCode(intCommand)
|
||||||
|
.setDataType(-1)
|
||||||
|
.setData(encPayload)
|
||||||
|
.getSmartSafeCommand();
|
||||||
|
logging_1.rootP2PLogger.debug(`Generate smart safe command`, { deviceSN: deviceSN, userId: user_id, command: command, intCommand: intCommand, channel: channel, sequence: sequence, data: data.toString("hex") });
|
||||||
|
return {
|
||||||
|
commandType: types_1.CommandType.CMD_SET_PAYLOAD,
|
||||||
|
value: JSON.stringify({
|
||||||
|
account_id: user_id,
|
||||||
|
cmd: command,
|
||||||
|
mChannel: channel,
|
||||||
|
mValue3: 0,
|
||||||
|
payload: {
|
||||||
|
data: bleCommand.toString("hex"),
|
||||||
|
prj_id: command,
|
||||||
|
seq_num: sequence,
|
||||||
|
}
|
||||||
|
}),
|
||||||
|
channel: channel
|
||||||
|
};
|
||||||
|
};
|
||||||
|
exports.getSmartSafeP2PCommand = getSmartSafeP2PCommand;
|
||||||
|
const getLockP2PCommand = function (deviceSN, user_id, command, channel, lockPublicKey, payload) {
|
||||||
|
const key = (0, exports.generateAdvancedLockAESKey)();
|
||||||
|
const ecdhKey = (0, exports.getAdvancedLockKey)(key, lockPublicKey);
|
||||||
|
const iv = (0, exports.getLockVectorBytes)(deviceSN);
|
||||||
|
const encPayload = (0, exports.encryptLockAESData)(key, iv, Buffer.from(JSON.stringify(payload)));
|
||||||
|
logging_1.rootP2PLogger.debug(`Generate lock command`, { deviceSN: deviceSN, userId: user_id, command: command, channel: channel, data: JSON.stringify(payload) });
|
||||||
|
return {
|
||||||
|
commandType: types_1.CommandType.CMD_SET_PAYLOAD,
|
||||||
|
value: JSON.stringify({
|
||||||
|
key: ecdhKey,
|
||||||
|
account_id: user_id,
|
||||||
|
cmd: command,
|
||||||
|
mChannel: channel,
|
||||||
|
mValue3: 0,
|
||||||
|
payload: encPayload.toString("base64")
|
||||||
|
}).replace(/=/g, "\\u003d"),
|
||||||
|
channel: channel,
|
||||||
|
aesKey: key
|
||||||
|
};
|
||||||
|
};
|
||||||
|
exports.getLockP2PCommand = getLockP2PCommand;
|
||||||
|
const getLockV12P2PCommand = function (deviceSN, user_id, command, channel, lockPublicKey, sequence, data) {
|
||||||
|
const key = (0, exports.generateAdvancedLockAESKey)();
|
||||||
|
const encryptedAesKey = (0, exports.getLockV12Key)(key, lockPublicKey);
|
||||||
|
const iv = (0, exports.getLockVectorBytes)(deviceSN);
|
||||||
|
const encPayload = (0, exports.encryptPayloadData)(data, Buffer.from(key, "hex"), Buffer.from(iv, "hex"));
|
||||||
|
logging_1.rootP2PLogger.debug(`Generate smart lock v12 command`, { deviceSN: deviceSN, userId: user_id, command: command, channel: channel, sequence: sequence, data: data.toString("hex") });
|
||||||
|
const bleCommand = new ble_1.BleCommandFactory()
|
||||||
|
.setVersionCode(device_1.Lock.VERSION_CODE_LOCKV12)
|
||||||
|
.setCommandCode(Number.parseInt(types_1.ESLBleCommand[types_1.ESLCommand[command]])) //TODO: Change internal command identification?
|
||||||
|
.setDataType(-1)
|
||||||
|
.setData(encPayload)
|
||||||
|
.setAdditionalData(Buffer.from(encryptedAesKey, "hex"));
|
||||||
|
return {
|
||||||
|
aesKey: key,
|
||||||
|
bleCommand: bleCommand.getCommandCode(),
|
||||||
|
payload: {
|
||||||
|
commandType: types_1.CommandType.CMD_SET_PAYLOAD,
|
||||||
|
value: JSON.stringify({
|
||||||
|
account_id: user_id,
|
||||||
|
cmd: types_1.CommandType.CMD_SET_PAYLOAD_LOCKV12,
|
||||||
|
mChannel: channel,
|
||||||
|
mValue3: 0,
|
||||||
|
payload: {
|
||||||
|
apiCommand: command,
|
||||||
|
lock_payload: bleCommand.getLockV12Command().toString("hex"),
|
||||||
|
seq_num: sequence,
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
};
|
||||||
|
};
|
||||||
|
exports.getLockV12P2PCommand = getLockV12P2PCommand;
|
||||||
|
const DecimalToRGBColor = function (color) {
|
||||||
|
return {
|
||||||
|
red: (color >> 16) & 0xff,
|
||||||
|
green: (color >> 8) & 0xff,
|
||||||
|
blue: color & 0xff,
|
||||||
|
};
|
||||||
|
};
|
||||||
|
exports.DecimalToRGBColor = DecimalToRGBColor;
|
||||||
|
const RGBColorToDecimal = function (color) {
|
||||||
|
return (color.red << 16) + (color.green << 8) + (color.blue);
|
||||||
|
};
|
||||||
|
exports.RGBColorToDecimal = RGBColorToDecimal;
|
||||||
|
const getNullTerminatedString = function (data, encoding) {
|
||||||
|
const index = data.indexOf(0);
|
||||||
|
return data.toString(encoding, 0, index === -1 ? data.length : index);
|
||||||
|
};
|
||||||
|
exports.getNullTerminatedString = getNullTerminatedString;
|
||||||
|
const isUsbCharging = function (value) {
|
||||||
|
return (value & 1) == 1;
|
||||||
|
};
|
||||||
|
exports.isUsbCharging = isUsbCharging;
|
||||||
|
const isSolarCharging = function (value) {
|
||||||
|
return ((value >> 2) & 1) == 1;
|
||||||
|
};
|
||||||
|
exports.isSolarCharging = isSolarCharging;
|
||||||
|
const isPlugSolarCharging = function (value) {
|
||||||
|
return ((value >> 3) & 1) == 1;
|
||||||
|
};
|
||||||
|
exports.isPlugSolarCharging = isPlugSolarCharging;
|
||||||
|
const isCharging = function (value) {
|
||||||
|
return (0, exports.isUsbCharging)(value) || (0, exports.isSolarCharging)(value) || (0, exports.isPlugSolarCharging)(value);
|
||||||
|
};
|
||||||
|
exports.isCharging = isCharging;
|
||||||
|
const getSmartLockCurrentTimeInSeconds = function () {
|
||||||
|
return Math.trunc(new Date().getTime() / 1000) | Math.trunc(Math.random() * 100);
|
||||||
|
};
|
||||||
|
exports.getSmartLockCurrentTimeInSeconds = getSmartLockCurrentTimeInSeconds;
|
||||||
|
const generateSmartLockAESKey = (adminUserId, time) => {
|
||||||
|
const buffer = Buffer.allocUnsafe(4);
|
||||||
|
buffer.writeUint32BE(time);
|
||||||
|
return Buffer.concat([Buffer.from(adminUserId.substring(adminUserId.length - 12)), buffer]);
|
||||||
|
};
|
||||||
|
exports.generateSmartLockAESKey = generateSmartLockAESKey;
|
||||||
|
const getSmartLockP2PCommand = function (deviceSN, user_id, command, channel, sequence, data, functionType = types_1.SmartLockFunctionType.TYPE_2) {
|
||||||
|
const time = (0, exports.getSmartLockCurrentTimeInSeconds)();
|
||||||
|
const key = (0, exports.generateSmartLockAESKey)(user_id, time);
|
||||||
|
const iv = (0, exports.getLockVectorBytes)(deviceSN);
|
||||||
|
const encPayload = (0, exports.encryptPayloadData)(data, key, Buffer.from(iv, "hex"));
|
||||||
|
logging_1.rootP2PLogger.debug(`Generate smart lock command`, { deviceSN: deviceSN, userId: user_id, command: command, channel: channel, sequence: sequence, data: data.toString("hex"), functionType: functionType });
|
||||||
|
let commandCode = 0;
|
||||||
|
if (functionType === types_1.SmartLockFunctionType.TYPE_1) {
|
||||||
|
commandCode = Number.parseInt(types_1.SmartLockBleCommandFunctionType1[types_1.SmartLockCommand[command]]);
|
||||||
|
}
|
||||||
|
else if (functionType === types_1.SmartLockFunctionType.TYPE_2) {
|
||||||
|
commandCode = Number.parseInt(types_1.SmartLockBleCommandFunctionType2[types_1.SmartLockCommand[command]]);
|
||||||
|
}
|
||||||
|
const bleCommand = new ble_1.BleCommandFactory()
|
||||||
|
.setVersionCode(device_1.Lock.VERSION_CODE_SMART_LOCK)
|
||||||
|
.setCommandCode(commandCode)
|
||||||
|
.setDataType(functionType)
|
||||||
|
.setData(encPayload);
|
||||||
|
return {
|
||||||
|
bleCommand: bleCommand.getCommandCode(),
|
||||||
|
payload: {
|
||||||
|
commandType: types_1.CommandType.CMD_SET_PAYLOAD,
|
||||||
|
value: JSON.stringify({
|
||||||
|
account_id: user_id,
|
||||||
|
cmd: types_1.CommandType.CMD_TRANSFER_PAYLOAD,
|
||||||
|
mChannel: channel,
|
||||||
|
mValue3: 0,
|
||||||
|
payload: {
|
||||||
|
apiCommand: command,
|
||||||
|
lock_payload: bleCommand.getSmartLockCommand().toString("hex"),
|
||||||
|
seq_num: sequence,
|
||||||
|
time: time,
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
};
|
||||||
|
};
|
||||||
|
exports.getSmartLockP2PCommand = getSmartLockP2PCommand;
|
||||||
|
const readNullTerminatedBuffer = (input) => {
|
||||||
|
const index = input.indexOf(new Uint8Array([0]));
|
||||||
|
if (index === -1) {
|
||||||
|
const result = Buffer.alloc(input.length);
|
||||||
|
input.copy(result);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
const result = Buffer.alloc(input.subarray(0, index).length);
|
||||||
|
input.subarray(0, index).copy(result);
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
exports.readNullTerminatedBuffer = readNullTerminatedBuffer;
|
||||||
|
//# sourceMappingURL=utils.js.map
|
||||||
1
build/p2p/utils.js.map
Normal file
1
build/p2p/utils.js.map
Normal file
File diff suppressed because one or more lines are too long
49
build/push/client.d.ts
vendored
Normal file
49
build/push/client.d.ts
vendored
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
import { TypedEmitter } from "tiny-typed-emitter";
|
||||||
|
import { PushClientEvents } from "./interfaces";
|
||||||
|
export declare class PushClient extends TypedEmitter<PushClientEvents> {
|
||||||
|
private readonly HOST;
|
||||||
|
private readonly PORT;
|
||||||
|
private readonly MCS_VERSION;
|
||||||
|
private readonly HEARTBEAT_INTERVAL;
|
||||||
|
private loggedIn;
|
||||||
|
private streamId;
|
||||||
|
private lastStreamIdReported;
|
||||||
|
private currentDelay;
|
||||||
|
private client?;
|
||||||
|
private heartbeatTimeout?;
|
||||||
|
private reconnectTimeout?;
|
||||||
|
private persistentIds;
|
||||||
|
private static proto;
|
||||||
|
private pushClientParser;
|
||||||
|
private auth;
|
||||||
|
private constructor();
|
||||||
|
static init(auth: {
|
||||||
|
androidId: string;
|
||||||
|
securityToken: string;
|
||||||
|
}): Promise<PushClient>;
|
||||||
|
private initialize;
|
||||||
|
getPersistentIds(): Array<string>;
|
||||||
|
setPersistentIds(ids: Array<string>): void;
|
||||||
|
connect(): void;
|
||||||
|
private buildLoginRequest;
|
||||||
|
private buildHeartbeatPingRequest;
|
||||||
|
private buildHeartbeatAckRequest;
|
||||||
|
private onSocketData;
|
||||||
|
private onSocketConnect;
|
||||||
|
private onSocketClose;
|
||||||
|
private onSocketError;
|
||||||
|
private handleParsedMessage;
|
||||||
|
private handleHeartbeatPing;
|
||||||
|
private handleHeartbeatAck;
|
||||||
|
private convertPayloadMessage;
|
||||||
|
private getStreamId;
|
||||||
|
private newStreamIdAvailable;
|
||||||
|
private scheduleHeartbeat;
|
||||||
|
private sendHeartbeat;
|
||||||
|
isConnected(): boolean;
|
||||||
|
private getHeartbeatInterval;
|
||||||
|
private getCurrentDelay;
|
||||||
|
private resetCurrentDelay;
|
||||||
|
private scheduleReconnect;
|
||||||
|
close(): void;
|
||||||
|
}
|
||||||
323
build/push/client.js
Normal file
323
build/push/client.js
Normal file
@ -0,0 +1,323 @@
|
|||||||
|
"use strict";
|
||||||
|
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
var desc = Object.getOwnPropertyDescriptor(m, k);
|
||||||
|
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
||||||
|
desc = { enumerable: true, get: function() { return m[k]; } };
|
||||||
|
}
|
||||||
|
Object.defineProperty(o, k2, desc);
|
||||||
|
}) : (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
o[k2] = m[k];
|
||||||
|
}));
|
||||||
|
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
||||||
|
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
||||||
|
}) : function(o, v) {
|
||||||
|
o["default"] = v;
|
||||||
|
});
|
||||||
|
var __importStar = (this && this.__importStar) || function (mod) {
|
||||||
|
if (mod && mod.__esModule) return mod;
|
||||||
|
var result = {};
|
||||||
|
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
||||||
|
__setModuleDefault(result, mod);
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
var __importDefault = (this && this.__importDefault) || function (mod) {
|
||||||
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.PushClient = void 0;
|
||||||
|
const long_1 = __importDefault(require("long"));
|
||||||
|
const path = __importStar(require("path"));
|
||||||
|
const protobufjs_1 = require("protobufjs");
|
||||||
|
const tls = __importStar(require("tls"));
|
||||||
|
const tiny_typed_emitter_1 = require("tiny-typed-emitter");
|
||||||
|
const models_1 = require("./models");
|
||||||
|
const parser_1 = require("./parser");
|
||||||
|
const utils_1 = require("../utils");
|
||||||
|
const error_1 = require("./error");
|
||||||
|
const error_2 = require("../error");
|
||||||
|
const utils_2 = require("../p2p/utils");
|
||||||
|
const logging_1 = require("../logging");
|
||||||
|
class PushClient extends tiny_typed_emitter_1.TypedEmitter {
|
||||||
|
HOST = "mtalk.google.com";
|
||||||
|
PORT = 5228;
|
||||||
|
MCS_VERSION = 41;
|
||||||
|
HEARTBEAT_INTERVAL = 5 * 60 * 1000;
|
||||||
|
loggedIn = false;
|
||||||
|
streamId = 0;
|
||||||
|
lastStreamIdReported = -1;
|
||||||
|
currentDelay = 0;
|
||||||
|
client;
|
||||||
|
heartbeatTimeout;
|
||||||
|
reconnectTimeout;
|
||||||
|
persistentIds = [];
|
||||||
|
static proto = null;
|
||||||
|
pushClientParser;
|
||||||
|
auth;
|
||||||
|
constructor(pushClientParser, auth) {
|
||||||
|
super();
|
||||||
|
this.pushClientParser = pushClientParser;
|
||||||
|
this.auth = auth;
|
||||||
|
}
|
||||||
|
static async init(auth) {
|
||||||
|
this.proto = await (0, protobufjs_1.load)(path.join(__dirname, "./proto/mcs.proto"));
|
||||||
|
const pushClientParser = await parser_1.PushClientParser.init();
|
||||||
|
return new PushClient(pushClientParser, auth);
|
||||||
|
}
|
||||||
|
initialize() {
|
||||||
|
this.loggedIn = false;
|
||||||
|
this.streamId = 0;
|
||||||
|
this.lastStreamIdReported = -1;
|
||||||
|
if (this.client) {
|
||||||
|
this.client.removeAllListeners();
|
||||||
|
this.client.destroy();
|
||||||
|
this.client = undefined;
|
||||||
|
}
|
||||||
|
this.pushClientParser.resetState();
|
||||||
|
if (this.reconnectTimeout) {
|
||||||
|
clearTimeout(this.reconnectTimeout);
|
||||||
|
this.reconnectTimeout = undefined;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
getPersistentIds() {
|
||||||
|
return this.persistentIds;
|
||||||
|
}
|
||||||
|
setPersistentIds(ids) {
|
||||||
|
this.persistentIds = ids;
|
||||||
|
}
|
||||||
|
connect() {
|
||||||
|
this.initialize();
|
||||||
|
this.pushClientParser.on("message", (message) => this.handleParsedMessage(message));
|
||||||
|
this.client = tls.connect(this.PORT, this.HOST, {
|
||||||
|
rejectUnauthorized: false,
|
||||||
|
});
|
||||||
|
this.client.setKeepAlive(true);
|
||||||
|
// For debugging purposes
|
||||||
|
//this.client.enableTrace();
|
||||||
|
this.client.on("connect", () => this.onSocketConnect());
|
||||||
|
this.client.on("close", () => this.onSocketClose());
|
||||||
|
this.client.on("error", (error) => this.onSocketError(error));
|
||||||
|
this.client.on("data", (newData) => this.onSocketData(newData));
|
||||||
|
this.client.write(this.buildLoginRequest());
|
||||||
|
}
|
||||||
|
buildLoginRequest() {
|
||||||
|
const androidId = this.auth.androidId;
|
||||||
|
const securityToken = this.auth.securityToken;
|
||||||
|
const LoginRequestType = PushClient.proto.lookupType("mcs_proto.LoginRequest");
|
||||||
|
const hexAndroidId = long_1.default.fromString(androidId).toString(16);
|
||||||
|
const loginRequest = {
|
||||||
|
adaptiveHeartbeat: false,
|
||||||
|
authService: 2,
|
||||||
|
authToken: securityToken,
|
||||||
|
id: "chrome-63.0.3234.0",
|
||||||
|
domain: "mcs.android.com",
|
||||||
|
deviceId: `android-${hexAndroidId}`,
|
||||||
|
networkType: 1,
|
||||||
|
resource: androidId,
|
||||||
|
user: androidId,
|
||||||
|
useRmq2: true,
|
||||||
|
setting: [{ name: "new_vc", value: "1" }],
|
||||||
|
clientEvent: [],
|
||||||
|
receivedPersistentId: this.persistentIds,
|
||||||
|
};
|
||||||
|
const errorMessage = LoginRequestType.verify(loginRequest);
|
||||||
|
if (errorMessage) {
|
||||||
|
throw new error_1.BuildLoginRequestError(errorMessage, { context: { loginRequest: loginRequest } });
|
||||||
|
}
|
||||||
|
const buffer = LoginRequestType.encodeDelimited(loginRequest).finish();
|
||||||
|
return Buffer.concat([Buffer.from([this.MCS_VERSION, models_1.MessageTag.LoginRequest]), buffer]);
|
||||||
|
}
|
||||||
|
buildHeartbeatPingRequest(stream_id) {
|
||||||
|
const heartbeatPingRequest = {};
|
||||||
|
if (stream_id) {
|
||||||
|
heartbeatPingRequest.last_stream_id_received = stream_id;
|
||||||
|
}
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - heartbeatPingRequest`, { streamId: stream_id, request: JSON.stringify(heartbeatPingRequest) });
|
||||||
|
const HeartbeatPingRequestType = PushClient.proto.lookupType("mcs_proto.HeartbeatPing");
|
||||||
|
const errorMessage = HeartbeatPingRequestType.verify(heartbeatPingRequest);
|
||||||
|
if (errorMessage) {
|
||||||
|
throw new error_1.BuildHeartbeatPingRequestError(errorMessage, { context: { heartbeatPingRequest: heartbeatPingRequest } });
|
||||||
|
}
|
||||||
|
const buffer = HeartbeatPingRequestType.encodeDelimited(heartbeatPingRequest).finish();
|
||||||
|
return Buffer.concat([Buffer.from([models_1.MessageTag.HeartbeatPing]), buffer]);
|
||||||
|
}
|
||||||
|
buildHeartbeatAckRequest(stream_id, status) {
|
||||||
|
const heartbeatAckRequest = {};
|
||||||
|
if (stream_id && !status) {
|
||||||
|
heartbeatAckRequest.last_stream_id_received = stream_id;
|
||||||
|
}
|
||||||
|
else if (!stream_id && status) {
|
||||||
|
heartbeatAckRequest.status = status;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
heartbeatAckRequest.last_stream_id_received = stream_id;
|
||||||
|
heartbeatAckRequest.status = status;
|
||||||
|
}
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - heartbeatAckRequest`, { streamId: stream_id, status: status, request: JSON.stringify(heartbeatAckRequest) });
|
||||||
|
const HeartbeatAckRequestType = PushClient.proto.lookupType("mcs_proto.HeartbeatAck");
|
||||||
|
const errorMessage = HeartbeatAckRequestType.verify(heartbeatAckRequest);
|
||||||
|
if (errorMessage) {
|
||||||
|
throw new error_1.BuildHeartbeatAckRequestError(errorMessage, { context: { heartbeatAckRequest: heartbeatAckRequest } });
|
||||||
|
}
|
||||||
|
const buffer = HeartbeatAckRequestType.encodeDelimited(heartbeatAckRequest).finish();
|
||||||
|
return Buffer.concat([Buffer.from([models_1.MessageTag.HeartbeatAck]), buffer]);
|
||||||
|
}
|
||||||
|
onSocketData(newData) {
|
||||||
|
this.pushClientParser.handleData(newData);
|
||||||
|
}
|
||||||
|
onSocketConnect() {
|
||||||
|
//
|
||||||
|
}
|
||||||
|
onSocketClose() {
|
||||||
|
this.loggedIn = false;
|
||||||
|
if (this.heartbeatTimeout) {
|
||||||
|
clearTimeout(this.heartbeatTimeout);
|
||||||
|
this.heartbeatTimeout = undefined;
|
||||||
|
}
|
||||||
|
this.emit("close");
|
||||||
|
this.scheduleReconnect();
|
||||||
|
}
|
||||||
|
onSocketError(err) {
|
||||||
|
const error = (0, error_2.ensureError)(err);
|
||||||
|
logging_1.rootPushLogger.error(`Push client - Socket Error`, { error: (0, utils_1.getError)(error) });
|
||||||
|
}
|
||||||
|
handleParsedMessage(message) {
|
||||||
|
this.resetCurrentDelay();
|
||||||
|
switch (message.tag) {
|
||||||
|
case models_1.MessageTag.DataMessageStanza:
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - DataMessageStanza`, { message: JSON.stringify(message) });
|
||||||
|
if (message.object && message.object.persistentId)
|
||||||
|
this.persistentIds.push(message.object.persistentId);
|
||||||
|
this.emit("message", this.convertPayloadMessage(message));
|
||||||
|
break;
|
||||||
|
case models_1.MessageTag.HeartbeatPing:
|
||||||
|
this.handleHeartbeatPing(message);
|
||||||
|
break;
|
||||||
|
case models_1.MessageTag.HeartbeatAck:
|
||||||
|
this.handleHeartbeatAck(message);
|
||||||
|
break;
|
||||||
|
case models_1.MessageTag.Close:
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - Close: Server requested close`, { message: JSON.stringify(message) });
|
||||||
|
break;
|
||||||
|
case models_1.MessageTag.LoginResponse:
|
||||||
|
logging_1.rootPushLogger.debug("Push client - Login response: GCM -> logged in -> waiting for push messages...", { message: JSON.stringify(message) });
|
||||||
|
this.loggedIn = true;
|
||||||
|
this.persistentIds = [];
|
||||||
|
this.emit("connect");
|
||||||
|
this.heartbeatTimeout = setTimeout(() => {
|
||||||
|
this.scheduleHeartbeat(this);
|
||||||
|
}, this.getHeartbeatInterval());
|
||||||
|
break;
|
||||||
|
case models_1.MessageTag.LoginRequest:
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - Login request`, { message: JSON.stringify(message) });
|
||||||
|
break;
|
||||||
|
case models_1.MessageTag.IqStanza:
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - IqStanza: Not implemented`, { message: JSON.stringify(message) });
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - Unknown message`, { message: JSON.stringify(message) });
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
this.streamId++;
|
||||||
|
}
|
||||||
|
handleHeartbeatPing(message) {
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - Heartbeat ping`, { message: JSON.stringify(message) });
|
||||||
|
let streamId = undefined;
|
||||||
|
let status = undefined;
|
||||||
|
if (this.newStreamIdAvailable()) {
|
||||||
|
streamId = this.getStreamId();
|
||||||
|
}
|
||||||
|
if (message.object && message.object.status) {
|
||||||
|
status = message.object.status;
|
||||||
|
}
|
||||||
|
if (this.client)
|
||||||
|
this.client.write(this.buildHeartbeatAckRequest(streamId, status));
|
||||||
|
}
|
||||||
|
handleHeartbeatAck(message) {
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - Heartbeat acknowledge`, { message: JSON.stringify(message) });
|
||||||
|
}
|
||||||
|
convertPayloadMessage(message) {
|
||||||
|
const { appData, ...otherData } = message.object;
|
||||||
|
const messageData = {};
|
||||||
|
appData.forEach((kv) => {
|
||||||
|
if (kv.key === "payload") {
|
||||||
|
const payload = (0, utils_1.parseJSON)((0, utils_2.getNullTerminatedString)(Buffer.from(kv.value, "base64"), "utf8"), logging_1.rootPushLogger);
|
||||||
|
messageData[kv.key] = payload;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
messageData[kv.key] = kv.value;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return {
|
||||||
|
...otherData,
|
||||||
|
payload: messageData,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
getStreamId() {
|
||||||
|
this.lastStreamIdReported = this.streamId;
|
||||||
|
return this.streamId;
|
||||||
|
}
|
||||||
|
newStreamIdAvailable() {
|
||||||
|
return this.lastStreamIdReported != this.streamId;
|
||||||
|
}
|
||||||
|
scheduleHeartbeat(client) {
|
||||||
|
if (client.sendHeartbeat()) {
|
||||||
|
this.heartbeatTimeout = setTimeout(() => {
|
||||||
|
this.scheduleHeartbeat(client);
|
||||||
|
}, client.getHeartbeatInterval());
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
logging_1.rootPushLogger.debug("Push client - Heartbeat disabled!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
sendHeartbeat() {
|
||||||
|
let streamId = undefined;
|
||||||
|
if (this.newStreamIdAvailable()) {
|
||||||
|
streamId = this.getStreamId();
|
||||||
|
}
|
||||||
|
if (this.client && this.isConnected()) {
|
||||||
|
logging_1.rootPushLogger.debug(`Push client - Sending heartbeat...`, { streamId: streamId });
|
||||||
|
this.client.write(this.buildHeartbeatPingRequest(streamId));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
logging_1.rootPushLogger.debug("Push client - No more connected, reconnect...");
|
||||||
|
this.scheduleReconnect();
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
isConnected() {
|
||||||
|
return this.loggedIn;
|
||||||
|
}
|
||||||
|
getHeartbeatInterval() {
|
||||||
|
return this.HEARTBEAT_INTERVAL;
|
||||||
|
}
|
||||||
|
getCurrentDelay() {
|
||||||
|
const delay = this.currentDelay == 0 ? 5000 : this.currentDelay;
|
||||||
|
if (this.currentDelay < 60000)
|
||||||
|
this.currentDelay += 10000;
|
||||||
|
if (this.currentDelay >= 60000 && this.currentDelay < 600000)
|
||||||
|
this.currentDelay += 60000;
|
||||||
|
return delay;
|
||||||
|
}
|
||||||
|
resetCurrentDelay() {
|
||||||
|
this.currentDelay = 0;
|
||||||
|
}
|
||||||
|
scheduleReconnect() {
|
||||||
|
const delay = this.getCurrentDelay();
|
||||||
|
logging_1.rootPushLogger.debug("Push client - Schedule reconnect...", { delay: delay });
|
||||||
|
if (!this.reconnectTimeout)
|
||||||
|
this.reconnectTimeout = setTimeout(() => {
|
||||||
|
this.connect();
|
||||||
|
}, delay);
|
||||||
|
}
|
||||||
|
close() {
|
||||||
|
const wasConnected = this.isConnected();
|
||||||
|
this.initialize();
|
||||||
|
if (wasConnected)
|
||||||
|
this.emit("close");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.PushClient = PushClient;
|
||||||
|
//# sourceMappingURL=client.js.map
|
||||||
1
build/push/client.js.map
Normal file
1
build/push/client.js.map
Normal file
File diff suppressed because one or more lines are too long
73
build/push/error.d.ts
vendored
Normal file
73
build/push/error.d.ts
vendored
Normal file
@ -0,0 +1,73 @@
|
|||||||
|
import { BaseError, Jsonable } from "../error";
|
||||||
|
export declare class UnknownExpiryFormaError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class FidRegistrationFailedError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class RenewFidTokenFailedError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class ExecuteCheckInError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class RegisterGcmError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BuildLoginRequestError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BuildHeartbeatPingRequestError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class BuildHeartbeatAckRequestError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class FidGenerationError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class MCSProtocolVersionError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class MCSProtocolProcessingStateError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
export declare class MCSProtocolMessageTagError extends BaseError {
|
||||||
|
constructor(message: string, options?: {
|
||||||
|
cause?: Error;
|
||||||
|
context?: Jsonable;
|
||||||
|
});
|
||||||
|
}
|
||||||
101
build/push/error.js
Normal file
101
build/push/error.js
Normal file
@ -0,0 +1,101 @@
|
|||||||
|
"use strict";
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.MCSProtocolMessageTagError = exports.MCSProtocolProcessingStateError = exports.MCSProtocolVersionError = exports.FidGenerationError = exports.BuildHeartbeatAckRequestError = exports.BuildHeartbeatPingRequestError = exports.BuildLoginRequestError = exports.RegisterGcmError = exports.ExecuteCheckInError = exports.RenewFidTokenFailedError = exports.FidRegistrationFailedError = exports.UnknownExpiryFormaError = void 0;
|
||||||
|
const error_1 = require("../error");
|
||||||
|
class UnknownExpiryFormaError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = UnknownExpiryFormaError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.UnknownExpiryFormaError = UnknownExpiryFormaError;
|
||||||
|
class FidRegistrationFailedError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = FidRegistrationFailedError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.FidRegistrationFailedError = FidRegistrationFailedError;
|
||||||
|
class RenewFidTokenFailedError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = RenewFidTokenFailedError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.RenewFidTokenFailedError = RenewFidTokenFailedError;
|
||||||
|
class ExecuteCheckInError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = ExecuteCheckInError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.ExecuteCheckInError = ExecuteCheckInError;
|
||||||
|
class RegisterGcmError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = RegisterGcmError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.RegisterGcmError = RegisterGcmError;
|
||||||
|
class BuildLoginRequestError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BuildLoginRequestError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BuildLoginRequestError = BuildLoginRequestError;
|
||||||
|
class BuildHeartbeatPingRequestError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BuildHeartbeatPingRequestError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BuildHeartbeatPingRequestError = BuildHeartbeatPingRequestError;
|
||||||
|
class BuildHeartbeatAckRequestError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = BuildHeartbeatAckRequestError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.BuildHeartbeatAckRequestError = BuildHeartbeatAckRequestError;
|
||||||
|
class FidGenerationError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = FidGenerationError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.FidGenerationError = FidGenerationError;
|
||||||
|
class MCSProtocolVersionError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = MCSProtocolVersionError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.MCSProtocolVersionError = MCSProtocolVersionError;
|
||||||
|
class MCSProtocolProcessingStateError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = MCSProtocolProcessingStateError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.MCSProtocolProcessingStateError = MCSProtocolProcessingStateError;
|
||||||
|
class MCSProtocolMessageTagError extends error_1.BaseError {
|
||||||
|
constructor(message, options = {}) {
|
||||||
|
super(message, options);
|
||||||
|
Object.setPrototypeOf(this, new.target.prototype);
|
||||||
|
this.name = MCSProtocolMessageTagError.name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
exports.MCSProtocolMessageTagError = MCSProtocolMessageTagError;
|
||||||
|
//# sourceMappingURL=error.js.map
|
||||||
1
build/push/error.js.map
Normal file
1
build/push/error.js.map
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"version":3,"file":"error.js","sourceRoot":"","sources":["../../src/push/error.ts"],"names":[],"mappings":";;;AAAA,oCAA+C;AAE/C,MAAa,uBAAwB,SAAQ,iBAAS;IAClD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,uBAAuB,CAAC,IAAI,CAAC;IAC7C,CAAC;CACJ;AAND,0DAMC;AAED,MAAa,0BAA2B,SAAQ,iBAAS;IACrD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,0BAA0B,CAAC,IAAI,CAAC;IAChD,CAAC;CACJ;AAND,gEAMC;AAED,MAAa,wBAAyB,SAAQ,iBAAS;IACnD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,wBAAwB,CAAC,IAAI,CAAC;IAC9C,CAAC;CACJ;AAND,4DAMC;AAED,MAAa,mBAAoB,SAAQ,iBAAS;IAC9C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,mBAAmB,CAAC,IAAI,CAAC;IACzC,CAAC;CACJ;AAND,kDAMC;AAED,MAAa,gBAAiB,SAAQ,iBAAS;IAC3C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,gBAAgB,CAAC,IAAI,CAAC;IACtC,CAAC;CACJ;AAND,4CAMC;AAED,MAAa,sBAAuB,SAAQ,iBAAS;IACjD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,sBAAsB,CAAC,IAAI,CAAC;IAC5C,CAAC;CACJ;AAND,wDAMC;AAED,MAAa,8BAA+B,SAAQ,iBAAS;IACzD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,8BAA8B,CAAC,IAAI,CAAC;IACpD,CAAC;CACJ;AAND,wEAMC;AAED,MAAa,6BAA8B,SAAQ,iBAAS;IACxD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,6BAA6B,CAAC,IAAI,CAAC;IACnD,CAAC;CACJ;AAND,sEAMC;AAED,MAAa,kBAAmB,SAAQ,iBAAS;IAC7C,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,kBAAkB,CAAC,IAAI,CAAC;IACxC,CAAC;CACJ;AAND,gDAMC;AAED,MAAa,uBAAwB,SAAQ,iBAAS;IAClD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,uBAAuB,CAAC,IAAI,CAAC;IAC7C,CAAC;CACJ;AAND,0DAMC;AAED,MAAa,+BAAgC,SAAQ,iBAAS;IAC1D,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,+BAA+B,CAAC,IAAI,CAAC;IACrD,CAAC;CACJ;AAND,0EAMC;AAED,MAAa,0BAA2B,SAAQ,iBAAS;IACrD,YAAY,OAAe,EAAE,UAAiD,EAAE;QAC5E,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QACxB,MAAM,CAAC,cAAc,CAAC,IAAI,EAAE,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QAClD,IAAI,CAAC,IAAI,GAAG,0BAA0B,CAAC,IAAI,CAAC;IAChD,CAAC;CACJ;AAND,gEAMC"}
|
||||||
6
build/push/index.d.ts
vendored
Normal file
6
build/push/index.d.ts
vendored
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
export * from "./models";
|
||||||
|
export * from "./interfaces";
|
||||||
|
export * from "./service";
|
||||||
|
export * from "./types";
|
||||||
|
export * from "./error";
|
||||||
|
export { sleep, convertTimestampMs } from "./utils";
|
||||||
26
build/push/index.js
Normal file
26
build/push/index.js
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
"use strict";
|
||||||
|
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
var desc = Object.getOwnPropertyDescriptor(m, k);
|
||||||
|
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
||||||
|
desc = { enumerable: true, get: function() { return m[k]; } };
|
||||||
|
}
|
||||||
|
Object.defineProperty(o, k2, desc);
|
||||||
|
}) : (function(o, m, k, k2) {
|
||||||
|
if (k2 === undefined) k2 = k;
|
||||||
|
o[k2] = m[k];
|
||||||
|
}));
|
||||||
|
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
||||||
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
exports.convertTimestampMs = exports.sleep = void 0;
|
||||||
|
__exportStar(require("./models"), exports);
|
||||||
|
__exportStar(require("./interfaces"), exports);
|
||||||
|
__exportStar(require("./service"), exports);
|
||||||
|
__exportStar(require("./types"), exports);
|
||||||
|
__exportStar(require("./error"), exports);
|
||||||
|
var utils_1 = require("./utils");
|
||||||
|
Object.defineProperty(exports, "sleep", { enumerable: true, get: function () { return utils_1.sleep; } });
|
||||||
|
Object.defineProperty(exports, "convertTimestampMs", { enumerable: true, get: function () { return utils_1.convertTimestampMs; } });
|
||||||
|
//# sourceMappingURL=index.js.map
|
||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user