feat(plugins): isolate device integrations

This commit is contained in:
DCCONSTRUCTIONS
2026-07-17 19:29:32 +03:00
parent f9ffb7bd1c
commit 24a47318f2
122 changed files with 3304 additions and 1892 deletions
+12 -3
View File
@@ -36,6 +36,8 @@ The separate SDK v0alpha2 package establishes executable contracts for:
- independently revisioned enrollment, connectivity, and acquisition states;
- operation policy, request, acknowledgement, progress, completion, failure,
timeout, cancellation, secret reference, and idempotency boundaries;
- immutable pre-session runtime-action invocation and result envelopes used by
the active backend dispatcher;
- canonical point cloud, pose, image, encoded video, and device-status streams;
- immutable evidence handles, raw transport records, lineage, and store
protocol;
@@ -49,11 +51,13 @@ compatibility profile and adapter.
Current host implementation references:
- `apps/control-station/src/core/device-plugins/` — TypeScript manifest and UI
contribution contracts;
- `apps/control-station/src/core/device-plugins/frontendSdk.ts` — current
public TypeScript/React host surface for statically reviewed UI contributions;
- `plugins/xgrids-k1/frontend/` — first physically plugin-owned consumer of
that frontend surface;
- `apps/control-station/src/core/runtime/` — normalized runtime envelope;
- `src/k1link/web/plugin_catalog.py` — strict backend manifest validation;
- `src/k1link/web/plugin_runtime.py` — host-owned allowlisted action dispatcher;
- `src/k1link/web/plugin_runtime.py` — host-owned allowlisted SDK-envelope action dispatcher;
- `src/k1link/web/device_plugin_composition.py` — manifest factory loader and
startup parity checks;
- `docs/adr/0003-device-plugin-ui-and-runtime-boundary.md` — accepted boundary
@@ -66,6 +70,11 @@ milestone. v0alpha2 models secret references and operation policy, but host
authorization and the actual secret vault remain separate implementation
responsibilities.
The React surface is not yet an independently published npm package. Its alias
is intentionally narrow so plugin source cannot import Control Station
implementation paths; packaging and signing it belong to the supervisor/bundle
milestone.
## Version policy
v0alpha2 may receive additive fields while it remains experimental. A breaking
@@ -47,6 +47,7 @@ from .operations import (
validate_operation_request,
)
from .payloads import InlinePayload, PayloadHandle, ReferencedPayload
from .runtime import RuntimeActionInvocation, RuntimeActionResult
from .schema import contract_json_schemas
from .session import (
AcquisitionState,
@@ -120,6 +121,8 @@ __all__ = [
"Quaternion",
"RawTransportRecord",
"RedactionState",
"RuntimeActionInvocation",
"RuntimeActionResult",
"ReferencedPayload",
"RuleOutcome",
"SecretReference",
@@ -0,0 +1,33 @@
"""Minimal pre-session action envelopes for the executable plugin runtime."""
from __future__ import annotations
from typing import Literal
from pydantic import AwareDatetime, Field
from .common import API_VERSION, ApiVersion, ContractModel, Identifier, JsonObject
class RuntimeActionInvocation(ContractModel):
"""Host-admitted invocation delivered to exactly one installed plugin."""
api_version: ApiVersion = API_VERSION
kind: Literal["RuntimeActionInvocation"] = "RuntimeActionInvocation"
invocation_id: Identifier
plugin_id: Identifier
action_id: Identifier
requested_at: AwareDatetime
parameters: JsonObject = Field(default_factory=dict)
class RuntimeActionResult(ContractModel):
"""Host-validated completion envelope for one runtime invocation."""
api_version: ApiVersion = API_VERSION
kind: Literal["RuntimeActionResult"] = "RuntimeActionResult"
invocation_id: Identifier
plugin_id: Identifier
action_id: Identifier
completed_at: AwareDatetime
output: JsonObject = Field(default_factory=dict)
@@ -8,6 +8,7 @@ from .compatibility import CompatibilityAssessment
from .evidence import EvidenceRecord, RawTransportRecord
from .identity import DeviceInstanceRef
from .operations import OperationEvent, OperationPolicy, OperationRequest
from .runtime import RuntimeActionInvocation, RuntimeActionResult
from .session import DeviceSessionContext, DeviceSessionSnapshot
from .streams import CanonicalStreamEnvelope
@@ -22,6 +23,8 @@ def contract_json_schemas() -> dict[str, dict[str, object]]:
"OperationPolicy": OperationPolicy,
"OperationRequest": OperationRequest,
"OperationEvent": OperationEvent,
"RuntimeActionInvocation": RuntimeActionInvocation,
"RuntimeActionResult": RuntimeActionResult,
"CanonicalStreamEnvelope": CanonicalStreamEnvelope,
"EvidenceRecord": EvidenceRecord,
"RawTransportRecord": RawTransportRecord,