123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102 |
- import json
- import logging
- import threading
- import time
- import psutil
- import shutil
- from frigate.config import FrigateConfig
- from frigate.const import RECORD_DIR, CLIPS_DIR, CACHE_DIR
- from frigate.version import VERSION
- logger = logging.getLogger(__name__)
- def stats_init(camera_metrics, detectors):
- stats_tracking = {
- "camera_metrics": camera_metrics,
- "detectors": detectors,
- "started": int(time.time()),
- }
- return stats_tracking
- def get_fs_type(path):
- bestMatch = ""
- fsType = ""
- for part in psutil.disk_partitions(all=True):
- if path.startswith(part.mountpoint) and len(bestMatch) < len(part.mountpoint):
- fsType = part.fstype
- bestMatch = part.mountpoint
- return fsType
- def stats_snapshot(stats_tracking):
- camera_metrics = stats_tracking["camera_metrics"]
- stats = {}
- total_detection_fps = 0
- for name, camera_stats in camera_metrics.items():
- total_detection_fps += camera_stats["detection_fps"].value
- stats[name] = {
- "camera_fps": round(camera_stats["camera_fps"].value, 2),
- "process_fps": round(camera_stats["process_fps"].value, 2),
- "skipped_fps": round(camera_stats["skipped_fps"].value, 2),
- "detection_fps": round(camera_stats["detection_fps"].value, 2),
- "pid": camera_stats["process"].pid,
- "capture_pid": camera_stats["capture_process"].pid,
- }
- stats["detectors"] = {}
- for name, detector in stats_tracking["detectors"].items():
- stats["detectors"][name] = {
- "inference_speed": round(detector.avg_inference_speed.value * 1000, 2),
- "detection_start": detector.detection_start.value,
- "pid": detector.detect_process.pid,
- }
- stats["detection_fps"] = round(total_detection_fps, 2)
- stats["service"] = {
- "uptime": (int(time.time()) - stats_tracking["started"]),
- "version": VERSION,
- "storage": {},
- }
- for path in [RECORD_DIR, CLIPS_DIR, CACHE_DIR, "/dev/shm"]:
- storage_stats = shutil.disk_usage(path)
- stats["service"]["storage"][path] = {
- "total": round(storage_stats.total / 1000000, 1),
- "used": round(storage_stats.used / 1000000, 1),
- "free": round(storage_stats.free / 1000000, 1),
- "mount_type": get_fs_type(path),
- }
- return stats
- class StatsEmitter(threading.Thread):
- def __init__(
- self,
- config: FrigateConfig,
- stats_tracking,
- mqtt_client,
- topic_prefix,
- stop_event,
- ):
- threading.Thread.__init__(self)
- self.name = "frigate_stats_emitter"
- self.config = config
- self.stats_tracking = stats_tracking
- self.mqtt_client = mqtt_client
- self.topic_prefix = topic_prefix
- self.stop_event = stop_event
- def run(self):
- time.sleep(10)
- while not self.stop_event.wait(self.config.mqtt.stats_interval):
- stats = stats_snapshot(self.stats_tracking)
- self.mqtt_client.publish(
- f"{self.topic_prefix}/stats", json.dumps(stats), retain=False
- )
- logger.info(f"Exiting watchdog...")
|