92 pull requests since 0.4.0 (plus 11 dependency bumps): the HomeBase S1 Pro and the portal's WebRTC route for call doorbells and PoE cameras, a PPCS relay fallback when no direct P2P path answers, per-mode push notification, lock actuation on the classic Wi-Fi lock and the T8530, and Tuya robots and mowers read the way the app reads them.
npm install @mega-yfue/eufy-sdk@0.5.0WebRTC portal route
- HomeBase S1 Pro (T9000): commands over the portal's control channel (#243), live view of the cameras behind it (#345), siren (#364, #401), a warm command session via the portal keepalive (#407), and no RTSP publish switch installed behind it (#453).
- Live video for the standalone T8223 (#419) and T8224 (#507) doorbells over the portal call.
- T8N00 PoE: commands over native call signaling (#354) and media over independent calls (#436). Independent optical views on NVR cameras (#479).
- A local candidate trickles only while the signalling socket is open (#363). A refused sign's error no longer echoes the token (#427). A peer that cannot be built ends its session and fails the bring-up with that error (#466).
P2P and live video
- Falls back to a PPCS relay when no direct path answers (#474), and a session whose RSA cipher key does not unwrap no longer fails (#505).
- Resync after unrecovered loss (#322), the app's attached live start selector (#337), probe receive buffers sized (#367), source timestamps kept for live timing (#368), and fMP4 durations on the arrival clock (#423). The original arrival time is exposed in readable envelopes (#396).
- Shared live consumers start at the next live keyframe (#483). Fragmented payloads are copied once (#392). UDP sends complete before close (#478).
- Session lifecycle: independent media survives a station control close (#393), a connected peer's END closes the session (#394), a session that acks forced starts but serves nothing is replaced (#390), level 2 is negotiated from a gateway-info reply sent in the clear (#391), and a cipher-0 own-session live view starts and stops unencrypted (#475).
- A failed live start traces its typed reason and stage (#462). Live-view quality can be set again over 2730 (#353). A short UDP receive buffer is noted at debug (#329).
- Audio: an
aac-eldframe carries the decoder config its framing lacks (#317), and talkback is sent in the codec the camera's speaker plays (#348).
Recordings. Recording pages are queried and archive downloads demonstrated (#313), and recording pictures are assembled before output (#312).
Arming. A device's push notification is read and set per guard mode, on stations (#357) and standalone cameras (#379). A T8410C gets its guard mode as the direct 1224 frame (#448).
Locks and SmartDrop
- The classic Wi-Fi lock actuates over its keyed-payload envelope (#232), and its padded result is read by its sign code (#485).
- T8530: control and status (#383), and its camera (#457).
- A standalone SmartDrop opens its lid with a level-2 key negotiated over RSA (#403).
Tuya robots and mowers
- Cloud login the way the app does it (#372). DPs read with
dp.get, also when the broker refuses the subscribe (#416), robots read without bringing up the broker (#440), refreshed on the cloud poll (#442), and last data points read from the cloud on load (#347). Clean-line devices are no longer subscribed on the AIoT broker (#434). - Read-only mower capability from the E15's Tuya schema (#366).
- Vacuum: one AutoClean pass starts an auto clean (#340), the alias names the robot (#344), suction range read when the catalog lists level names (#365), and a Raw-DP payload whose getter answers a boolean is kept (#443).
Devices and model
- New or corrected models: T8E00/T8P00 PoE (#355, #376, #438), T8213 (#356), T8210C (#358), T8354 with pan/tilt (#430), T90S0 smoke alarm (#452). Doorbells are typed from the app's doorbell tables rather than a row per model (#481).
- Capability fixes: S350 on/off through privacy mode (#321), T8423 spotlight (#351), E330 Pro spotlight (#406), T8171 spotlight not inferred (#498), T8134 ptz not granted (#431), T8442 night vision (#492), keypad charging and battery-low params (#496).
- The manifest says whether each property has been reported (#359), the property schema resolves from realtime evidence too (#335), and Wi-Fi signal is exposed (#352).
aiDetectType's JSON object form is read (#464), a stopped station alarm is told from a triggered one (#425), and a v2 thumbnail with encrypted chroma tables is recovered (#409). - A standalone camera can be restarted (#311). A wired station's session reopens after a standalone recycle (#426). Per-sensor indoor sensitivity is stored without warning (#405).
Push, HTTP, MQTT
- A push bring-up that failed at startup is retried (#377). Acknowledged persistent ids are dropped after an MCS login (#495). A transition push with nothing left to move lapses quietly (#341).
- Autonomous re-login stops once one needs a captcha or 2FA (#432), and a stored session from another country logs in again (#433).
- Each probed broker's refusal reason is named (#429), and push and broker connection errors name the socket (#451).
Repo. Release job's npm pinned to CI's (#343), T8N00 routing spec fixed (#374), Photo / Icon toggle in the devices gallery (#399).
Deps. node-datachannel ships as a dependency (#361), so the WebRTC route installs with the SDK. Latest compatible versions (#499), mqtt 5.16.1, protobufjs 8.8.1, vitest 5.0.5 and docs toolchain bumps (#332, #333, #334, #413, #414, #417, #482, #489, #490, #493, #503). npm audit is clean.
Breaking changes
LiveTracegains astart-failedphase (#462). A host typing an exhaustive table against the union needs the row before it compiles.LiveAudioFrameis a union keyed oncodec(#317). Anaac-eldframe always carriesconfig;aac-lcandg711aframes never do.LiveConsumer.primedis removed (#483). A host reading it no longer compiles.SharedLiveSourceOptions.onSessionUnreachablereturnsboolean(#390), notvoid. A() => voidcallback no longer typechecks.DpCatalog.enumRangesholdsstring[](#365), notnumber[].
No export removed. Two runtime exports added, MOWER_MEMBERS and SMART_DROP_MEMBERS (301, up from 299), and five types: MediaSourceSelection, MowerActions, SmartDropActions, ReceivedVideoFrame, TalkbackCodec.
What's Changed
- chore(deps-dev): bump source-map-js from 1.2.1 to 1.2.2 in /docs by @dependabot[bot] in #334
- chore(deps): bump brace-expansion from 5.0.9 to 5.0.12 in /docs by @dependabot[bot] in #333
- chore(deps): bump @vue/server-renderer and vue in /docs by @dependabot[bot] in #332
- fix(p2p): note a short UDP receive buffer at debug, not warn by @martijnpoppen in #329
- fix(p2p): resynchronize live video after unrecovered loss by @sapireli in #322
- feat(client): restart a standalone camera, not only a HomeBase by @martijnpoppen in #311
- fix(model): resolve the property schema from realtime evidence too by @martijnpoppen in #335
- feat(rtc): drive the HomeBase S1 Pro (T9000) over the portal's WebRTC control channel by @danymexi in #243
- fix(ci): pin the release job's npm to 11.5.1, the one CI runs by @lenoxys in #343
- fix(client): let a transition push with nothing left to move lapse quietly by @martijnpoppen in #341
- fix(p2p): match attached live start selector from the app by @sapireli in #337
- fix(vacuum): start an auto clean with one AutoClean pass by @martijnpoppen in #340
- fix(p2p): describe aac-eld audio with the decoder config its framing lacks by @abavyka in #317
- fix(client): read a robot's last data points from the cloud on load by @martijnpoppen in #347
- fix(client): name a robot vacuum by its alias, not the product label by @martijnpoppen in #344
- fix(model): register the T8213 Video Doorbell Dual as a doorbell by @max246 in #356
- feat(camera): expose reported Wi-Fi signal by @genomez in #352
- fix(light): send the T8423 spotlight enable on the level-1 int+string frame by @ImSkully in #351
- fix(p2p): send talkback in the codec the camera's speaker plays by @abavyka in #348
- fix(camera): set live-view quality again over 2730 by @lenoxys in #353
- fix(p2p): assemble recording pictures before producing output by @benhei2 in #312
- feat(p2p): query recording pages and demonstrate archive downloads by @benhei2 in #313
- fix(rtc): connect T8N00 commands through native call signaling by @fubo08 in #354
- feat(arming): read and set a device's push notification per guard mode by @lenoxys in #357
- fix(p2p): size adopted probe receive buffers by @sapireli in #367
- fix(model): classify the T8E00 PoE S4 as a camera by @fubo08 in #355
- fix(ci): set the T8N00 child channel in the routing spec by @lenoxys in #374
- fix(model): read a vacuum's suction range when the catalog lists level names by @martijnpoppen in #365
- fix(deps): ship node-datachannel as a dependency by @lenoxys in #361
- fix(rtc): trickle a local candidate only while the signalling socket is open by @danymexi in #363
- feat(p2p): preserve source timestamps for live video timing by @sapireli in #368
- feat(rtc): live view of a camera behind a HomeBase S1 Pro (T9000) by @danymexi in #345
- fix(client): retry a push bring-up that failed at startup by @martijnpoppen in #377
- feat(siren): sound a camera behind a HomeBase S1 Pro with the portal's command by @danymexi in #364
- fix(motion): store a per-sensor indoor sensitivity list without warning by @martijnpoppen in #405
- fix(model): register the T8210C variant as a Video Doorbell by @max246 in #358
- chore(deps): bump protobufjs from 8.8.0 to 8.8.1 by @dependabot[bot] in #417
- chore(deps-dev): bump the toolchain group with 2 updates by @dependabot[bot] in #413
- fix(rtc): drop the echoed token from a refused RTC sign's error by @max246 in #427
- fix(p2p): keep fMP4 video durations on the arrival clock by @max246 in #423
- perf(p2p): copy fragmented payloads once at completion by @sapireli in #392
- fix(light): route E330 Pro (T8600) spotlight switch to int-string wire by @bgagan4 in #406
- fix(ptz): recognize the T8E00 PoE S4 model by @fubo08 in #376
- fix(camera): route S350 on/off through privacy mode by @Tursko in #321
- chore(deps): bump actions/setup-node from 7.0.0 to 7.1.0 by @dependabot[bot] in #414
- fix(model): stop granting ptz to the fixed-lens T8134 from its preset params by @max246 in #431
- fix(model): register the T8354 Baby Monitor E21 with pan/tilt by @max246 in #430
- fix(mqtt): name each probed broker's reason when none grants the SUBSCRIBE by @max246 in #429
- fix(client): reopen a wired station's session after a standalone recycle by @max246 in #426
- fix(model): tell a stopped station alarm from a triggered one by @max246 in #425
- fix(image): recover a v2 thumbnail whose chroma tables are encrypted too by @danymexi in #409
- feat(rtc): keep a station's command session warm with the portal keepalive by @danymexi in #407
- fix(p2p): preserve independent media when station control closes by @sapireli in #393
- fix(p2p): close a session when its connected peer sends END by @sapireli in #394
- docs(gallery): add a Photo / Icon toggle to the devices gallery by @martijnpoppen in #399
- feat(model): say in the manifest whether the device has reported each property by @max246 in #359
- feat(transport): log into the Tuya cloud the way the app does (et=3, eh- account, wire names) by @martijnpoppen in #372
- fix(client): read Tuya DPs with dp.get, also when the broker refuses the subscribe by @martijnpoppen in #416
- feat(arming): read and set a standalone camera's notification per guard mode by @lenoxys in #379
- fix(client): don't subscribe Tuya clean-line devices on the AIoT broker by @martijnpoppen in #434
- feat(model): read-only mower capability from the E15's Tuya schema by @martijnpoppen in #366
- fix(http): stop autonomous re-login once one needs a captcha or 2FA by @max246 in #432
- fix(p2p): negotiate level 2 from a gateway-info reply sent in the clear by @lenoxys in #391
- fix(model): classify T8E00 and T8P00 PoE cameras as wired by @fubo08 in #438
- fix(client): read Tuya robots without bringing up the broker by @martijnpoppen in #440
- feat(p2p): expose original arrival time in readable envelopes by @sapireli in #396
- fix(http): log in again when the stored session's country differs by @max246 in #433
- fix(p2p): replace a session that acknowledges forced starts and serves nothing by @lenoxys in #390
- fix(model): classify the T90S0 smoke alarm as a sensor by @martijnpoppen in #452
- fix(transport): name the socket in a push or broker connection error by @martijnpoppen in #451
- fix(rtsp): install no publish switch behind a HomeBase S1 Pro by @martijnpoppen in #453
- feat(client): refresh Tuya robot state on the cloud poll by @martijnpoppen in #442
- fix(arming): send a T8410C its guard mode as the direct 1224 frame by @abavyka in #448
- feat(rtc): live video for the standalone T8223 doorbell over the portal call by @nothenkjan in #419
- fix(model): keep a Raw-DP payload whose getter answers a boolean by @martijnpoppen in #443
- feat(siren): admit six more camera models behind a HomeBase S1 Pro by @danymexi in #401
- feat(p2p): open a standalone SmartDrop's lid with a level-2 key negotiated over RSA by @danymexi in #403
- feat(lock): support for T8530 control and status reporting by @JohnONolan in #383
- fix(rtc): end a session whose peer cannot be built, and fail its bring-up with that error by @martijnpoppen in #466
- fix(model): read aiDetectType's JSON object form and type the clean-line direction as a string by @martijnpoppen in #464
- feat(rtc): serve T8N00 PoE camera media over independent calls by @fubo08 in #436
- feat(model): give the T8530 video lock its camera by @davidjortizrivera in #457
- chore(deps-dev): bump vite from 8.3.0 to 8.3.4 in /docs by @dependabot[bot] in #482
- fix(p2p): wait for UDP send completion before closing by @sapireli in #478
- feat(rtc): select independent optical views on NVR cameras by @fubo08 in #479
- fix(model): type a doorbell from the app's doorbell tables, not a row per model by @lenoxys in #481
- feat(p2p): trace a failed live start with its typed reason and stage by @lenoxys in #462
- chore(deps): bump markdown-it from 14.3.2 to 14.3.3 in /docs by @dependabot[bot] in #493
- chore(deps): bump protobufjs from 8.8.0 to 8.8.1 by @dependabot[bot] in #490
- chore(deps): bump mqtt from 5.16.0 to 5.16.1 by @dependabot[bot] in #489
- fix(p2p): read the lock's padded result by its sign code, not by a zero tail by @tturnerdev in #485
- fix(media): start shared live consumers at the next live keyframe by @sapireli in #483
- fix(p2p): start and stop a cipher-0 own-session live view unencrypted by @Bielecki-UK in #475
- chore(deps): bump markdown-it from 14.3.2 to 14.3.3 in /docs by @dependabot[bot] in #503
- fix: support T8442 night vision read and write by @minollo in #492
- fix(push): drop the persistent ids a successful MCS login acknowledged by @martijnpoppen in #495
- fix(keypad): read charging from 1655, move batteryLow to 1653 by @martijnpoppen in #496
- feat(lock): actuate the classic Wi-Fi lock over its keyed-payload envelope by @tturnerdev in #232
- chore(deps): bump dependencies to their latest compatible versions by @lenoxys in #499
- fix(light): don't infer spotlight support on T8171 by @BremerLabs in #498
- fix(p2p): don't fail a session whose RSA cipher key does not unwrap by @lenoxys in #505
- fix(rtc): route the standalone T8224 doorbell over the portal call route by @lenoxys in #507
- feat(p2p): fall back to a PPCS relay when no direct path answers by @martijnpoppen in #474
- release: 0.5.0 by @lenoxys in #508
New Contributors
- @abavyka made their first contribution in #317
- @benhei2 made their first contribution in #312
- @fubo08 made their first contribution in #354
- @bgagan4 made their first contribution in #406
- @nothenkjan made their first contribution in #419
- @JohnONolan made their first contribution in #383
- @davidjortizrivera made their first contribution in #457
- @Bielecki-UK made their first contribution in #475
- @minollo made their first contribution in #492
- @BremerLabs made their first contribution in #498
Full Changelog: v0.4.0...v0.5.0