mirror of
https://github.com/blakeblackshear/frigate.git
synced 2026-04-05 14:47:40 +03:00
dynamically update onvif config
This commit is contained in:
parent
6215501ae8
commit
932cca62c7
@ -131,6 +131,8 @@ class CameraConfigUpdateSubscriber:
|
||||
config.lpr = updated_config
|
||||
elif update_type == CameraConfigUpdateEnum.snapshots:
|
||||
config.snapshots = updated_config
|
||||
elif update_type == CameraConfigUpdateEnum.onvif:
|
||||
config.onvif = updated_config
|
||||
elif update_type == CameraConfigUpdateEnum.zones:
|
||||
config.zones = updated_config
|
||||
|
||||
|
||||
@ -15,6 +15,10 @@ from zeep.exceptions import Fault, TransportError
|
||||
|
||||
from frigate.camera import PTZMetrics
|
||||
from frigate.config import FrigateConfig, ZoomingModeEnum
|
||||
from frigate.config.camera.updater import (
|
||||
CameraConfigUpdateEnum,
|
||||
CameraConfigUpdateSubscriber,
|
||||
)
|
||||
from frigate.util.builtin import find_by_key
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
@ -65,7 +69,14 @@ class OnvifController:
|
||||
self.camera_configs[cam_name] = cam
|
||||
self.status_locks[cam_name] = asyncio.Lock()
|
||||
|
||||
self.config_subscriber = CameraConfigUpdateSubscriber(
|
||||
self.config,
|
||||
self.config.cameras,
|
||||
[CameraConfigUpdateEnum.onvif],
|
||||
)
|
||||
|
||||
asyncio.run_coroutine_threadsafe(self._init_cameras(), self.loop)
|
||||
asyncio.run_coroutine_threadsafe(self._poll_config_updates(), self.loop)
|
||||
|
||||
def _run_event_loop(self) -> None:
|
||||
"""Run the event loop in a separate thread."""
|
||||
@ -80,6 +91,52 @@ class OnvifController:
|
||||
for cam_name in self.camera_configs:
|
||||
await self._init_single_camera(cam_name)
|
||||
|
||||
async def _poll_config_updates(self) -> None:
|
||||
"""Poll for ONVIF config updates and re-initialize cameras as needed."""
|
||||
while True:
|
||||
await asyncio.sleep(1)
|
||||
try:
|
||||
updates = self.config_subscriber.check_for_updates()
|
||||
for update_type, cameras in updates.items():
|
||||
if update_type == CameraConfigUpdateEnum.onvif.name:
|
||||
for cam_name in cameras:
|
||||
await self._reinit_camera(cam_name)
|
||||
except Exception:
|
||||
logger.error("Error checking for ONVIF config updates")
|
||||
|
||||
async def _close_camera(self, cam_name: str) -> None:
|
||||
"""Close the ONVIF client session for a camera."""
|
||||
cam_state = self.cams.get(cam_name)
|
||||
if cam_state and "onvif" in cam_state:
|
||||
try:
|
||||
await cam_state["onvif"].close()
|
||||
except Exception:
|
||||
logger.debug(f"Error closing ONVIF session for {cam_name}")
|
||||
|
||||
async def _reinit_camera(self, cam_name: str) -> None:
|
||||
"""Re-initialize a camera after config change."""
|
||||
logger.info(f"Re-initializing ONVIF for {cam_name} due to config change")
|
||||
|
||||
# close existing session before re-init
|
||||
await self._close_camera(cam_name)
|
||||
|
||||
cam = self.config.cameras.get(cam_name)
|
||||
if not cam or not cam.onvif.host:
|
||||
# ONVIF removed from config, clean up
|
||||
self.cams.pop(cam_name, None)
|
||||
self.camera_configs.pop(cam_name, None)
|
||||
self.failed_cams.pop(cam_name, None)
|
||||
return
|
||||
|
||||
# update stored config and reset state
|
||||
self.camera_configs[cam_name] = cam
|
||||
if cam_name not in self.status_locks:
|
||||
self.status_locks[cam_name] = asyncio.Lock()
|
||||
self.cams.pop(cam_name, None)
|
||||
self.failed_cams.pop(cam_name, None)
|
||||
|
||||
await self._init_single_camera(cam_name)
|
||||
|
||||
async def _init_single_camera(self, cam_name: str) -> bool:
|
||||
"""Initialize a single camera by name.
|
||||
|
||||
@ -1041,6 +1098,7 @@ class OnvifController:
|
||||
return
|
||||
|
||||
logger.info("Exiting ONVIF controller...")
|
||||
self.config_subscriber.stop()
|
||||
|
||||
def stop_and_cleanup():
|
||||
try:
|
||||
|
||||
@ -19,16 +19,7 @@ const onvif: SectionConfigOverrides = {
|
||||
],
|
||||
advancedFields: ["tls_insecure", "ignore_time_mismatch"],
|
||||
overrideFields: [],
|
||||
restartRequired: [
|
||||
"host",
|
||||
"port",
|
||||
"user",
|
||||
"password",
|
||||
"profile",
|
||||
"tls_insecure",
|
||||
"ignore_time_mismatch",
|
||||
"autotracking.calibrate_on_startup",
|
||||
],
|
||||
restartRequired: ["autotracking.calibrate_on_startup"],
|
||||
uiSchema: {
|
||||
host: {
|
||||
"ui:options": { size: "sm" },
|
||||
|
||||
Loading…
Reference in New Issue
Block a user