python-aidot-cameras 0.5.16__tar.gz → 0.5.17__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {python_aidot_cameras-0.5.16/src/python_aidot_cameras.egg-info → python_aidot_cameras-0.5.17}/PKG-INFO +1 -1
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/pyproject.toml +1 -1
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/device_client.py +12 -12
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17/src/python_aidot_cameras.egg-info}/PKG-INFO +1 -1
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/LICENSE +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/README.md +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/setup.cfg +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/__init__.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/aes_utils.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/client.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/const.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/credentials.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/discover.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/exceptions.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/aidot/g711.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/python_aidot_cameras.egg-info/SOURCES.txt +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/python_aidot_cameras.egg-info/dependency_links.txt +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/python_aidot_cameras.egg-info/requires.txt +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/src/python_aidot_cameras.egg-info/top_level.txt +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_alarm_event.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_highport_nomination.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_motion_poll.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_no_undefined_names.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_sdes_idle_release.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_sdes_sprop.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_sdes_talk.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_sdes_watchdog.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_speak.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_stream_cap.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_talk.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_terminal_ack.py +0 -0
- {python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_token_refresh.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: python-aidot-cameras
|
|
3
|
-
Version: 0.5.
|
|
3
|
+
Version: 0.5.17
|
|
4
4
|
Summary: Control AiDot/Leedarson WiFi lights and cameras (WebRTC streaming, two-way audio, PTZ, controls)
|
|
5
5
|
Author-email: cbrightly <chris.brightly@gmail.com>
|
|
6
6
|
License-Expression: MIT
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "python-aidot-cameras"
|
|
7
|
-
version = "0.5.
|
|
7
|
+
version = "0.5.17"
|
|
8
8
|
description = "Control AiDot/Leedarson WiFi lights and cameras (WebRTC streaming, two-way audio, PTZ, controls)"
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
license = "MIT"
|
|
@@ -245,7 +245,7 @@ class DeviceInformation:
|
|
|
245
245
|
# Local device access password (TUTK viewPwd candidate)
|
|
246
246
|
device_password: str
|
|
247
247
|
# TUTK IOCtrl direction codes the camera advertises (e.g. [3,6] = left+right
|
|
248
|
-
# for a pan-only camera, [1,2,3,6] = full PTZ). Empty means unknown
|
|
248
|
+
# for a pan-only camera, [1,2,3,6] = full PTZ). Empty means unknown - callers
|
|
249
249
|
# should treat unknown as "show all" for backward compatibility.
|
|
250
250
|
ptz_directions: list
|
|
251
251
|
|
|
@@ -2062,7 +2062,7 @@ def _save_sprop(devid: str, sprop: str) -> None:
|
|
|
2062
2062
|
except OSError as exc:
|
|
2063
2063
|
# Surface (don't swallow): if the cache dir isn't writable the whole
|
|
2064
2064
|
# sprop feature is silently inert. AIDOT_SPROP_DIR can redirect it.
|
|
2065
|
-
_LOGGER.warning("sprop cache write failed (%s): %s
|
|
2065
|
+
_LOGGER.warning("sprop cache write failed (%s): %s - set AIDOT_SPROP_DIR "
|
|
2066
2066
|
"to a writable path", _SPROP_DIR, exc)
|
|
2067
2067
|
|
|
2068
2068
|
|
|
@@ -2258,7 +2258,7 @@ def _dtls_av_mux_run(vq, aq, out_fileobj, progress, stop_flag) -> None:
|
|
|
2258
2258
|
if fr is None:
|
|
2259
2259
|
# 160 PCMA samples → 960 resampled @ 48 kHz, but AAC needs 1024.
|
|
2260
2260
|
# Every ~17 packets (~340 ms) the FIFO falls 64 samples short
|
|
2261
|
-
# and would skip an entire 21 ms frame
|
|
2261
|
+
# and would skip an entire 21 ms frame - audible choppiness.
|
|
2262
2262
|
# Pad the leftover with silence so the frame is complete.
|
|
2263
2263
|
s = getattr(fifo, "samples", 0)
|
|
2264
2264
|
if s == 0:
|
|
@@ -2295,7 +2295,7 @@ def _dtls_av_mux_run(vq, aq, out_fileobj, progress, stop_flag) -> None:
|
|
|
2295
2295
|
while not stop_flag.is_set():
|
|
2296
2296
|
_flush_video()
|
|
2297
2297
|
_flush_audio()
|
|
2298
|
-
_t.sleep(0.005) # 5 ms
|
|
2298
|
+
_t.sleep(0.005) # 5 ms - processes audio within 5 ms of arrival vs 20 ms
|
|
2299
2299
|
_flush_video()
|
|
2300
2300
|
_flush_audio()
|
|
2301
2301
|
try:
|
|
@@ -3657,7 +3657,7 @@ class DeviceClient(object):
|
|
|
3657
3657
|
async def async_set_motion_sensitivity(self, level: int) -> bool:
|
|
3658
3658
|
"""Set motion detection sensitivity.
|
|
3659
3659
|
|
|
3660
|
-
level: 1 (lowest)
|
|
3660
|
+
level: 1 (lowest) - 5 (highest).
|
|
3661
3661
|
Attribute: MotionDetection_Sen (observed value '2' on A000088).
|
|
3662
3662
|
"""
|
|
3663
3663
|
return await self.async_set_device_attribute(
|
|
@@ -4360,7 +4360,7 @@ class DeviceClient(object):
|
|
|
4360
4360
|
"""True if a TCP client is connected to the SDES serve ``port`` (a viewer
|
|
4361
4361
|
is pulling), False if none, None if the TCP table can't be read (non-Linux
|
|
4362
4362
|
/ sandboxed host). The caller MUST treat None as 'unknown' and NOT release
|
|
4363
|
-
|
|
4363
|
+
- failing safe to the current always-reconnect behaviour."""
|
|
4364
4364
|
read_any = False
|
|
4365
4365
|
found = False
|
|
4366
4366
|
for _path in ("/proc/net/tcp", "/proc/net/tcp6"):
|
|
@@ -4413,7 +4413,7 @@ class DeviceClient(object):
|
|
|
4413
4413
|
_idle_release = False
|
|
4414
4414
|
# No-viewer release. Unlike the DTLS serve (which idle-releases when
|
|
4415
4415
|
# its mux pipe goes stale), an SDES keepalive otherwise reconnects
|
|
4416
|
-
# FOREVER even with zero HA consumers
|
|
4416
|
+
# FOREVER even with zero HA consumers - a battery-draining orphan that
|
|
4417
4417
|
# also holds a stream slot and TURN-relay bandwidth. SDES has no mux
|
|
4418
4418
|
# pipe to watch, so detect "nobody is pulling" via an ESTABLISHED TCP
|
|
4419
4419
|
# connection on the -listen serve port and release after the same idle
|
|
@@ -5403,7 +5403,7 @@ class DeviceClient(object):
|
|
|
5403
5403
|
|
|
5404
5404
|
# AIDOT_FAST_CONNECT (default off): LAN-direct mode. Both transports stall
|
|
5405
5405
|
# the offer on a TURN relay allocation to the cloud TURN server before ICE
|
|
5406
|
-
# can even start
|
|
5406
|
+
# can even start - for DTLS, aiortc's setLocalDescription blocks until ICE
|
|
5407
5407
|
# gathering (incl. TURN Allocate) completes; for SDES we synchronously
|
|
5408
5408
|
# pre-allocate relay before building the offer. On a LAN the camera's host
|
|
5409
5409
|
# candidate wins anyway, so this is pure cold-start latency (~2-3 s). When
|
|
@@ -6085,7 +6085,7 @@ class DeviceClient(object):
|
|
|
6085
6085
|
# setKeepAliveTime keeps the camera in active state for 25 s
|
|
6086
6086
|
# after wake (n.java:224 - keepAliveTime=25, not 20).
|
|
6087
6087
|
# Without this call the camera's built-in timer may return it
|
|
6088
|
-
# to sleep before SCTP + LIVING completes (~10
|
|
6088
|
+
# to sleep before SCTP + LIVING completes (~10-15 s).
|
|
6089
6089
|
try:
|
|
6090
6090
|
import aiohttp as _aiohttp_k
|
|
6091
6091
|
async with _aiohttp_k.ClientSession() as _ks:
|
|
@@ -6203,7 +6203,7 @@ class DeviceClient(object):
|
|
|
6203
6203
|
# cold-start cost (camera-awake → ICE-servers ≈ 2.5 s = 0.5 s echo +
|
|
6204
6204
|
# 2.0 s here). The official app does NOT wait for/parse livePlayResp
|
|
6205
6205
|
# (parity-confirmed). AIDOT_FAST_CONNECT skips it and proceeds to
|
|
6206
|
-
# SDP/ICE immediately
|
|
6206
|
+
# SDP/ICE immediately - losing fast-fail on rejection (rare; ICE then
|
|
6207
6207
|
# fails instead) in exchange for ~2 s off every LAN connect.
|
|
6208
6208
|
if not _fast_connect:
|
|
6209
6209
|
try:
|
|
@@ -6227,7 +6227,7 @@ class DeviceClient(object):
|
|
|
6227
6227
|
# once a live camera session is active (i.e. after livePlayReq).
|
|
6228
6228
|
# Waiting here ensures TURN credentials arrive before RTCPeerConnection
|
|
6229
6229
|
# is created. MEASURED (2026-06-07, live): this wait is the DOMINANT
|
|
6230
|
-
# cold-start cost
|
|
6230
|
+
# cold-start cost - ~2.5 s for getIceConfigResp to arrive after camera
|
|
6231
6231
|
# wake (NOT the TURN gather, which is ~70 ms). AIDOT_FAST_CONNECT
|
|
6232
6232
|
# skips it: we proceed immediately on STUN/host candidates (no relay),
|
|
6233
6233
|
# so a LAN camera connects in ~1 s. getIceConfigResp only supplies the
|
|
@@ -6459,7 +6459,7 @@ class DeviceClient(object):
|
|
|
6459
6459
|
)
|
|
6460
6460
|
if _fast_connect:
|
|
6461
6461
|
# Strip TURN URIs so aiortc's setLocalDescription doesn't block on a
|
|
6462
|
-
# TURN Allocate round-trip during ICE gathering
|
|
6462
|
+
# TURN Allocate round-trip during ICE gathering - the LAN host
|
|
6463
6463
|
# candidate then connects in ~1 s. Keep STUN (cheap, no allocate).
|
|
6464
6464
|
_stun_only = []
|
|
6465
6465
|
for _srv in _ice_servers:
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: python-aidot-cameras
|
|
3
|
-
Version: 0.5.
|
|
3
|
+
Version: 0.5.17
|
|
4
4
|
Summary: Control AiDot/Leedarson WiFi lights and cameras (WebRTC streaming, two-way audio, PTZ, controls)
|
|
5
5
|
Author-email: cbrightly <chris.brightly@gmail.com>
|
|
6
6
|
License-Expression: MIT
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_highport_nomination.py
RENAMED
|
File without changes
|
|
File without changes
|
{python_aidot_cameras-0.5.16 → python_aidot_cameras-0.5.17}/tests/test_no_undefined_names.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|