toposync-ext-streaming 0.7.10__tar.gz → 0.8.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/.gitignore +1 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/PKG-INFO +1 -1
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/pyproject.toml +1 -1
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/api/routes.py +101 -5
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/pipelines/operators.py +35 -7
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/wizard/pipeline_builder.py +10 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/LICENSE +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/LICENSE.ffmpeg +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/LICENSE.mediamtx +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/README.md +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/__init__.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/api/__init__.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/api/models.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/bin/ffmpeg/LICENSE +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/bin/mediamtx/LICENSE +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/extension.json +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/pipelines/__init__.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/plugin.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/326.js +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/326.js.LICENSE.txt +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/387.js +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/4.js +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/4.js.LICENSE.txt +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/623.js +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/623.js.LICENSE.txt +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/703.js +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/703.js.LICENSE.txt +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/main.js +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/main.js.LICENSE.txt +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/static/remoteEntry.js +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/__init__.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/arbitration.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/camera_ingest.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/distributed_sync.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/encoder_state.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/engine_manager.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/ffmpeg_binary.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/go2rtc_binary.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/go2rtc_config.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/go2rtc_manager.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/ingest_auth.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/ingest_resolver.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/jsmpeg_manager.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/mediamtx_api_client.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/mediamtx_binary.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/mediamtx_config.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/mediamtx_processes.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/placeholder.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/platform.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/playback_events.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/publisher_manager.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/resize.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/runtime_state.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/streaming/writer_bridge.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/wizard/__init__.py +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/package.json +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/activate.tsx +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/api/streamingApi.ts +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/constants.ts +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/entry.ts +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/settings/StreamingSettingsPanel.tsx +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/settings/SubModal.tsx +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/settings/WizardCreatePipelineFromTransmission.tsx +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/translations.ts +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/src/types.ts +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/tsconfig.json +0 -0
- {toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/ui/webpack.config.js +0 -0
|
@@ -5903,6 +5903,7 @@ async def _sync_pipeline_output_publication_nodes(
|
|
|
5903
5903
|
graph = pipeline.graph if isinstance(pipeline.graph, dict) else {}
|
|
5904
5904
|
nodes = graph.get("nodes") if isinstance(graph.get("nodes"), list) else []
|
|
5905
5905
|
changed = False
|
|
5906
|
+
publication_targets: dict[str, tuple[str, str, str]] = {}
|
|
5906
5907
|
for node in nodes:
|
|
5907
5908
|
if not isinstance(node, dict):
|
|
5908
5909
|
continue
|
|
@@ -5914,11 +5915,25 @@ async def _sync_pipeline_output_publication_nodes(
|
|
|
5914
5915
|
continue
|
|
5915
5916
|
cfg = node.get("config") if isinstance(node.get("config"), dict) else {}
|
|
5916
5917
|
expected_transmission_id = _publication_transmission_id(publication)
|
|
5917
|
-
|
|
5918
|
-
|
|
5919
|
-
|
|
5920
|
-
|
|
5921
|
-
|
|
5918
|
+
expected_output_id = f"hls_{_publication_quality_profile(publication)}"
|
|
5919
|
+
expected_quality_profile_id = _publication_quality_profile(publication)
|
|
5920
|
+
publication_targets[node_id] = (
|
|
5921
|
+
expected_transmission_id,
|
|
5922
|
+
expected_output_id,
|
|
5923
|
+
expected_quality_profile_id,
|
|
5924
|
+
)
|
|
5925
|
+
if str(cfg.get("transmission_id") or "").strip() != expected_transmission_id:
|
|
5926
|
+
next_cfg = {**cfg, "transmission_id": expected_transmission_id}
|
|
5927
|
+
node["config"] = next_cfg
|
|
5928
|
+
changed = True
|
|
5929
|
+
if publication_targets:
|
|
5930
|
+
updated_gate_ids = _sync_demand_gates_for_publication_targets(
|
|
5931
|
+
graph=graph,
|
|
5932
|
+
nodes=nodes,
|
|
5933
|
+
publication_targets=publication_targets,
|
|
5934
|
+
)
|
|
5935
|
+
if updated_gate_ids:
|
|
5936
|
+
changed = True
|
|
5922
5937
|
if not changed:
|
|
5923
5938
|
continue
|
|
5924
5939
|
updated = pipeline.model_copy(update={"graph": graph})
|
|
@@ -5937,6 +5952,87 @@ async def _sync_pipeline_output_publication_nodes(
|
|
|
5937
5952
|
return changed_pipelines
|
|
5938
5953
|
|
|
5939
5954
|
|
|
5955
|
+
def _sync_demand_gates_for_publication_targets(
|
|
5956
|
+
*,
|
|
5957
|
+
graph: dict[str, Any],
|
|
5958
|
+
nodes: list[Any],
|
|
5959
|
+
publication_targets: dict[str, tuple[str, str, str]],
|
|
5960
|
+
) -> list[str]:
|
|
5961
|
+
if not publication_targets:
|
|
5962
|
+
return []
|
|
5963
|
+
edges = graph.get("edges") if isinstance(graph.get("edges"), list) else []
|
|
5964
|
+
downstream_by_node: dict[str, set[str]] = {}
|
|
5965
|
+
for edge in edges:
|
|
5966
|
+
if not isinstance(edge, dict):
|
|
5967
|
+
continue
|
|
5968
|
+
source = edge.get("from")
|
|
5969
|
+
target = edge.get("to")
|
|
5970
|
+
if not isinstance(source, dict) or not isinstance(target, dict):
|
|
5971
|
+
continue
|
|
5972
|
+
source_node = str(source.get("node") or "").strip()
|
|
5973
|
+
target_node = str(target.get("node") or "").strip()
|
|
5974
|
+
if not source_node or not target_node:
|
|
5975
|
+
continue
|
|
5976
|
+
downstream_by_node.setdefault(source_node, set()).add(target_node)
|
|
5977
|
+
|
|
5978
|
+
changed_gate_ids: list[str] = []
|
|
5979
|
+
for node in nodes:
|
|
5980
|
+
if not isinstance(node, dict):
|
|
5981
|
+
continue
|
|
5982
|
+
if str(node.get("operator") or "").strip() != "stream.demand_gate":
|
|
5983
|
+
continue
|
|
5984
|
+
gate_id = str(node.get("id") or "").strip()
|
|
5985
|
+
if not gate_id:
|
|
5986
|
+
continue
|
|
5987
|
+
reachable_publications = [
|
|
5988
|
+
publish_node_id
|
|
5989
|
+
for publish_node_id in publication_targets
|
|
5990
|
+
if _graph_node_reaches(gate_id, publish_node_id, downstream_by_node)
|
|
5991
|
+
]
|
|
5992
|
+
if len(reachable_publications) != 1:
|
|
5993
|
+
continue
|
|
5994
|
+
transmission_id, output_id, quality_profile_id = publication_targets[reachable_publications[0]]
|
|
5995
|
+
cfg = node.get("config") if isinstance(node.get("config"), dict) else {}
|
|
5996
|
+
demand_scope = str(cfg.get("demand_scope") or "").strip().lower()
|
|
5997
|
+
use_specific_output = demand_scope == "output"
|
|
5998
|
+
next_cfg = {**cfg, "transmission_id": transmission_id}
|
|
5999
|
+
if use_specific_output:
|
|
6000
|
+
next_cfg["demand_scope"] = "output"
|
|
6001
|
+
next_cfg["output_id"] = str(cfg.get("output_id") or "").strip() or output_id
|
|
6002
|
+
next_cfg["quality_profile_id"] = str(cfg.get("quality_profile_id") or "").strip() or quality_profile_id
|
|
6003
|
+
else:
|
|
6004
|
+
next_cfg["demand_scope"] = "transmission"
|
|
6005
|
+
next_cfg["output_id"] = ""
|
|
6006
|
+
next_cfg["quality_profile_id"] = ""
|
|
6007
|
+
if next_cfg == cfg:
|
|
6008
|
+
continue
|
|
6009
|
+
node["config"] = next_cfg
|
|
6010
|
+
changed_gate_ids.append(gate_id)
|
|
6011
|
+
return changed_gate_ids
|
|
6012
|
+
|
|
6013
|
+
|
|
6014
|
+
def _graph_node_reaches(
|
|
6015
|
+
source_node_id: str,
|
|
6016
|
+
target_node_id: str,
|
|
6017
|
+
downstream_by_node: dict[str, set[str]],
|
|
6018
|
+
) -> bool:
|
|
6019
|
+
if source_node_id == target_node_id:
|
|
6020
|
+
return True
|
|
6021
|
+
seen: set[str] = set()
|
|
6022
|
+
stack = [source_node_id]
|
|
6023
|
+
while stack:
|
|
6024
|
+
current = stack.pop()
|
|
6025
|
+
if current in seen:
|
|
6026
|
+
continue
|
|
6027
|
+
seen.add(current)
|
|
6028
|
+
for child in downstream_by_node.get(current, set()):
|
|
6029
|
+
if child == target_node_id:
|
|
6030
|
+
return True
|
|
6031
|
+
if child not in seen:
|
|
6032
|
+
stack.append(child)
|
|
6033
|
+
return False
|
|
6034
|
+
|
|
6035
|
+
|
|
5940
6036
|
async def _delete_camera_live_pipelines(
|
|
5941
6037
|
*,
|
|
5942
6038
|
request: Request,
|
|
@@ -8,7 +8,7 @@ import numpy
|
|
|
8
8
|
from pydantic import BaseModel, ConfigDict, Field, field_validator, model_validator
|
|
9
9
|
|
|
10
10
|
from toposync.runtime.pipelines.execution import PipelineRuntimeDependencies, SinkRuntime, SourceOperatorRuntime
|
|
11
|
-
from toposync.runtime.pipelines.images import normalize_artifact_name
|
|
11
|
+
from toposync.runtime.pipelines.images import MAIN_ARTIFACT_NAME, normalize_artifact_name
|
|
12
12
|
from toposync.runtime.pipelines.operator_registry import OperatorDiagnostic, OperatorRegistry
|
|
13
13
|
from toposync.runtime.pipelines.packet_contract import resolve_media_ts
|
|
14
14
|
from toposync.runtime.pipelines.runtime import Lifecycle, Packet
|
|
@@ -85,11 +85,30 @@ class DemandGateConfig(BaseModel):
|
|
|
85
85
|
model_config = ConfigDict(extra="forbid")
|
|
86
86
|
|
|
87
87
|
transmission_id: str = ""
|
|
88
|
+
demand_scope: Literal["transmission", "output"] = "transmission"
|
|
88
89
|
output_id: str = ""
|
|
89
90
|
quality_profile_id: str = ""
|
|
90
91
|
poll_interval_ms: int = Field(default=500, ge=100, le=10_000)
|
|
91
92
|
fail_open: bool = True
|
|
92
93
|
|
|
94
|
+
@model_validator(mode="before")
|
|
95
|
+
@classmethod
|
|
96
|
+
def _normalize_legacy_scope(cls, value: Any) -> Any:
|
|
97
|
+
if not isinstance(value, dict):
|
|
98
|
+
return value
|
|
99
|
+
data = dict(value)
|
|
100
|
+
scope = str(data.get("demand_scope") or "").strip().lower()
|
|
101
|
+
if scope == "auto":
|
|
102
|
+
scope = "transmission"
|
|
103
|
+
if scope not in {"transmission", "output"}:
|
|
104
|
+
has_specific_output = bool(
|
|
105
|
+
str(data.get("output_id") or "").strip()
|
|
106
|
+
or str(data.get("quality_profile_id") or "").strip()
|
|
107
|
+
)
|
|
108
|
+
scope = "output" if has_specific_output else "transmission"
|
|
109
|
+
data["demand_scope"] = scope
|
|
110
|
+
return data
|
|
111
|
+
|
|
93
112
|
@field_validator("transmission_id", "output_id", "quality_profile_id", mode="after")
|
|
94
113
|
@classmethod
|
|
95
114
|
def _trim(cls, value: str) -> str:
|
|
@@ -147,10 +166,11 @@ class DemandGateRuntime(SourceOperatorRuntime):
|
|
|
147
166
|
self._last_open = is_open
|
|
148
167
|
self._last_payload = payload
|
|
149
168
|
lifecycle = Lifecycle.OPEN if is_open else Lifecycle.CLOSE
|
|
169
|
+
output_id, quality_profile_id = self._selected_demand_target()
|
|
150
170
|
stream_id = _demand_gate_stream_id(
|
|
151
171
|
self._config.transmission_id,
|
|
152
|
-
output_id=
|
|
153
|
-
quality_profile_id=
|
|
172
|
+
output_id=output_id,
|
|
173
|
+
quality_profile_id=quality_profile_id,
|
|
154
174
|
)
|
|
155
175
|
return Packet.create(
|
|
156
176
|
stream_id=stream_id,
|
|
@@ -158,8 +178,9 @@ class DemandGateRuntime(SourceOperatorRuntime):
|
|
|
158
178
|
payload={
|
|
159
179
|
"gate_open": bool(is_open),
|
|
160
180
|
"transmission_id": self._config.transmission_id,
|
|
161
|
-
"
|
|
162
|
-
"
|
|
181
|
+
"demand_scope": self._config.demand_scope,
|
|
182
|
+
"output_id": output_id,
|
|
183
|
+
"quality_profile_id": quality_profile_id,
|
|
163
184
|
**payload,
|
|
164
185
|
},
|
|
165
186
|
)
|
|
@@ -175,11 +196,12 @@ class DemandGateRuntime(SourceOperatorRuntime):
|
|
|
175
196
|
"reason": "services_unavailable",
|
|
176
197
|
}
|
|
177
198
|
try:
|
|
199
|
+
output_id, quality_profile_id = self._selected_demand_target()
|
|
178
200
|
raw = await services.call(
|
|
179
201
|
"streaming.demand.snapshot",
|
|
180
202
|
transmission_id=self._config.transmission_id,
|
|
181
|
-
output_id=
|
|
182
|
-
quality_profile_id=
|
|
203
|
+
output_id=output_id,
|
|
204
|
+
quality_profile_id=quality_profile_id,
|
|
183
205
|
)
|
|
184
206
|
except Exception as exc: # noqa: BLE001
|
|
185
207
|
return bool(self._config.fail_open), {
|
|
@@ -199,6 +221,11 @@ class DemandGateRuntime(SourceOperatorRuntime):
|
|
|
199
221
|
"matched_outputs": int(snapshot.get("matched_outputs") or 0),
|
|
200
222
|
}
|
|
201
223
|
|
|
224
|
+
def _selected_demand_target(self) -> tuple[str, str]:
|
|
225
|
+
if self._config.demand_scope != "output":
|
|
226
|
+
return "", ""
|
|
227
|
+
return self._config.output_id, self._config.quality_profile_id
|
|
228
|
+
|
|
202
229
|
|
|
203
230
|
def register_streaming_pipeline_operators(registry: OperatorRegistry) -> None:
|
|
204
231
|
if registry.get("stream.demand_gate") is None:
|
|
@@ -227,6 +254,7 @@ def register_streaming_pipeline_operators(registry: OperatorRegistry) -> None:
|
|
|
227
254
|
capabilities=["streaming", "sink", "realtime"],
|
|
228
255
|
defaults=PublishVideoConfig(publication_enabled=True).model_dump(mode="json"),
|
|
229
256
|
share_strategy="never",
|
|
257
|
+
requires_artifacts=[MAIN_ARTIFACT_NAME],
|
|
230
258
|
requires_media_fields=["ts", "width", "height"],
|
|
231
259
|
input_modalities=["video"],
|
|
232
260
|
owner=EXTENSION_ID,
|
|
@@ -91,6 +91,15 @@ def build_streaming_wizard_graph(
|
|
|
91
91
|
demand_gate_fail_open = _coerce_bool(options.get("demand_gate_fail_open"), default=True)
|
|
92
92
|
demand_gate_output_id = _safe_text(options.get("demand_gate_output_id"))
|
|
93
93
|
demand_gate_quality_profile_id = _safe_text(options.get("demand_gate_quality_profile_id"))
|
|
94
|
+
demand_gate_scope_default = "output" if demand_gate_output_id or demand_gate_quality_profile_id else "transmission"
|
|
95
|
+
demand_gate_scope = _pick_choice(
|
|
96
|
+
options.get("demand_gate_scope"),
|
|
97
|
+
allowed={"transmission", "output"},
|
|
98
|
+
default=demand_gate_scope_default,
|
|
99
|
+
)
|
|
100
|
+
if demand_gate_scope != "output":
|
|
101
|
+
demand_gate_output_id = ""
|
|
102
|
+
demand_gate_quality_profile_id = ""
|
|
94
103
|
demand_gate_poll_interval_ms = _coerce_int(
|
|
95
104
|
options.get("demand_gate_poll_interval_ms"),
|
|
96
105
|
default=500,
|
|
@@ -144,6 +153,7 @@ def build_streaming_wizard_graph(
|
|
|
144
153
|
"operator": "stream.demand_gate",
|
|
145
154
|
"config": {
|
|
146
155
|
"transmission_id": transmission_id,
|
|
156
|
+
"demand_scope": demand_gate_scope,
|
|
147
157
|
"output_id": demand_gate_output_id,
|
|
148
158
|
"quality_profile_id": demand_gate_quality_profile_id,
|
|
149
159
|
"poll_interval_ms": int(demand_gate_poll_interval_ms),
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{toposync_ext_streaming-0.7.10 → toposync_ext_streaming-0.8.0}/src/toposync_ext_streaming/plugin.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|