feat(observatory): admit canonical recorded replay
This commit is contained in:
@@ -12,9 +12,10 @@ from pathlib import Path
|
||||
from typing import Any
|
||||
|
||||
import pytest
|
||||
from fastapi import APIRouter, HTTPException, Request, Response
|
||||
from fastapi import APIRouter, FastAPI, HTTPException, Request, Response
|
||||
from fastapi.responses import FileResponse
|
||||
from fastapi.routing import APIRoute
|
||||
from fastapi.testclient import TestClient
|
||||
|
||||
import k1link.sessions.media as recorded_media_module
|
||||
import k1link.web.session_api as session_api_module
|
||||
@@ -22,6 +23,7 @@ from k1link.compute import RecordedPerceptionOverlayArtifact, RecordedPerception
|
||||
from k1link.device_plugins.xgrids_k1 import xgrids_k1_archive_source
|
||||
from k1link.device_plugins.xgrids_k1.mqtt.capture import FRAME_HEADER, RAW_MAGIC
|
||||
from k1link.sessions import (
|
||||
LabReplayCapability,
|
||||
MaterializedRecording,
|
||||
RecordedMediaInspector,
|
||||
RecordedMediaManifest,
|
||||
@@ -347,6 +349,79 @@ def test_session_router_exposes_immutable_lab_provenance(tmp_path: Path) -> None
|
||||
assert_no_local_paths((item, detail), repository)
|
||||
|
||||
|
||||
def test_session_router_rolls_capability_projections_out_only_in_v2(
|
||||
tmp_path: Path,
|
||||
) -> None:
|
||||
repository = tmp_path / "repo"
|
||||
sessions = repository / "sessions"
|
||||
source = make_legacy_session(sessions, "20260716T205632Z_viewer_live")
|
||||
store = SessionStore(repository, data_dir=tmp_path / "data")
|
||||
store.reconcile_archive(xgrids_k1_archive_source(sessions))
|
||||
legacy = store.publish_lab_instance(
|
||||
session_id="lab-e21-legacy",
|
||||
source_session_id=source.name,
|
||||
display_name="LAB E21 · legacy",
|
||||
lab_id="LAB E21",
|
||||
result_kind="e21-realtime-envelope",
|
||||
result_id="e21-realtime-envelope-" + "1" * 64,
|
||||
run_created_at_utc="2026-07-23T15:55:15.548Z",
|
||||
provenance={"method": lab_method()},
|
||||
)
|
||||
capability = LabReplayCapability(
|
||||
schema_version="missioncore.observation-lab-replay-capability/v1",
|
||||
kind="canonical-recorded-rerun",
|
||||
viewer_profile="recorded-session",
|
||||
timeline="session_time",
|
||||
activation="explicit",
|
||||
commands_enabled=False,
|
||||
)
|
||||
canonical = store.publish_lab_instance(
|
||||
session_id="lab-v1-vegetation-shadow-" + "8" * 64,
|
||||
source_session_id=source.name,
|
||||
display_name="RAV004 · recorded",
|
||||
lab_id="LAB V1",
|
||||
result_kind="recorded-perception-qualification",
|
||||
result_id="lab-v1-vegetation-shadow-" + "8" * 64,
|
||||
run_created_at_utc="2026-08-29T18:05:11.329061+00:00",
|
||||
replay_capability=capability,
|
||||
provenance={
|
||||
"replay_capability": capability.as_dict(),
|
||||
"method": lab_method(),
|
||||
},
|
||||
)
|
||||
router = build_session_router(store)
|
||||
list_route = endpoint(router, "/api/v1/observation-sessions", "GET")
|
||||
|
||||
default_items = list_route(limit=20, cursor=None, scope="all")["items"]
|
||||
assert {item["id"] for item in default_items} == {source.name, legacy.session_id}
|
||||
default_legacy = next(item for item in default_items if item["id"] == legacy.session_id)
|
||||
assert "replay_capability" not in default_legacy["lab"]
|
||||
|
||||
v1_labs = list_route(
|
||||
limit=20,
|
||||
cursor=None,
|
||||
scope="laboratory",
|
||||
lab_contract="v1",
|
||||
)["items"]
|
||||
assert [item["id"] for item in v1_labs] == [legacy.session_id]
|
||||
v2_labs = list_route(
|
||||
limit=20,
|
||||
cursor=None,
|
||||
scope="laboratory",
|
||||
lab_contract="v2",
|
||||
)["items"]
|
||||
by_id = {item["id"]: item for item in v2_labs}
|
||||
assert set(by_id) == {legacy.session_id, canonical.session_id}
|
||||
assert by_id[legacy.session_id]["lab"]["replay_capability"] is None
|
||||
assert by_id[canonical.session_id]["lab"]["replay_capability"] == capability.as_dict()
|
||||
|
||||
application = FastAPI()
|
||||
application.include_router(router)
|
||||
assert TestClient(application).get(
|
||||
"/api/v1/observation-sessions?lab_contract=v3"
|
||||
).status_code == 422
|
||||
|
||||
|
||||
def test_delete_session_removes_evidence_and_cache_but_refuses_an_open_recording(
|
||||
tmp_path: Path,
|
||||
) -> None:
|
||||
|
||||
Reference in New Issue
Block a user