dominus-sdk-python 6.1.0__tar.gz → 6.1.1__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.
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/PKG-INFO +18 -2
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/README.md +17 -1
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/__init__.py +1 -1
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/coder.py +56 -5
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/platform.py +27 -2
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus_sdk_python.egg-info/PKG-INFO +18 -2
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/pyproject.toml +1 -1
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_platform_coder_namespaces.py +25 -1
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/config/__init__.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/config/endpoints.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/errors.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/helpers/__init__.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/helpers/auth.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/helpers/cache.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/helpers/console_capture.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/helpers/core.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/helpers/crypto.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/helpers/sse.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/helpers/trace.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/__init__.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/admin.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/ai.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/artifacts.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/auth.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/authority.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/browser.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/courier.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/db.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/ddl.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/deployer.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/fastapi.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/files.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/health.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/jobs.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/logs.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/portal.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/processor.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/recipes.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/redis.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/secrets.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/secure.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/stash.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/sync.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/warden.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/namespaces/workflow.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/services/__init__.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus/start.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus_sdk_python.egg-info/SOURCES.txt +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus_sdk_python.egg-info/dependency_links.txt +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus_sdk_python.egg-info/requires.txt +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus_sdk_python.egg-info/top_level.txt +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/setup.cfg +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_auth.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_authority_public_vocabulary.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_browser_namespace.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_control_plane_namespaces.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_errors.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_flat_commands.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_health.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_logs.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_provisioning_parity.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_public_exports.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_recipes_namespace.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_transport_compat.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_workflow_lifecycle.py +0 -0
- {dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_workflow_refs.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: dominus-sdk-python
|
|
3
|
-
Version: 6.1.
|
|
3
|
+
Version: 6.1.1
|
|
4
4
|
Summary: Python SDK for the Dominus gateway-first platform
|
|
5
5
|
Author-email: CareBridge Systems <dev@carebridge.io>
|
|
6
6
|
License-Expression: LicenseRef-Proprietary
|
|
@@ -42,7 +42,7 @@ Async Python SDK for the Dominus gateway-first service plane.
|
|
|
42
42
|
- Gateway-scoped client mode for MCP and other user-JWT sessions
|
|
43
43
|
- Transport compatibility for wrapped `{success,data}` responses and unwrapped Warden/control-plane success objects
|
|
44
44
|
- Local helpers for JWT verification, trace propagation, retries, and console capture
|
|
45
|
-
- Current package version: `6.
|
|
45
|
+
- Current package version: `6.1.1`
|
|
46
46
|
|
|
47
47
|
## Install
|
|
48
48
|
|
|
@@ -94,6 +94,20 @@ machine_logs = await dominus.logs.tail(
|
|
|
94
94
|
since="2026-04-11T08:33:00Z",
|
|
95
95
|
level="error",
|
|
96
96
|
)
|
|
97
|
+
policy = await dominus.platform.ensure_policy_decision(
|
|
98
|
+
{
|
|
99
|
+
"group": "dominus",
|
|
100
|
+
"repository": "carebridgesystems/dominus-platform-worker",
|
|
101
|
+
},
|
|
102
|
+
actor_context={"type": "user", "id": "operator-1"},
|
|
103
|
+
)
|
|
104
|
+
coder_run = await dominus.coder.ensure_run(
|
|
105
|
+
policy_decision_id=policy["data"]["policy_decision"]["decision_id"],
|
|
106
|
+
workflow_recipe_ref="recipe://workflow-recipe-v1/coder-feature@head",
|
|
107
|
+
repository="carebridgesystems/dominus-platform-worker",
|
|
108
|
+
instructions="Fix failing tests",
|
|
109
|
+
actor_context={"type": "user", "id": "operator-1"},
|
|
110
|
+
)
|
|
97
111
|
|
|
98
112
|
# Archive maintenance is explicit and dry-run first.
|
|
99
113
|
verify = await dominus.authority.verify_timeline_archive_manifests(
|
|
@@ -206,6 +220,8 @@ JWT and selected scope headers directly through Gateway.
|
|
|
206
220
|
| `browser` | Browser Worker | Browser run health, ensure/start/status/result/retry/nudge/cancel/timeline/dossier |
|
|
207
221
|
| `deployer` | Deployer | Thin operator control-plane request surface |
|
|
208
222
|
| `warden` | Warden | Thin operator control-plane request surface |
|
|
223
|
+
| `platform` | Platform Worker | Group/repository policy decisions with actor attribution |
|
|
224
|
+
| `coder` | Coder Runtime | Policy-bound Coder run lifecycle with workflow/pipeline recipe launch sources |
|
|
209
225
|
| `fastapi` | Local decorators | `@jwt`, `@psk`, `@scopes(...)` |
|
|
210
226
|
|
|
211
227
|
## Root Shortcuts
|
|
@@ -9,7 +9,7 @@ Async Python SDK for the Dominus gateway-first service plane.
|
|
|
9
9
|
- Gateway-scoped client mode for MCP and other user-JWT sessions
|
|
10
10
|
- Transport compatibility for wrapped `{success,data}` responses and unwrapped Warden/control-plane success objects
|
|
11
11
|
- Local helpers for JWT verification, trace propagation, retries, and console capture
|
|
12
|
-
- Current package version: `6.
|
|
12
|
+
- Current package version: `6.1.1`
|
|
13
13
|
|
|
14
14
|
## Install
|
|
15
15
|
|
|
@@ -61,6 +61,20 @@ machine_logs = await dominus.logs.tail(
|
|
|
61
61
|
since="2026-04-11T08:33:00Z",
|
|
62
62
|
level="error",
|
|
63
63
|
)
|
|
64
|
+
policy = await dominus.platform.ensure_policy_decision(
|
|
65
|
+
{
|
|
66
|
+
"group": "dominus",
|
|
67
|
+
"repository": "carebridgesystems/dominus-platform-worker",
|
|
68
|
+
},
|
|
69
|
+
actor_context={"type": "user", "id": "operator-1"},
|
|
70
|
+
)
|
|
71
|
+
coder_run = await dominus.coder.ensure_run(
|
|
72
|
+
policy_decision_id=policy["data"]["policy_decision"]["decision_id"],
|
|
73
|
+
workflow_recipe_ref="recipe://workflow-recipe-v1/coder-feature@head",
|
|
74
|
+
repository="carebridgesystems/dominus-platform-worker",
|
|
75
|
+
instructions="Fix failing tests",
|
|
76
|
+
actor_context={"type": "user", "id": "operator-1"},
|
|
77
|
+
)
|
|
64
78
|
|
|
65
79
|
# Archive maintenance is explicit and dry-run first.
|
|
66
80
|
verify = await dominus.authority.verify_timeline_archive_manifests(
|
|
@@ -173,6 +187,8 @@ JWT and selected scope headers directly through Gateway.
|
|
|
173
187
|
| `browser` | Browser Worker | Browser run health, ensure/start/status/result/retry/nudge/cancel/timeline/dossier |
|
|
174
188
|
| `deployer` | Deployer | Thin operator control-plane request surface |
|
|
175
189
|
| `warden` | Warden | Thin operator control-plane request surface |
|
|
190
|
+
| `platform` | Platform Worker | Group/repository policy decisions with actor attribution |
|
|
191
|
+
| `coder` | Coder Runtime | Policy-bound Coder run lifecycle with workflow/pipeline recipe launch sources |
|
|
176
192
|
| `fastapi` | Local decorators | `@jwt`, `@psk`, `@scopes(...)` |
|
|
177
193
|
|
|
178
194
|
## Root Shortcuts
|
|
@@ -54,6 +54,26 @@ def _mutation_body(
|
|
|
54
54
|
)
|
|
55
55
|
|
|
56
56
|
|
|
57
|
+
def _actor_headers(actor_context: Optional[Dict[str, str]]) -> Optional[Dict[str, str]]:
|
|
58
|
+
if not actor_context:
|
|
59
|
+
return None
|
|
60
|
+
actor_type = str(actor_context.get("type") or actor_context.get("actor_type") or "").strip()
|
|
61
|
+
actor_id = str(actor_context.get("id") or actor_context.get("actor_id") or "").strip()
|
|
62
|
+
if not actor_type or not actor_id:
|
|
63
|
+
return None
|
|
64
|
+
return {"X-Actor-Type": actor_type, "X-Actor-Id": actor_id}
|
|
65
|
+
|
|
66
|
+
|
|
67
|
+
def _assert_one_launch_source(workflow_recipe_ref: Optional[str], pipeline_recipe_ref: Optional[str]) -> None:
|
|
68
|
+
present = [
|
|
69
|
+
ref
|
|
70
|
+
for ref in (workflow_recipe_ref, pipeline_recipe_ref)
|
|
71
|
+
if isinstance(ref, str) and ref.strip()
|
|
72
|
+
]
|
|
73
|
+
if len(present) != 1:
|
|
74
|
+
raise ValueError("ensure_run requires exactly one of workflow_recipe_ref or pipeline_recipe_ref")
|
|
75
|
+
|
|
76
|
+
|
|
57
77
|
class CoderNamespace:
|
|
58
78
|
"""Coder run lifecycle helpers."""
|
|
59
79
|
|
|
@@ -101,9 +121,11 @@ class CoderNamespace:
|
|
|
101
121
|
instructions: Optional[str] = None,
|
|
102
122
|
inputs: Optional[Dict[str, Any]] = None,
|
|
103
123
|
metadata: Optional[Dict[str, Any]] = None,
|
|
124
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
104
125
|
) -> Dict[str, Any]:
|
|
105
126
|
if not policy_decision_id or policy_decision_id.strip() == "":
|
|
106
127
|
raise ValueError("ensure_run requires policy_decision_id")
|
|
128
|
+
_assert_one_launch_source(workflow_recipe_ref, pipeline_recipe_ref)
|
|
107
129
|
|
|
108
130
|
body = _compact(
|
|
109
131
|
{
|
|
@@ -128,6 +150,7 @@ class CoderNamespace:
|
|
|
128
150
|
"/runs/ensure",
|
|
129
151
|
method="POST",
|
|
130
152
|
body=body,
|
|
153
|
+
headers=_actor_headers(actor_context),
|
|
131
154
|
timeout=600.0,
|
|
132
155
|
)
|
|
133
156
|
|
|
@@ -139,6 +162,7 @@ class CoderNamespace:
|
|
|
139
162
|
repository: Optional[str] = None,
|
|
140
163
|
limit: Optional[int] = None,
|
|
141
164
|
offset: Optional[int] = None,
|
|
165
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
142
166
|
) -> Dict[str, Any]:
|
|
143
167
|
qs = _query_string(
|
|
144
168
|
{
|
|
@@ -149,10 +173,19 @@ class CoderNamespace:
|
|
|
149
173
|
"offset": offset,
|
|
150
174
|
}
|
|
151
175
|
)
|
|
152
|
-
return await self.request(f"/runs{qs}", method="GET")
|
|
176
|
+
return await self.request(f"/runs{qs}", method="GET", headers=_actor_headers(actor_context))
|
|
153
177
|
|
|
154
|
-
async def get_run(
|
|
155
|
-
|
|
178
|
+
async def get_run(
|
|
179
|
+
self,
|
|
180
|
+
run_id: str,
|
|
181
|
+
*,
|
|
182
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
183
|
+
) -> Dict[str, Any]:
|
|
184
|
+
return await self.request(
|
|
185
|
+
f"/runs/{quote(run_id, safe='')}",
|
|
186
|
+
method="GET",
|
|
187
|
+
headers=_actor_headers(actor_context),
|
|
188
|
+
)
|
|
156
189
|
|
|
157
190
|
async def cancel_run(
|
|
158
191
|
self,
|
|
@@ -161,6 +194,7 @@ class CoderNamespace:
|
|
|
161
194
|
reason: Optional[str] = None,
|
|
162
195
|
idempotency_key: Optional[str] = None,
|
|
163
196
|
metadata: Optional[Dict[str, Any]] = None,
|
|
197
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
164
198
|
) -> Dict[str, Any]:
|
|
165
199
|
return await self.request(
|
|
166
200
|
f"/runs/{quote(run_id, safe='')}/cancel",
|
|
@@ -170,6 +204,7 @@ class CoderNamespace:
|
|
|
170
204
|
idempotency_key=idempotency_key,
|
|
171
205
|
metadata=metadata,
|
|
172
206
|
),
|
|
207
|
+
headers=_actor_headers(actor_context),
|
|
173
208
|
)
|
|
174
209
|
|
|
175
210
|
async def retry_run(
|
|
@@ -179,6 +214,7 @@ class CoderNamespace:
|
|
|
179
214
|
reason: Optional[str] = None,
|
|
180
215
|
idempotency_key: Optional[str] = None,
|
|
181
216
|
metadata: Optional[Dict[str, Any]] = None,
|
|
217
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
182
218
|
) -> Dict[str, Any]:
|
|
183
219
|
return await self.request(
|
|
184
220
|
f"/runs/{quote(run_id, safe='')}/retry",
|
|
@@ -188,6 +224,7 @@ class CoderNamespace:
|
|
|
188
224
|
idempotency_key=idempotency_key,
|
|
189
225
|
metadata=metadata,
|
|
190
226
|
),
|
|
227
|
+
headers=_actor_headers(actor_context),
|
|
191
228
|
)
|
|
192
229
|
|
|
193
230
|
async def nudge_run(
|
|
@@ -197,6 +234,7 @@ class CoderNamespace:
|
|
|
197
234
|
reason: Optional[str] = None,
|
|
198
235
|
idempotency_key: Optional[str] = None,
|
|
199
236
|
metadata: Optional[Dict[str, Any]] = None,
|
|
237
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
200
238
|
) -> Dict[str, Any]:
|
|
201
239
|
return await self.request(
|
|
202
240
|
f"/runs/{quote(run_id, safe='')}/nudge",
|
|
@@ -206,16 +244,29 @@ class CoderNamespace:
|
|
|
206
244
|
idempotency_key=idempotency_key,
|
|
207
245
|
metadata=metadata,
|
|
208
246
|
),
|
|
247
|
+
headers=_actor_headers(actor_context),
|
|
209
248
|
)
|
|
210
249
|
|
|
211
|
-
async def get_run_summary(
|
|
250
|
+
async def get_run_summary(
|
|
251
|
+
self,
|
|
252
|
+
run_id: str,
|
|
253
|
+
*,
|
|
254
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
255
|
+
) -> Dict[str, Any]:
|
|
212
256
|
return await self.request(
|
|
213
257
|
f"/runs/{quote(run_id, safe='')}/summary",
|
|
214
258
|
method="GET",
|
|
259
|
+
headers=_actor_headers(actor_context),
|
|
215
260
|
)
|
|
216
261
|
|
|
217
|
-
async def get_run_artifacts(
|
|
262
|
+
async def get_run_artifacts(
|
|
263
|
+
self,
|
|
264
|
+
run_id: str,
|
|
265
|
+
*,
|
|
266
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
267
|
+
) -> Dict[str, Any]:
|
|
218
268
|
return await self.request(
|
|
219
269
|
f"/runs/{quote(run_id, safe='')}/artifacts",
|
|
220
270
|
method="GET",
|
|
271
|
+
headers=_actor_headers(actor_context),
|
|
221
272
|
)
|
|
@@ -23,6 +23,16 @@ def _normalize_platform_path(path: str) -> str:
|
|
|
23
23
|
return f"/svc/platform{normalized}"
|
|
24
24
|
|
|
25
25
|
|
|
26
|
+
def _actor_headers(actor_context: Optional[Dict[str, str]]) -> Optional[Dict[str, str]]:
|
|
27
|
+
if not actor_context:
|
|
28
|
+
return None
|
|
29
|
+
actor_type = str(actor_context.get("type") or actor_context.get("actor_type") or "").strip()
|
|
30
|
+
actor_id = str(actor_context.get("id") or actor_context.get("actor_id") or "").strip()
|
|
31
|
+
if not actor_type or not actor_id:
|
|
32
|
+
return None
|
|
33
|
+
return {"X-Actor-Type": actor_type, "X-Actor-Id": actor_id}
|
|
34
|
+
|
|
35
|
+
|
|
26
36
|
class PlatformNamespace:
|
|
27
37
|
"""Platform group/repository policy helpers."""
|
|
28
38
|
|
|
@@ -105,26 +115,41 @@ class PlatformNamespace:
|
|
|
105
115
|
body=repository,
|
|
106
116
|
)
|
|
107
117
|
|
|
108
|
-
async def ensure_policy_decision(
|
|
118
|
+
async def ensure_policy_decision(
|
|
119
|
+
self,
|
|
120
|
+
options: Dict[str, Any],
|
|
121
|
+
*,
|
|
122
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
123
|
+
) -> Dict[str, Any]:
|
|
109
124
|
return await self.request(
|
|
110
125
|
"/policy/decisions/ensure",
|
|
111
126
|
method="POST",
|
|
112
127
|
body=options,
|
|
128
|
+
headers=_actor_headers(actor_context),
|
|
113
129
|
)
|
|
114
130
|
|
|
115
|
-
async def get_policy_decision(
|
|
131
|
+
async def get_policy_decision(
|
|
132
|
+
self,
|
|
133
|
+
decision_id: str,
|
|
134
|
+
*,
|
|
135
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
136
|
+
) -> Dict[str, Any]:
|
|
116
137
|
return await self.request(
|
|
117
138
|
f"/policy/decisions/{quote(decision_id, safe='')}",
|
|
118
139
|
method="GET",
|
|
140
|
+
headers=_actor_headers(actor_context),
|
|
119
141
|
)
|
|
120
142
|
|
|
121
143
|
async def rehydrate_policy_decision(
|
|
122
144
|
self,
|
|
123
145
|
decision_id: str,
|
|
124
146
|
options: Optional[Dict[str, Any]] = None,
|
|
147
|
+
*,
|
|
148
|
+
actor_context: Optional[Dict[str, str]] = None,
|
|
125
149
|
) -> Dict[str, Any]:
|
|
126
150
|
return await self.request(
|
|
127
151
|
f"/policy/decisions/{quote(decision_id, safe='')}/rehydrate",
|
|
128
152
|
method="POST",
|
|
129
153
|
body=options or {},
|
|
154
|
+
headers=_actor_headers(actor_context),
|
|
130
155
|
)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: dominus-sdk-python
|
|
3
|
-
Version: 6.1.
|
|
3
|
+
Version: 6.1.1
|
|
4
4
|
Summary: Python SDK for the Dominus gateway-first platform
|
|
5
5
|
Author-email: CareBridge Systems <dev@carebridge.io>
|
|
6
6
|
License-Expression: LicenseRef-Proprietary
|
|
@@ -42,7 +42,7 @@ Async Python SDK for the Dominus gateway-first service plane.
|
|
|
42
42
|
- Gateway-scoped client mode for MCP and other user-JWT sessions
|
|
43
43
|
- Transport compatibility for wrapped `{success,data}` responses and unwrapped Warden/control-plane success objects
|
|
44
44
|
- Local helpers for JWT verification, trace propagation, retries, and console capture
|
|
45
|
-
- Current package version: `6.
|
|
45
|
+
- Current package version: `6.1.1`
|
|
46
46
|
|
|
47
47
|
## Install
|
|
48
48
|
|
|
@@ -94,6 +94,20 @@ machine_logs = await dominus.logs.tail(
|
|
|
94
94
|
since="2026-04-11T08:33:00Z",
|
|
95
95
|
level="error",
|
|
96
96
|
)
|
|
97
|
+
policy = await dominus.platform.ensure_policy_decision(
|
|
98
|
+
{
|
|
99
|
+
"group": "dominus",
|
|
100
|
+
"repository": "carebridgesystems/dominus-platform-worker",
|
|
101
|
+
},
|
|
102
|
+
actor_context={"type": "user", "id": "operator-1"},
|
|
103
|
+
)
|
|
104
|
+
coder_run = await dominus.coder.ensure_run(
|
|
105
|
+
policy_decision_id=policy["data"]["policy_decision"]["decision_id"],
|
|
106
|
+
workflow_recipe_ref="recipe://workflow-recipe-v1/coder-feature@head",
|
|
107
|
+
repository="carebridgesystems/dominus-platform-worker",
|
|
108
|
+
instructions="Fix failing tests",
|
|
109
|
+
actor_context={"type": "user", "id": "operator-1"},
|
|
110
|
+
)
|
|
97
111
|
|
|
98
112
|
# Archive maintenance is explicit and dry-run first.
|
|
99
113
|
verify = await dominus.authority.verify_timeline_archive_manifests(
|
|
@@ -206,6 +220,8 @@ JWT and selected scope headers directly through Gateway.
|
|
|
206
220
|
| `browser` | Browser Worker | Browser run health, ensure/start/status/result/retry/nudge/cancel/timeline/dossier |
|
|
207
221
|
| `deployer` | Deployer | Thin operator control-plane request surface |
|
|
208
222
|
| `warden` | Warden | Thin operator control-plane request surface |
|
|
223
|
+
| `platform` | Platform Worker | Group/repository policy decisions with actor attribution |
|
|
224
|
+
| `coder` | Coder Runtime | Policy-bound Coder run lifecycle with workflow/pipeline recipe launch sources |
|
|
209
225
|
| `fastapi` | Local decorators | `@jwt`, `@psk`, `@scopes(...)` |
|
|
210
226
|
|
|
211
227
|
## Root Shortcuts
|
{dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_platform_coder_namespaces.py
RENAMED
|
@@ -31,7 +31,8 @@ async def test_platform_namespace_normalizes_helpers_onto_service_routes():
|
|
|
31
31
|
"group": "dominus",
|
|
32
32
|
"repository": "carebridgesystems/dominus-platform-worker",
|
|
33
33
|
"metadata": {"safe": "ok"},
|
|
34
|
-
}
|
|
34
|
+
},
|
|
35
|
+
actor_context={"type": "user", "id": "user-1"},
|
|
35
36
|
)
|
|
36
37
|
await platform.rehydrate_policy_decision("pd_123", {"run_id": "run_123"})
|
|
37
38
|
|
|
@@ -51,6 +52,7 @@ async def test_platform_namespace_normalizes_helpers_onto_service_routes():
|
|
|
51
52
|
"repository": "carebridgesystems/dominus-platform-worker",
|
|
52
53
|
"metadata": {"safe": "ok"},
|
|
53
54
|
}
|
|
55
|
+
assert client.calls[5][1]["headers"] == {"X-Actor-Type": "user", "X-Actor-Id": "user-1"}
|
|
54
56
|
|
|
55
57
|
|
|
56
58
|
@pytest.mark.asyncio
|
|
@@ -76,8 +78,10 @@ async def test_coder_namespace_exposes_lifecycle_helpers_but_no_raw_shell():
|
|
|
76
78
|
policy_decision_id="pd_123",
|
|
77
79
|
mode="async",
|
|
78
80
|
task_recipe_ref="recipe://coder-task-recipe-v1/fix-tests@head",
|
|
81
|
+
workflow_recipe_ref="recipe://workflow-recipe-v1/coder-feature@head",
|
|
79
82
|
repository="carebridgesystems/dominus-platform-worker",
|
|
80
83
|
instructions="Fix failing tests",
|
|
84
|
+
actor_context={"type": "user", "id": "user-1"},
|
|
81
85
|
)
|
|
82
86
|
await coder.list_runs(status="running", limit=10)
|
|
83
87
|
await coder.cancel_run("run_123", reason="operator requested")
|
|
@@ -99,9 +103,11 @@ async def test_coder_namespace_exposes_lifecycle_helpers_but_no_raw_shell():
|
|
|
99
103
|
"policy_decision_id": "pd_123",
|
|
100
104
|
"mode": "async",
|
|
101
105
|
"task_recipe_ref": "recipe://coder-task-recipe-v1/fix-tests@head",
|
|
106
|
+
"workflow_recipe_ref": "recipe://workflow-recipe-v1/coder-feature@head",
|
|
102
107
|
"repository": "carebridgesystems/dominus-platform-worker",
|
|
103
108
|
"instructions": "Fix failing tests",
|
|
104
109
|
}
|
|
110
|
+
assert client.calls[0][1]["headers"] == {"X-Actor-Type": "user", "X-Actor-Id": "user-1"}
|
|
105
111
|
assert not hasattr(coder, "shell")
|
|
106
112
|
assert not hasattr(coder, "exec")
|
|
107
113
|
assert not hasattr(coder, "command")
|
|
@@ -116,3 +122,21 @@ async def test_coder_ensure_run_requires_policy_decision_id():
|
|
|
116
122
|
await coder.ensure_run(policy_decision_id="")
|
|
117
123
|
|
|
118
124
|
assert client.calls == []
|
|
125
|
+
|
|
126
|
+
|
|
127
|
+
@pytest.mark.asyncio
|
|
128
|
+
async def test_coder_ensure_run_requires_exactly_one_authority_launch_source():
|
|
129
|
+
client = MockGatewayClient()
|
|
130
|
+
coder = CoderNamespace(client)
|
|
131
|
+
|
|
132
|
+
with pytest.raises(ValueError, match="exactly one"):
|
|
133
|
+
await coder.ensure_run(policy_decision_id="pd_123")
|
|
134
|
+
|
|
135
|
+
with pytest.raises(ValueError, match="exactly one"):
|
|
136
|
+
await coder.ensure_run(
|
|
137
|
+
policy_decision_id="pd_123",
|
|
138
|
+
workflow_recipe_ref="recipe://workflow-recipe-v1/coder@head",
|
|
139
|
+
pipeline_recipe_ref="recipe://pipeline-recipe-v1/coder@head",
|
|
140
|
+
)
|
|
141
|
+
|
|
142
|
+
assert client.calls == []
|
|
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
|
{dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus_sdk_python.egg-info/SOURCES.txt
RENAMED
|
File without changes
|
|
File without changes
|
{dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus_sdk_python.egg-info/requires.txt
RENAMED
|
File without changes
|
{dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/dominus_sdk_python.egg-info/top_level.txt
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_authority_public_vocabulary.py
RENAMED
|
File without changes
|
|
File without changes
|
{dominus_sdk_python-6.1.0 → dominus_sdk_python-6.1.1}/tests/test_control_plane_namespaces.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
|