mirror of
https://github.com/blakeblackshear/frigate.git
synced 2026-02-08 12:15:25 +03:00
Refactor path handling
- Use pathlib for path joining sugar using slashes - Rename BASE_DIR to MEDIA_DIR, which is more meaningful - Introduce INSTALL_DIR for the installation base dir - Replace glob.glob usage with no wildcard to file existance check
This commit is contained in:
parent
3df8b5829c
commit
6596207fb4
@ -109,7 +109,7 @@ class FrigateApp:
|
||||
root_configurer(self.log_queue)
|
||||
|
||||
def init_config(self) -> None:
|
||||
config_file = os.environ.get("CONFIG_FILE", "/config/config.yml")
|
||||
config_file = os.environ.get("CONFIG_FILE", str(CONFIG_DIR / "config.yml"))
|
||||
|
||||
# Check if we can use .yaml instead of .yml
|
||||
config_file_yaml = config_file.replace(".yml", ".yaml")
|
||||
|
||||
@ -910,7 +910,7 @@ class CameraConfig(FrigateBaseModel):
|
||||
|
||||
|
||||
class DatabaseConfig(FrigateBaseModel):
|
||||
path: str = Field(default=DEFAULT_DB_PATH, title="Database path.")
|
||||
path: str = Field(default=str(DEFAULT_DB_PATH), title="Database path.")
|
||||
|
||||
|
||||
class LogLevelEnum(str, Enum):
|
||||
|
||||
@ -1,14 +1,23 @@
|
||||
CONFIG_DIR = "/config"
|
||||
DEFAULT_DB_PATH = f"{CONFIG_DIR}/frigate.db"
|
||||
MODEL_CACHE_DIR = f"{CONFIG_DIR}/model_cache"
|
||||
BASE_DIR = "/media/frigate"
|
||||
CLIPS_DIR = f"{BASE_DIR}/clips"
|
||||
RECORD_DIR = f"{BASE_DIR}/recordings"
|
||||
EXPORT_DIR = f"{BASE_DIR}/exports"
|
||||
BIRDSEYE_PIPE = "/tmp/cache/birdseye"
|
||||
CACHE_DIR = "/tmp/cache"
|
||||
from pathlib import Path
|
||||
|
||||
CACHE_DIR = Path("/tmp/cache")
|
||||
BIRDSEYE_PIPE = CACHE_DIR / "birdseye"
|
||||
|
||||
CONFIG_DIR = Path("/config")
|
||||
DEFAULT_DB_PATH = CONFIG_DIR / "frigate.db"
|
||||
MODEL_CACHE_DIR = CONFIG_DIR / "model_cache"
|
||||
|
||||
INSTALL_DIR = Path("/opt/frigate")
|
||||
|
||||
MEDIA_DIR = Path("/media/frigate")
|
||||
CLIPS_DIR = MEDIA_DIR / "clips"
|
||||
RECORD_DIR = MEDIA_DIR / "recordings"
|
||||
EXPORT_DIR = MEDIA_DIR / "exports"
|
||||
|
||||
YAML_EXT = (".yaml", ".yml")
|
||||
|
||||
FRIGATE_LOCALHOST = "http://127.0.0.1:5000"
|
||||
|
||||
PLUS_ENV_VAR = "PLUS_API_KEY"
|
||||
PLUS_API_HOST = "https://api.frigate.video"
|
||||
|
||||
|
||||
@ -10,6 +10,7 @@ import requests
|
||||
from pydantic import BaseModel, Extra, Field
|
||||
from pydantic.fields import PrivateAttr
|
||||
|
||||
from frigate.const import MODEL_CACHE_DIR
|
||||
from frigate.plus import PlusApi
|
||||
from frigate.util.builtin import load_labels
|
||||
|
||||
@ -83,7 +84,7 @@ class ModelConfig(BaseModel):
|
||||
return
|
||||
|
||||
model_id = self.path[7:]
|
||||
self.path = f"/config/model_cache/{model_id}"
|
||||
self.path = str(MODEL_CACHE_DIR / model_id)
|
||||
model_info_path = f"{self.path}.json"
|
||||
|
||||
# download the model if it doesn't exist
|
||||
|
||||
@ -15,6 +15,7 @@ except: # noqa: E722
|
||||
|
||||
from pydantic import Field
|
||||
|
||||
from frigate.const import MODEL_CACHE_DIR
|
||||
from frigate.detectors.detection_api import DetectionApi
|
||||
from frigate.detectors.detector_config import BaseDetectorConfig
|
||||
|
||||
@ -86,12 +87,10 @@ class Rknn(DetectionApi):
|
||||
else:
|
||||
model_suffix = yolov8_suffix[self.model_path]
|
||||
self.model_path = (
|
||||
"/config/model_cache/rknn/yolov8{suffix}-320x320-{soc}.rknn".format(
|
||||
suffix=model_suffix, soc=soc
|
||||
)
|
||||
MODEL_CACHE_DIR / f"rknn/yolov8{model_suffix}-320x320-{soc}.rknn"
|
||||
)
|
||||
|
||||
os.makedirs("/config/model_cache/rknn", exist_ok=True)
|
||||
os.makedirs(MODEL_CACHE_DIR / "rknn", exist_ok=True)
|
||||
if not os.path.isfile(self.model_path):
|
||||
logger.info(
|
||||
"Downloading yolov8{suffix} model.".format(suffix=model_suffix)
|
||||
|
||||
@ -1,6 +1,5 @@
|
||||
import base64
|
||||
import copy
|
||||
import glob
|
||||
import json
|
||||
import logging
|
||||
import os
|
||||
@ -41,7 +40,9 @@ from frigate.const import (
|
||||
CLIPS_DIR,
|
||||
CONFIG_DIR,
|
||||
EXPORT_DIR,
|
||||
INSTALL_DIR,
|
||||
MAX_SEGMENT_DURATION,
|
||||
MEDIA_DIR,
|
||||
RECORD_DIR,
|
||||
)
|
||||
from frigate.events.external import ExternalEventProcessor
|
||||
@ -1384,7 +1385,7 @@ def config():
|
||||
|
||||
@bp.route("/config/raw")
|
||||
def config_raw():
|
||||
config_file = os.environ.get("CONFIG_FILE", "/config/config.yml")
|
||||
config_file = os.environ.get("CONFIG_FILE", CONFIG_DIR / "config.yml")
|
||||
|
||||
# Check if we can use .yaml instead of .yml
|
||||
config_file_yaml = config_file.replace(".yml", ".yaml")
|
||||
@ -1434,7 +1435,7 @@ def config_save():
|
||||
|
||||
# Save the config to file
|
||||
try:
|
||||
config_file = os.environ.get("CONFIG_FILE", "/config/config.yml")
|
||||
config_file = os.environ.get("CONFIG_FILE", CONFIG_DIR / "config.yml")
|
||||
|
||||
# Check if we can use .yaml instead of .yml
|
||||
config_file_yaml = config_file.replace(".yml", ".yaml")
|
||||
@ -1647,11 +1648,11 @@ def latest_frame(camera_name):
|
||||
+ retry_interval
|
||||
):
|
||||
if current_app.camera_error_image is None:
|
||||
error_image = glob.glob("/opt/frigate/frigate/images/camera-error.jpg")
|
||||
error_image = INSTALL_DIR / "frigate/images/camera-error.jpg"
|
||||
|
||||
if len(error_image) > 0:
|
||||
if error_image.is_file():
|
||||
current_app.camera_error_image = cv2.imread(
|
||||
error_image[0], cv2.IMREAD_UNCHANGED
|
||||
str(error_image), cv2.IMREAD_UNCHANGED
|
||||
)
|
||||
|
||||
frame = current_app.camera_error_image
|
||||
@ -2097,7 +2098,7 @@ def preview_ts(camera_name, start_ts, end_ts):
|
||||
clips.append(
|
||||
{
|
||||
"camera": preview["camera"],
|
||||
"src": preview["path"].replace("/media/frigate", ""),
|
||||
"src": preview["path"].replace(MEDIA_DIR, ""),
|
||||
"type": "video/mp4",
|
||||
"start": preview["start_time"],
|
||||
"end": preview["end_time"],
|
||||
|
||||
@ -1,7 +1,6 @@
|
||||
"""Handle outputting birdseye frames via jsmpeg and go2rtc."""
|
||||
|
||||
import datetime
|
||||
import glob
|
||||
import logging
|
||||
import math
|
||||
import multiprocessing as mp
|
||||
@ -15,7 +14,7 @@ import cv2
|
||||
import numpy as np
|
||||
|
||||
from frigate.config import BirdseyeModeEnum, FrigateConfig
|
||||
from frigate.const import BASE_DIR, BIRDSEYE_PIPE
|
||||
from frigate.const import BIRDSEYE_PIPE, INSTALL_DIR, MEDIA_DIR
|
||||
from frigate.types import CameraMetricsTypes
|
||||
from frigate.util.image import (
|
||||
SharedMemoryFrameManager,
|
||||
@ -280,16 +279,16 @@ class BirdsEyeFrameManager:
|
||||
# find and copy the logo on the blank frame
|
||||
birdseye_logo = None
|
||||
|
||||
custom_logo_files = glob.glob(f"{BASE_DIR}/custom.png")
|
||||
custom_logo_file = MEDIA_DIR / "custom.png"
|
||||
|
||||
if len(custom_logo_files) > 0:
|
||||
birdseye_logo = cv2.imread(custom_logo_files[0], cv2.IMREAD_UNCHANGED)
|
||||
if custom_logo_file.is_file():
|
||||
birdseye_logo = cv2.imread(str(custom_logo_file), cv2.IMREAD_UNCHANGED)
|
||||
|
||||
if birdseye_logo is None:
|
||||
logo_files = glob.glob("/opt/frigate/frigate/images/birdseye.png")
|
||||
logo_file = INSTALL_DIR / "frigate/images/birdseye.png"
|
||||
|
||||
if len(logo_files) > 0:
|
||||
birdseye_logo = cv2.imread(logo_files[0], cv2.IMREAD_UNCHANGED)
|
||||
if logo_file.is_file():
|
||||
birdseye_logo = cv2.imread(str(logo_file), cv2.IMREAD_UNCHANGED)
|
||||
|
||||
if birdseye_logo is not None:
|
||||
transparent_layer = birdseye_logo[:, :, 3]
|
||||
|
||||
@ -300,7 +300,7 @@ def stats_snapshot(
|
||||
|
||||
for path in [RECORD_DIR, CLIPS_DIR, CACHE_DIR, "/dev/shm"]:
|
||||
try:
|
||||
storage_stats = shutil.disk_usage(path)
|
||||
storage_stats = shutil.disk_usage(str(path))
|
||||
except FileNotFoundError:
|
||||
stats["service"]["storage"][path] = {}
|
||||
continue
|
||||
@ -309,7 +309,7 @@ def stats_snapshot(
|
||||
"total": round(storage_stats.total / pow(2, 20), 1),
|
||||
"used": round(storage_stats.used / pow(2, 20), 1),
|
||||
"free": round(storage_stats.free / pow(2, 20), 1),
|
||||
"mount_type": get_fs_type(path),
|
||||
"mount_type": get_fs_type(str(path)),
|
||||
}
|
||||
|
||||
stats["processes"] = {}
|
||||
|
||||
@ -847,9 +847,9 @@ class TestConfig(unittest.TestCase):
|
||||
assert runtime_config.model.merged_labelmap[0] == "person"
|
||||
|
||||
def test_plus_labelmap(self):
|
||||
with open("/config/model_cache/test", "w") as f:
|
||||
with open(MODEL_CACHE_DIR / "test", "w") as f:
|
||||
json.dump(self.plus_model_info, f)
|
||||
with open("/config/model_cache/test.json", "w") as f:
|
||||
with open(MODEL_CACHE_DIR / "test.json", "w") as f:
|
||||
json.dump(self.plus_model_info, f)
|
||||
|
||||
config = {
|
||||
|
||||
@ -11,6 +11,7 @@ from playhouse.sqlite_ext import SqliteExtDatabase
|
||||
from playhouse.sqliteq import SqliteQueueDatabase
|
||||
|
||||
from frigate.config import FrigateConfig
|
||||
from frigate.const import CACHE_DIR, CLIPS_DIR, RECORD_DIR
|
||||
from frigate.http import create_app
|
||||
from frigate.models import Event, Recordings
|
||||
from frigate.plus import PlusApi
|
||||
@ -76,19 +77,19 @@ class TestHttp(unittest.TestCase):
|
||||
"total": 67.1,
|
||||
"used": 16.6,
|
||||
},
|
||||
"/media/frigate/clips": {
|
||||
str(CLIPS_DIR): {
|
||||
"free": 42429.9,
|
||||
"mount_type": "ext4",
|
||||
"total": 244529.7,
|
||||
"used": 189607.0,
|
||||
},
|
||||
"/media/frigate/recordings": {
|
||||
str(RECORD_DIR): {
|
||||
"free": 0.2,
|
||||
"mount_type": "ext4",
|
||||
"total": 8.0,
|
||||
"used": 7.8,
|
||||
},
|
||||
"/tmp/cache": {
|
||||
str(CACHE_DIR): {
|
||||
"free": 976.8,
|
||||
"mount_type": "tmpfs",
|
||||
"total": 1000.0,
|
||||
|
||||
Loading…
Reference in New Issue
Block a user