Cap quality replacement against tracked files only, not total Frigate count
Previously, effective_count and the jobs.py cap check used the total Frigate file count (including manually-added files), so any file a user curated by hand ate into winnow's managed quota. Now: - get_tracked_frigate_file_count() returns len(frigate_files) from the tracker — only files winnow uploaded and reconciled - effective_count in the upload loop uses this tracker count so manually-added files are invisible to the cap - jobs.py capacity check uses len(frigate_files) instead of the live Frigate API count or cached frigate_count - Frigate API call for known_frigate_files_at_start is now only used for the post-upload reconciliation diff, not for cap enforcement Side-effect: fixes audit bug #1 — an unreachable Frigate GET no longer zeroes effective_count and bypasses the cap, because the cap is now read from the always-available local tracker. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
+6
-4
@@ -19,6 +19,7 @@ from .immich_api import fetch_face_data, fetch_full_image
|
||||
from .log_config import console
|
||||
from .upload_tracker import (
|
||||
get_lowest_quality_mapped_file,
|
||||
get_tracked_frigate_file_count,
|
||||
mark_rejected,
|
||||
mark_uploaded,
|
||||
record_frigate_file,
|
||||
@@ -316,9 +317,11 @@ def upload_to_frigate(jobs: list[dict]) -> None:
|
||||
person_uploaded = 0
|
||||
person_failed = 0
|
||||
|
||||
known_frigate_files: set[str] = set(get_frigate_person_files(name) or [])
|
||||
known_frigate_files_at_start = set(known_frigate_files)
|
||||
effective_count = len(known_frigate_files)
|
||||
# Snapshot live Frigate files for post-upload reconciliation diff only.
|
||||
# effective_count is sourced from the tracker (mapped files) so that
|
||||
# manually-added Frigate files don't consume winnow's managed quota.
|
||||
known_frigate_files_at_start: set[str] = set(get_frigate_person_files(name) or [])
|
||||
effective_count = get_tracked_frigate_file_count(name)
|
||||
quality_replacement = job.get("config", {}).get("quality_replacement", False)
|
||||
actually_uploaded: list[tuple[str, str | None]] = []
|
||||
|
||||
@@ -353,7 +356,6 @@ def upload_to_frigate(jobs: list[dict]) -> None:
|
||||
)
|
||||
if delete_frigate_person_files(name, [worst_frigate_file]):
|
||||
remove_frigate_file(name, worst_frigate_file)
|
||||
known_frigate_files.discard(worst_frigate_file)
|
||||
effective_count -= 1
|
||||
else:
|
||||
logger.warning(f"Failed to delete {worst_frigate_file} for {name}, skipping replacement")
|
||||
|
||||
Reference in New Issue
Block a user