feat: consumption log top1 + elapsed since recording; RTSP play once
- Add top1_name/top1_conf to TSV and show top1–3 in pending markdown - Add 相对开录 column and pass since_recording_start from surgery start - Track surgery_started_wall and format_elapsed_mmss_since in session registry - Remove ffmpeg stream_loop from synthetic/demo fake RTSP (play once) - Fix fake_rtsp_from_file poll loop indentation; update README - Extend consumption TSV tests; add face test PNGs under tests/faces Made-with: Cursor
This commit is contained in:
@@ -12,7 +12,7 @@
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
from loguru import logger
|
||||
import time
|
||||
|
||||
from app.baked import pipeline as bp
|
||||
from app.services.consumable_vision_algorithm import (
|
||||
@@ -28,6 +28,7 @@ from app.services.video.inference_aggregator import WindowInferenceReady
|
||||
from app.services.video.session_registry import (
|
||||
SurgerySessionRegistry,
|
||||
SurgerySessionState,
|
||||
format_elapsed_mmss_since,
|
||||
)
|
||||
|
||||
|
||||
@@ -83,6 +84,10 @@ class VisionClassificationHandler:
|
||||
camera_id=camera_id,
|
||||
wall_start_epoch=ready.wall_lo,
|
||||
wall_end_epoch=ready.wall_hi,
|
||||
since_recording_start=format_elapsed_mmss_since(
|
||||
state.surgery_started_wall,
|
||||
at_epoch=ready.wall_hi,
|
||||
),
|
||||
)
|
||||
|
||||
async def handle(
|
||||
@@ -182,11 +187,7 @@ class VisionClassificationHandler:
|
||||
)
|
||||
if cid is None:
|
||||
return
|
||||
logger.info(
|
||||
"Enqueued pending consumable confirmation id={} top_key={}",
|
||||
cid,
|
||||
top_key,
|
||||
)
|
||||
at_ep = ready.wall_hi if ready is not None else time.time()
|
||||
if ready is not None and surgery_id and camera_id and (
|
||||
bp.CONSUMPTION_TSV_LOG_ENABLED
|
||||
or bp.CONSUMPTION_LOG_MARKDOWN_TERMINAL
|
||||
@@ -201,6 +202,10 @@ class VisionClassificationHandler:
|
||||
wall_end_epoch=ready.wall_hi,
|
||||
tsv_enabled=bp.CONSUMPTION_TSV_LOG_ENABLED,
|
||||
markdown_terminal=bp.CONSUMPTION_LOG_MARKDOWN_TERMINAL,
|
||||
since_recording_start=format_elapsed_mmss_since(
|
||||
state.surgery_started_wall,
|
||||
at_epoch=at_ep,
|
||||
),
|
||||
)
|
||||
await self._registry.append_pending_consumption_detail(
|
||||
state=state,
|
||||
|
||||
@@ -30,6 +30,7 @@ from app.services.video.session_registry import (
|
||||
RunningSurgery,
|
||||
SurgerySessionRegistry,
|
||||
SurgerySessionState,
|
||||
format_elapsed_mmss_since,
|
||||
)
|
||||
from app.services.tear_gated_segment_consumption.product_map import (
|
||||
load_tear_segment_name_to_id,
|
||||
@@ -166,6 +167,7 @@ class CameraSessionManager:
|
||||
state = SurgerySessionState(
|
||||
candidate_consumables=list(resolved),
|
||||
name_to_code=name_to_code,
|
||||
surgery_started_wall=time.time(),
|
||||
)
|
||||
stop_event = asyncio.Event()
|
||||
readies = [asyncio.Event() for _ in camera_ids]
|
||||
@@ -447,9 +449,13 @@ class CameraSessionManager:
|
||||
|
||||
if bp.VIDEO_LOG_INFERENCE_RESULTS:
|
||||
logger.info(
|
||||
"Vision result surgery={} camera={} top1={}({:.3f}) top2={}({:.3f}) top3={}({:.3f})",
|
||||
"Vision result surgery={} camera={} 相对开录={} top1={}({:.3f}) top2={}({:.3f}) top3={}({:.3f})",
|
||||
surgery_id,
|
||||
camera_id,
|
||||
format_elapsed_mmss_since(
|
||||
state.surgery_started_wall,
|
||||
at_epoch=time.time(),
|
||||
),
|
||||
snap.t1_name,
|
||||
snap.t1_conf,
|
||||
snap.t2_name,
|
||||
|
||||
@@ -29,6 +29,16 @@ from app.services.voice_confirm import build_prompt_text
|
||||
from app.surgery_errors import SurgeryPipelineError
|
||||
|
||||
|
||||
def format_elapsed_mmss_since(surgery_started_wall: float | None, *, at_epoch: float) -> str:
|
||||
"""从 ``start_surgery`` 记录的开录时刻到 ``at_epoch`` 的流逝时间(分+秒),供终端 loguru 使用。"""
|
||||
if surgery_started_wall is None:
|
||||
return "—"
|
||||
sec = max(0.0, at_epoch - surgery_started_wall)
|
||||
total = int(sec)
|
||||
m, s = divmod(total, 60)
|
||||
return f"{m}分{s:02d}秒"
|
||||
|
||||
|
||||
@dataclass
|
||||
class PendingConsumableConfirmation:
|
||||
"""待客户端确认的一条低置信度识别(不阻塞后续帧推理)。"""
|
||||
@@ -73,6 +83,8 @@ class SurgerySessionState:
|
||||
last_asr_text: str | None = None
|
||||
#: 最近一次语音确认错误说明(ASR/解析失败等)。
|
||||
last_voice_error: str | None = None
|
||||
#: ``start_surgery`` 创建会话时的 ``time.time()``,用于日志中「相对开录的流逝时间」。
|
||||
surgery_started_wall: float | None = None
|
||||
|
||||
|
||||
@dataclass
|
||||
|
||||
Reference in New Issue
Block a user