# NODEDC MISSION CORE monorepo This document maps the current repository to the target Mission Core architecture without claiming that deferred package and process boundaries already exist. The accepted device-lifecycle decision is recorded in [`ADR 0004`](adr/0004-plugin-sdk-v0alpha2-and-experimental-device-lifecycle.md). ## Current layout | Path | Current responsibility | Target responsibility | | --- | --- | --- | | `apps/control-station/` | React shell, device workflow, spatial scene | Vendor-neutral operator application | | `packages/plugin-sdk/` | Installable v0alpha2 Pydantic contracts and JSON Schema export | Portable host/plugin identity, lifecycle, stream and evidence boundary | | `plugins/xgrids-k1/` | v1alpha2 manifest, exact compatibility profile, fail-closed loader and extraction documentation | Independently versioned XGRIDS device plugin | | `src/k1link/web/` | Local FastAPI host, in-memory operation/acquisition lifecycle and transitional XGRIDS facade | Generic host APIs plus isolated plugin supervisor | | `src/k1link/mqtt/` | Raw-first K1 MQTT capture | Plugin-owned transport behind an EvidenceStore | | `src/k1link/protocol/` | Firmware-scoped K1 codecs and explicit vendor normalizer | Plugin-owned protocol adapter | | `src/k1link/data_plane/` | Transport-neutral decoded in-process consumer views | Local projections hydrated from portable SDK envelopes | | `src/k1link/viewer/` | Rerun consumer, visualization runtime and legacy Foxglove regression module | Replaceable canonical scene sink and presentation adapters | | `docs/domain-model/` | Versioned experimental Mission Core vocabulary | Promotion source for meanings proven across devices/services | ## Implemented boundary The current K1 live/replay data path is: ```text raw K1 transport -> raw-first evidence capture -> bounded preview queue -> XGRIDS normalizer injected by the plugin facade -> DecodedPointCloudView / DecodedPoseView -> Rerun bridge -> embedded local viewer ``` Rerun does not import K1 protocol code, inspect MQTT topics or receive raw payloads. `VisualizationRuntime` cannot choose a vendor decoder implicitly; its composition owner injects one. The local `Decoded*View` classes are in-process consumer projections, not the portable Plugin SDK wire envelopes. The Plugin SDK v0alpha2 separately defines model/device/session identity, operation events, acquisition-related session state, canonical stream envelopes, payload handles, evidence lineage and compatibility assessments. It is importable through the root editable path dependency and independently buildable from `packages/plugin-sdk`. The hot K1 path does not yet instantiate all SDK envelopes or use the SDK `EvidenceStore` protocol. ## Experimental vocabulary, not Platform Ontology The local vocabulary distinguishes: ```text model != device != transport alias != device session acquisition != operation != source/channel != evidence acknowledgement != completion raw evidence != decoded data != viewer state ``` These meanings remain versioned under `docs/domain-model/` and do not mutate or create a runtime dependency on NODE.DC Platform Ontology. Promotion requires a second device family or another platform service using the same stable meaning, an owner, lifecycle, compatibility policy and migration tests. ## Plugin manifest and compatibility The catalog accepts existing v1alpha1 manifests and additive v1alpha2 manifests. v1alpha1 remains a one-model contract; v1alpha2 accepts one or more models and requires every model to be covered by a reviewed, plugin-local, path-confined compatibility profile. The current XGRIDS profile matches exactly: - XGRIDS LixelKity K1; - firmware `3.0.2`; - direct-LAN topology; - one retained physical laboratory evidence scope. Unknown or unattested firmware fails closed. The current runtime does not read firmware from the device: it activates this limited, read-only profile only after explicit operator attestation of firmware `3.0.2` and direct-LAN topology, and records the basis as `operator-attested`. That claim is not device-derived proof. The profile independently records observation, decode, replay, physical-verification and write evidence. Loading it cannot authorize a transport mutation. Application-command publishing remains disabled; the separately reviewed BLE Wi-Fi provisioning write retains its own explicit operator gate. ## Semantic lifecycle The transitional facade now creates separate provisional device, device-session, acquisition and operation IDs. Acquisition can be prepared, wait for receiver readiness, then wait for an external physical start, and become acquiring only after real point data, wait for an externally confirmed stop, finalize and complete. Capture-only stop reports the K1 physical state as unknown. The operation journal is bounded and in memory. It records IDs, idempotency, declared deadlines, progress and terminal results without action parameters or secrets. It is not durable, distributed or recoverable after process restart. Semantic acquisition actions coexist with legacy `stream.*` actions for v1alpha1/UI compatibility. On this profile, start and stop operate the local receiver and operator workflow only. K1 scanning is still started and stopped by physical double-click; no modeling request is published. Left/right camera preview transport, endpoint paths and H.264 framing are now observed under the exact compatibility profile. The read-only runtime adapter is not implemented yet. Device status and heartbeat remain raw observed channels without semantic decoders. Device calibration command and sensor-to-vehicle extrinsics are unavailable. ## Remaining extraction order 1. Preserve native replay parity and repeat the exact-profile physical point/pose regression through the explicit normalizer boundary. 2. Map portable SDK stream/evidence contracts onto the hot path without replacing raw evidence or changing consumer output. 3. Extract codecs, normalizer and raw capture physically behind the XGRIDS plugin package boundary. 4. Add process isolation and a durable operation/evidence supervisor. 5. Replace compatibility routes and singleton state with multi-device session routing. 6. Split Edge execution from the Control Station behind authenticated transport. 7. Implement the now-observed read-only RTSP/H.264 camera adapter; keep the modeling-command publisher disabled until its separate safety gate closes. ## Invariants - Raw evidence is persisted before preview work and is never overwritten by a decode result. - Mission Core starts when the XGRIDS manifest is absent. Formal installed plugin quarantine remains a future supervisor feature. - Core code does not branch on XGRIDS IDs, fields, topics or firmware. - A plugin cannot add global navigation or arbitrary CSS. - A transport alias never becomes a stable device identity merely because it appears in a vendor header. - Acknowledgement, first data, operator confirmation and physical completion remain distinct evidence levels. - Vendor writes require a declared capability, exact compatibility evidence, host authorization and an operator gate. Manifest metadata and profiles alone grant none of these. - The visualization engine can be replaced without changing vendor transports or codecs. - Real captures, credentials, device identities, maps and router metadata remain outside Git. ## Deferred, not implemented - isolated/signed plugin processes and crash containment; - durable operation journal, restart recovery, vault and RBAC; - persistent device identity and concurrent multi-device routing; - complete SDK-envelope/EvidenceStore hot-path integration; - remote Edge split, authenticated WAN relay and fleet orchestration; - automatic K1 start/stop/calibration commands; - camera discovery, decoding, synchronization and visualization. ## Workspace-repeatable locked architecture gate From the repository root: ```bash uv sync --frozen --group dev uv run pytest \ tests/test_plugin_sdk_v0alpha2_contracts.py \ tests/test_plugin_catalog.py \ tests/test_xgrids_compatibility_profile.py \ tests/test_device_lifecycle.py \ tests/test_xgrids_acquisition_lifecycle.py \ tests/test_canonical_pipeline.py \ tests/test_rerun_bridge.py \ tests/test_web_validation_security.py uv run ruff check . uv run mypy uv run mypy --strict packages/plugin-sdk/python/missioncore_plugin_sdk uv run python plugins/xgrids-k1/profile_loader.py uv run python -m missioncore_plugin_sdk.v0alpha2 \ > /tmp/missioncore-plugin-sdk-v0alpha2.schemas.json cd apps/control-station npm ci npm run test:unit npm run typecheck npm run build ``` These checks perform no BLE scan, network capture, router mutation or K1 application write. The next physical and communication gates are specified in ADR 0004. This gate is repeatable in the current workspace, not standalone reproducible. The frontend consumes mutable sibling `file:` dependencies from `NODEDC_DESIGN_GUIDELINE`; its lockfile does not pin the donor checkout's Git revision or content hash. CI and portable packaging remain blocked until those packages are published or vendored, or an immutable donor revision and content verification are enforced. The current root Python wheel also omits the plugin manifests/profile loader and built frontend, so it is not a deployment bundle.