12 KiB
Template / Scene Binding Refactor Design
Goal
Refactor the configuration model across the admin backend and the OrangePi media service so that:
识别模板only defines a single-stream processing flow and its default technical parameters.基础配置owns reusable concrete instances such as视频源and第三方服务.场景配置becomes the single assembly layer that binds template slots to concrete instances and scene-level output parameters.- The agent runtime config format stays stable in the first phase; the main change is in the modeling and render pipeline.
This is a cross-repo refactor involving:
C:/Users/Tellme/apps/3588AdminBackendC:/Users/Tellme/apps/OrangePi3588Media
Problem Statement
The current template JSON mixes three different concerns:
- Flow definition
- Scene instance parameters
- Concrete third-party service endpoints and credentials
That creates several problems:
- Templates are not reusable enough because they carry site-specific and service-specific values.
- Service endpoints and credentials are duplicated in templates instead of being centrally managed.
- Scene configuration is not the true assembly layer even though it is the closest object to actual deployment.
- The same conceptual binding is split between template params, profile params, and runtime substitution.
The target model should separate these concerns cleanly.
Target Information Architecture
1. 识别模板
Template is a reusable processing definition for one video stream.
Template owns:
- Node graph
- Edge graph
- Default algorithm parameters
- Default preprocess and publish technical parameters
- Declarations of required input / output / service slots
Template does not own:
- Concrete video source URLs
- Concrete third-party service instances
- Scene-specific publish paths or ports
- Site-specific display labels
2. 基础配置
Base config owns reusable concrete instances.
Initial scope:
视频源第三方服务
These objects are real instances that can be shared by many scenes.
3. 场景配置
Scene config is the only assembly layer.
It owns:
- Template selection
- Binding of template input slots to video-source instances
- Binding of template service slots to third-party service instances
- Binding of template output slots to scene-specific publish settings
- Scene-level labels and business parameters
Data Model Boundaries
Template-owned fields
These remain inside template definitions:
- Node types
- Edges
- Model paths
- Thresholds
- Inference rates
- Preprocess defaults
- Publish codec defaults
- Alarm rule structure
- Default sink behavior
Examples from existing templates:
infer_fpsconf_threshnms_threshdst_wdst_hcodecbitrate_kbpsrulesface_rules
Scene-owned fields
These move to scene config:
publish_hls_pathpublish_rtsp_portpublish_rtsp_pathchannel_nodisplay_namesite_name- any scene-specific output behavior or business label
device_code should be treated as legacy and kept only for compatibility during migration. It should not be expanded further as a primary scene-model concept.
Base-config-owned fields
These move into reusable instance objects:
视频源
- input URL
- source type
- resolution metadata
- frame size
- fps
- format
- installation metadata
第三方服务
- object storage endpoint / bucket / keys
- token service URL
- alarm service URL
- tenant or service-side connection metadata
Slot-Based Template Model
The core change is to stop treating template placeholders as generic flat vars and instead treat them as declared slots.
Template slot categories
Templates may declare:
inputslotsserviceslotsoutputslots
Examples:
video_input_mainobject_storage_maintoken_service_mainalarm_service_mainstream_output_main
Meaning of slots
A slot expresses a requirement, not an instance.
Examples:
video_input_mainmeans this template requires one concrete video input.object_storage_mainmeans this template requires one object storage service instance.stream_output_mainmeans this template produces a stream and needs scene-level output binding.
Scene Binding Model
Scene config binds template slots to concrete values.
Input binding
Example:
{
"input_bindings": {
"video_input_main": {
"video_source_ref": "gate_cam_01"
}
}
}
Service binding
Example:
{
"service_bindings": {
"object_storage_main": {
"service_ref": "minio_prod_main"
},
"token_service_main": {
"service_ref": "token_service_prod"
},
"alarm_service_main": {
"service_ref": "alarm_center_prod"
}
}
}
Output binding
Example:
{
"output_bindings": {
"stream_output_main": {
"publish_hls_path": "./web/hls/cam1/index.m3u8",
"publish_rtsp_port": 8555,
"publish_rtsp_path": "/live/cam1"
}
}
}
Scene metadata
Scene keeps business-facing labels:
display_namesite_namechannel_no
These are scene-level values and should not live in templates.
Backward Compatibility Strategy
Phase 1 must preserve the existing agent runtime config format.
That means:
render_config.pymay continue producing the current final flat config shape.- Agent runtime does not need to understand slots yet.
- Binding logic is introduced in the config-render pipeline, not in the agent runtime.
Compatibility rules:
- If new slot bindings exist, they take priority.
- If old flat fields still exist, they remain supported during migration.
- Existing templates and scene configs must continue rendering during the transition.
Existing Field Migration Matrix
Input-related
rtsp_url- Current location: scene/profile params
- Target location: video source instance referenced from scene input binding
- Compatibility: continue supporting direct inline
rtsp_url
Output-related
publish_hls_path- Current location: scene/profile params
- Target location: scene output binding
publish_rtsp_port- Current location: scene/profile params
- Target location: scene output binding
publish_rtsp_path- Current location: scene/profile params
- Target location: scene output binding
Scene label fields
channel_no- Current location: scene/profile params and used by alarm external API
- Target location: scene metadata or output binding context
display_name- Current location: scene/profile params
- Target location: scene metadata
site_name- Current location: scene/profile params
- Target location: scene metadata
device_code- Current location: scene/profile params
- Target location: legacy compatibility only in phase 1
Third-party service fields
minio_endpoint- Current location: template params
- Target location: object storage service instance
minio_bucket- Current location: template params
- Target location: object storage service instance
minio_access_key- Current location: template params
- Target location: object storage service instance
minio_secret_key- Current location: template params
- Target location: object storage service instance
external_get_token_url- Current location: template params
- Target location: token service instance
external_put_message_url- Current location: template params
- Target location: alarm service instance
tenant_code- Current location: template params
- Target location: token/alarm service instance, with optional scene-level override if needed later
Cross-Repo Responsibilities
3588AdminBackend
Admin backend changes:
- Extend template asset model to expose slot declarations.
- Extend scene config model to store slot bindings.
- Maintain
视频源and第三方服务as reusable base config objects. - Update scene-config UI so users bind template slots to concrete instances.
- Update preview pipeline inputs to pass structured bindings to the renderer.
OrangePi3588Media
Media service changes:
- Upgrade template JSON model to support explicit slot declarations.
- Update
render_config.pyto resolve slot bindings into the current runtime config format. - Keep final generated runtime config compatible with the current agent in phase 1.
- Support fallback rendering for older templates and profiles during migration.
Rendering Strategy
Rendering should become a two-stage process.
Stage 1: Resolve scene bindings
Resolve:
- video source refs
- third-party service refs
- scene output parameters
into a structured bound scene model.
Stage 2: Expand into final runtime config
Expand the bound scene model into the current flat runtime config fields expected by the agent.
Examples:
- resolved video source URL becomes runtime
rtsp_url - resolved object storage instance becomes runtime
minio_* - resolved alarm/token services become runtime
external_*andtenant_code
This lets us modernize the model without forcing an immediate runtime-schema rewrite.
UI Implications
Template page
Template page should gradually shift from editing concrete values to editing:
- graph structure
- default technical parameters
- declared slots
It should no longer encourage editing concrete service endpoints or stream addresses inside templates.
Scene page
Scene page becomes the main assembly workspace.
It should expose:
- input bindings
- service bindings
- output bindings
- scene labels and business fields
Base-config pages
These remain the concrete instance maintenance surfaces:
- video source list/detail
- third-party service list/detail
Phased Rollout
Phase 1
- Keep current runtime config shape.
- Add slot-aware scene bindings.
- Add renderer logic that expands new bindings into old flat values.
- Preserve legacy flat template/profile fields.
Phase 2
- Move standard templates to explicit slot declarations.
- Stop storing real service endpoints in new template definitions.
- Prefer video-source refs over inline stream URLs.
Phase 3
- Remove or deprecate legacy flat substitutions from template authoring.
- Reduce compatibility code once all standard and active custom configs are migrated.
Risks
1. Dual-model complexity during migration
Supporting both legacy flat fields and new bindings will increase renderer complexity temporarily.
Mitigation:
- Keep priority order explicit.
- Add fixture-based render tests for old and new models.
2. Template authoring confusion
Users may still expect templates to own instance values.
Mitigation:
- Shift template UI away from concrete service editing.
- Make scene config the clear assembly surface.
3. Cross-repo drift
If backend and media-repo schema changes are not kept aligned, preview and apply flows will break.
Mitigation:
- Treat slot/binding schema as a shared contract.
- Land cross-repo fixture tests around the render boundary.
Testing Strategy
Admin backend
- Unit tests for slot-aware scene models
- Unit tests for binding persistence
- UI tests for scene binding forms
- Preview tests for structured binding expansion
Media repo
- Fixture tests for template slot declarations
- Fixture tests for legacy-template rendering
- Fixture tests for new scene-binding rendering
- Golden tests for final runtime config output
Recommendation
Use the ideal layered model now, but keep runtime compatibility in phase 1:
- Template defines requirements and defaults.
- Base config provides reusable concrete instances.
- Scene config performs all actual binding.
- Render pipeline expands the new structure into the current agent runtime config.
This delivers the clean architecture we want without forcing a dangerous all-at-once runtime rewrite.