feat(ack): add structured worker model routing

This commit is contained in:
2026-07-31 23:34:13 +08:00
parent ee66dbe9ce
commit ae3bce7b5d
23 changed files with 6491 additions and 327 deletions
File diff suppressed because it is too large Load Diff
+19 -1
View File
@@ -34,6 +34,16 @@ class AckSkillContentTests(unittest.TestCase):
self.assertIn('display_name: "ACK"', metadata)
self.assertIn("allow_implicit_invocation: false", metadata)
def test_model_routing_is_fingerprint_bound_and_does_not_trust_receipt_reuse(self) -> None:
content = (
REPO_ROOT / "skills" / "ack" / "references" / "model-routing.md"
).read_text(encoding="utf-8")
self.assertIn("--expected-launch-fingerprint", content)
self.assertIn("allowlist-v1", content)
self.assertIn("禁止根据持久化 receipt 自动复用", content)
self.assertIn("launcher 身份证明", content)
def test_ack_knowledge_resources_and_version_are_present(self) -> None:
ack_dir = REPO_ROOT / "skills" / "ack"
@@ -44,9 +54,17 @@ class AckSkillContentTests(unittest.TestCase):
"scripts/validate_knowledge.py",
"scripts/select_knowledge.py",
"scripts/run_verification.py",
"scripts/worker_profiles.py",
"scripts/launch_worker.py",
):
self.assertTrue((ack_dir / relative_path).is_file(), relative_path)
self.assertEqual((ack_dir / "VERSION").read_text(encoding="utf-8").strip(), "0.9.0")
self.assertEqual((ack_dir / "VERSION").read_text(encoding="utf-8").strip(), "0.10.0")
self.assertIn(
'ackVersion: "<接入时的 ack skill 版本>"',
(ack_dir / "templates" / "tasks.template.yaml").read_text(
encoding="utf-8"
),
)
if __name__ == "__main__":
+185
View File
@@ -1,6 +1,9 @@
from __future__ import annotations
import copy
import importlib.util
import json
import re
import subprocess
import sys
import tempfile
@@ -12,6 +15,7 @@ from pathlib import Path
REPO_ROOT = Path(__file__).resolve().parents[1]
VALIDATOR = REPO_ROOT / "skills" / "ack" / "scripts" / "validate_tasks.py"
EXAMPLE = REPO_ROOT / "skills" / "ack" / "examples" / "tasks.example.yaml"
SCHEMA = REPO_ROOT / "skills" / "ack" / "templates" / "tasks.schema.json"
def valid_knowledge_board() -> dict:
@@ -59,6 +63,21 @@ def valid_knowledge_board() -> dict:
}
def valid_manual_routing_board() -> dict:
board = valid_knowledge_board()
board["ackVersion"] = "0.10.0"
board["project"]["orchestration"] = {
"profileVersion": 1,
"mode": "manual",
"allowedWorktrees": [],
"modelAllowlist": {},
"profiles": {},
"defaults": {},
}
board["workerReceipts"] = []
return board
class AckTaskValidationTests(unittest.TestCase):
def run_validator(
self,
@@ -129,6 +148,160 @@ class AckTaskValidationTests(unittest.TestCase):
self.assertEqual(result.returncode, 0, result.stderr)
self.assertIn("任务板校验通过", result.stdout)
def test_v010_requires_structured_routing_but_v009_remains_readable(self) -> None:
current = valid_knowledge_board()
current["ackVersion"] = "0.10.0"
self.assert_board_rejected_in_all_modes(
current,
"project.orchestration: is required",
)
legacy = valid_knowledge_board()
legacy["ackVersion"] = "0.9.0"
self.assert_board_accepted_in_all_modes(legacy)
def test_builtin_rejects_invalid_ack_semver_in_all_modes(self) -> None:
for invalid in ("0.10", "00.10.0", "0.10.01", "v0.10.0", "0.10.0-"):
with self.subTest(ack_version=invalid):
board = valid_knowledge_board()
board["ackVersion"] = invalid
self.assert_board_rejected_in_all_modes(
board,
"ackVersion 必须是合法 SemVer",
)
def test_schema_declares_semver_routing_and_attempt_contracts(self) -> None:
schema = json.loads(SCHEMA.read_text(encoding="utf-8"))
ack_pattern = re.compile(schema["properties"]["ackVersion"]["pattern"])
for valid in ("0.9.0", "0.10.0", "0.11.2-alpha.1+build.7", "1.0.0"):
with self.subTest(valid_semver=valid):
self.assertIsNotNone(ack_pattern.fullmatch(valid))
for invalid in ("0.10", "00.10.0", "0.10.01", "v0.10.0", "0.10.0-"):
with self.subTest(invalid_semver=invalid):
self.assertIsNone(ack_pattern.fullmatch(invalid))
current_gate, orchestration_gate, receipts_gate = schema["allOf"]
current_pattern = re.compile(
current_gate["if"]["properties"]["ackVersion"]["pattern"]
)
for current in ("0.10.0", "0.99.1", "1.0.0", "12.34.56+build"):
self.assertIsNotNone(current_pattern.search(current))
self.assertIsNone(current_pattern.search("0.9.99"))
self.assertIn("workerReceipts", current_gate["then"]["required"])
self.assertIn(
"workerReceipts",
current_gate["then"]["properties"],
)
self.assertIn(
"orchestration",
current_gate["then"]["properties"]["project"]["required"],
)
self.assertIn(
"orchestration",
current_gate["then"]["properties"]["project"]["properties"],
)
self.assertIn("workerReceipts", orchestration_gate["then"]["required"])
self.assertIn(
"workerReceipts",
orchestration_gate["then"]["properties"],
)
self.assertIn(
"orchestration",
receipts_gate["then"]["properties"]["project"]["required"],
)
self.assertIn(
"orchestration",
receipts_gate["then"]["properties"]["project"]["properties"],
)
for gate in (current_gate, orchestration_gate, receipts_gate):
self.assertEqual(
gate["then"]["properties"]["tasks"]["$ref"],
"#/definitions/launchableTasks",
)
role_dispatch = schema["definitions"]["roleDispatch"]
self.assertIn("attemptId", role_dispatch["required"])
receipt_rule = role_dispatch["allOf"][0]
self.assertEqual(
receipt_rule["then"]["properties"]["attemptId"]["type"],
"null",
)
self.assertEqual(
receipt_rule["else"]["properties"]["attemptId"]["type"],
"string",
)
@unittest.skipUnless(
importlib.util.find_spec("jsonschema") is not None,
"jsonschema is required for the schema-only contract test",
)
def test_schema_alone_enforces_v010_and_mutual_routing_presence(self) -> None:
import jsonschema # type: ignore
schema = json.loads(SCHEMA.read_text(encoding="utf-8"))
validator = jsonschema.Draft7Validator(schema)
def messages(board: dict) -> list[str]:
return [error.message for error in validator.iter_errors(board)]
base = {
"version": 1,
"ackVersion": "0.9.0",
"project": {"name": "demo"},
"tasks": [],
}
self.assertEqual(messages(base), [])
for current in ("0.10.0", "0.11.2-alpha.1+build.7", "1.0.0"):
with self.subTest(ack_version=current):
board = copy.deepcopy(base)
board["ackVersion"] = current
errors = messages(board)
self.assertIn("'workerReceipts' is a required property", errors)
self.assertIn("'orchestration' is a required property", errors)
manual = {
"profileVersion": 1,
"mode": "manual",
"allowedWorktrees": [],
"modelAllowlist": {},
"profiles": {},
"defaults": {},
}
orchestration_only = copy.deepcopy(base)
orchestration_only["project"]["orchestration"] = manual
self.assertIn(
"'workerReceipts' is a required property",
messages(orchestration_only),
)
receipts_only = copy.deepcopy(base)
receipts_only["workerReceipts"] = []
self.assertIn(
"'orchestration' is a required property",
messages(receipts_only),
)
complete = copy.deepcopy(orchestration_only)
complete["ackVersion"] = "0.10.0+routing.1"
complete["workerReceipts"] = []
self.assertEqual(messages(complete), [])
def test_v010_task_ids_match_launcher_while_legacy_ids_remain_readable(
self,
) -> None:
current = valid_manual_routing_board()
current["tasks"][0]["id"] = "BUG/001"
self.assert_board_rejected_in_all_modes(
current,
"v0.10 自动路由 id 只允许字母、数字、点、下划线和连字符",
)
legacy = valid_knowledge_board()
legacy["ackVersion"] = "0.9.0"
legacy["tasks"][0]["id"] = "BUG/001"
self.assert_board_accepted_in_all_modes(legacy)
def test_knowledge_applied_and_checks_must_reference_selected_knowledge(self) -> None:
result = self.run_validator(
"""
@@ -582,6 +755,18 @@ class AckTaskValidationTests(unittest.TestCase):
"T-RESOLUTION.resolution: 必须是对象",
)
def test_dispatch_rejects_free_command_field_without_jsonschema(self) -> None:
board = valid_knowledge_board()
board["tasks"][0]["dispatch"] = {
"command": "cursor-agent --yolo",
"rounds": [],
}
self.assert_board_rejected_in_all_modes(
board,
"dispatch: 未知字段 'command'",
)
def test_valid_optional_schema_fields_pass_in_all_modes(self) -> None:
board = valid_knowledge_board()
board.update(
+895
View File
@@ -0,0 +1,895 @@
from __future__ import annotations
import copy
import sys
import unittest
from pathlib import Path
REPO_ROOT = Path(__file__).resolve().parents[1]
SCRIPTS_DIR = REPO_ROOT / "skills" / "ack" / "scripts"
sys.path.insert(0, str(SCRIPTS_DIR))
import worker_profiles # noqa: E402
def valid_orchestration() -> dict:
return {
"profileVersion": 1,
"mode": "orca",
"allowedWorktrees": ["/repo/demo"],
"modelAllowlist": {
"codex": {
"developer": {
"standard": ["gpt-safe-dev"],
"strong": ["gpt-safe-strong"],
},
"test": {"standard": ["gpt-safe-test"]},
},
"cursor-agent": {
"developer": {"standard": ["cursor-auto"]},
"test": {"standard": ["cursor-auto"]},
},
},
"profiles": {
"codex-dev-standard": {
"role": "developer",
"cli": "codex",
"tier": "standard",
"model": "gpt-safe-dev",
"reasoningEffort": "medium",
"permissionMode": "workspace-write",
},
"codex-dev-strong": {
"role": "developer",
"cli": "codex",
"tier": "strong",
"model": "gpt-safe-strong",
"reasoningEffort": "high",
"permissionMode": "workspace-write",
},
"cursor-test-standard": {
"role": "test",
"cli": "cursor-agent",
"tier": "standard",
"model": "cursor-auto",
"reasoningEffort": None,
"permissionMode": "read-only",
},
"cursor-dev-standard": {
"role": "developer",
"cli": "cursor-agent",
"tier": "standard",
"model": "cursor-auto",
"reasoningEffort": None,
"permissionMode": "workspace-write",
},
},
"defaults": {
"developer": "codex-dev-standard",
"test": "cursor-test-standard",
"developerUpgraded": "codex-dev-strong",
},
}
def valid_receipt(orchestration: dict | None = None) -> dict:
routing = orchestration or valid_orchestration()
profile_id = "codex-dev-standard"
profile = routing["profiles"][profile_id]
executable = "/usr/local/bin/codex"
worktree_path = "/repo/demo"
argv = worker_profiles.render_worker_argv(profile, executable, worktree_path)
launch_id = "a" * 64
requested = {
"cli": profile["cli"],
"tier": profile["tier"],
"model": profile["model"],
"reasoningEffort": profile["reasoningEffort"],
"permissionMode": profile["permissionMode"],
"executable": executable,
"executableDevice": 8,
"executableInode": 201,
"cliVersion": "codex 1.0.0",
"argv": argv,
"argvHash": worker_profiles.canonical_sha256(argv),
"environmentPolicy": "per-cli-allowlist-v1",
}
worktree = {
"path": worktree_path,
"device": 8,
"inode": 101,
"gitCommonDir": "/repo/demo/.git",
"gitCommonDevice": 8,
"gitCommonInode": 102,
}
receipt = {
"receiptVersion": 1,
"id": f"WR-{launch_id}",
"launchId": launch_id,
"profileId": profile_id,
"profileHash": worker_profiles.profile_hash(profile),
"launchFingerprint": worker_profiles.canonical_sha256(
{
"protocolVersion": 1,
"backend": "orca",
"profileId": profile_id,
"profileHash": worker_profiles.profile_hash(profile),
"createdFor": {
"taskId": "TASK-001",
"attemptId": "TASK-001-A1",
"role": "developer",
},
"worktree": worktree,
"requested": requested,
"slot": 1,
}
),
"slot": 1,
"createdFor": {
"taskId": "TASK-001",
"attemptId": "TASK-001-A1",
"role": "developer",
},
"worktree": worktree,
"requested": requested,
"binding": {
"orchestrator": "orca",
"runtimeId": "runtime-001",
"handle": "terminal-001",
"incarnationId": "incarnation-001",
"observedWorktreePath": worktree_path,
"connected": True,
"writable": True,
"boundAt": "2026-07-31T12:00:01+08:00",
},
"createdAt": "2026-07-31T12:00:00+08:00",
"receiptHash": "",
}
receipt["receiptHash"] = worker_profiles.receipt_hash(receipt)
return receipt
class CanonicalHashTests(unittest.TestCase):
def test_hash_is_prefixed_order_independent_and_content_sensitive(self) -> None:
first = worker_profiles.canonical_sha256(
{"b": [2, 1], "a": {"enabled": True}}
)
reordered = worker_profiles.canonical_sha256(
{"a": {"enabled": True}, "b": [2, 1]}
)
changed = worker_profiles.canonical_sha256(
{"a": {"enabled": False}, "b": [2, 1]}
)
self.assertEqual(first, reordered)
self.assertNotEqual(first, changed)
self.assertRegex(first, r"^sha256:[0-9a-f]{64}$")
def test_hash_rejects_non_json_and_non_finite_values(self) -> None:
with self.assertRaises(ValueError):
worker_profiles.canonical_sha256({"bad": object()})
with self.assertRaises(ValueError):
worker_profiles.canonical_sha256({"bad": float("nan")})
cyclic: list = []
cyclic.append(cyclic)
with self.assertRaises(ValueError):
worker_profiles.canonical_sha256(cyclic)
def test_profile_hash_rejects_invalid_profile(self) -> None:
profile = valid_orchestration()["profiles"]["codex-dev-standard"]
profile["command"] = "codex; touch forged"
with self.assertRaises(ValueError):
worker_profiles.profile_hash(profile)
def test_profile_hash_binds_profile_version(self) -> None:
profile = valid_orchestration()["profiles"]["codex-dev-standard"]
self.assertNotEqual(
worker_profiles.profile_hash(profile, profile_version=1),
worker_profiles.profile_hash(profile, profile_version=2),
)
class ProfileValidationTests(unittest.TestCase):
def test_valid_orchestration_passes(self) -> None:
self.assertEqual(
worker_profiles.validate_orchestration(valid_orchestration()),
[],
)
def test_manual_mode_accepts_empty_structured_routing(self) -> None:
routing = {
"profileVersion": 1,
"mode": "manual",
"allowedWorktrees": [],
"modelAllowlist": {},
"profiles": {},
"defaults": {},
}
self.assertEqual(worker_profiles.validate_orchestration(routing), [])
def test_partial_empty_allowlist_nodes_are_rejected(self) -> None:
routing = {
"profileVersion": 1,
"mode": "manual",
"allowedWorktrees": [],
"modelAllowlist": {"codex": {}},
"profiles": {},
"defaults": {},
}
errors = worker_profiles.validate_orchestration(routing)
self.assertTrue(any("modelAllowlist.codex: must not be empty" in error for error in errors))
def test_profile_rejects_all_command_shaped_and_unknown_fields(self) -> None:
forbidden = ("command", "args", "env", "executable", "argv", "extraArgs")
for field in forbidden:
with self.subTest(field=field):
routing = valid_orchestration()
routing["profiles"]["codex-dev-standard"][field] = "forged"
errors = worker_profiles.validate_orchestration(routing)
self.assertTrue(any(f"unknown field '{field}'" in error for error in errors))
def test_routing_rejects_unknown_top_level_fields(self) -> None:
routing = valid_orchestration()
routing["command"] = "codex"
errors = worker_profiles.validate_orchestration(routing)
self.assertIn("project.orchestration: unknown field 'command'", errors)
def test_model_id_rejects_shell_and_whitespace_syntax(self) -> None:
for model in (
"safe;touch-forged",
"safe && forged",
"$(touch-forged)",
"`touch-forged`",
"safe\nforged",
"--dangerously-bypass-approvals-and-sandbox",
):
with self.subTest(model=model):
routing = valid_orchestration()
routing["profiles"]["codex-dev-standard"]["model"] = model
errors = worker_profiles.validate_orchestration(routing)
self.assertTrue(any("safe model ID" in error for error in errors))
def test_only_safe_permission_modes_are_accepted(self) -> None:
for permission in (
"danger-full-access",
"full-access",
"yolo",
"bypass",
"never",
):
with self.subTest(permission=permission):
routing = valid_orchestration()
routing["profiles"]["codex-dev-standard"][
"permissionMode"
] = permission
errors = worker_profiles.validate_orchestration(routing)
self.assertTrue(any("read-only/workspace-write" in error for error in errors))
def test_reasoning_effort_is_required_for_codex_and_null_for_cursor(self) -> None:
codex = valid_orchestration()
codex["profiles"]["codex-dev-standard"]["reasoningEffort"] = None
cursor = valid_orchestration()
cursor["profiles"]["cursor-test-standard"]["reasoningEffort"] = "low"
codex_errors = worker_profiles.validate_orchestration(codex)
cursor_errors = worker_profiles.validate_orchestration(cursor)
self.assertTrue(any("Codex requires" in error for error in codex_errors))
self.assertTrue(any("Cursor requires null" in error for error in cursor_errors))
def test_test_cannot_use_strong_tier(self) -> None:
routing = valid_orchestration()
profile = routing["profiles"]["cursor-test-standard"]
profile["tier"] = "strong"
routing["modelAllowlist"]["cursor-agent"]["test"]["strong"] = [
"cursor-auto"
]
errors = worker_profiles.validate_orchestration(routing)
self.assertTrue(any("Test may only use standard" in error for error in errors))
self.assertTrue(any("Test cannot define a strong allowlist" in error for error in errors))
def test_profile_model_must_match_exact_cli_role_tier_allowlist(self) -> None:
routing = valid_orchestration()
routing["profiles"]["codex-dev-standard"]["model"] = "other-safe-model"
errors = worker_profiles.validate_orchestration(routing)
self.assertTrue(any("is not allowed for its cli/role/tier" in error for error in errors))
def test_defaults_require_matching_role_and_standard_tier(self) -> None:
wrong_role = valid_orchestration()
wrong_role["defaults"]["test"] = "codex-dev-standard"
strong_default = valid_orchestration()
strong_default["defaults"]["developer"] = "codex-dev-strong"
role_errors = worker_profiles.validate_orchestration(wrong_role)
tier_errors = worker_profiles.validate_orchestration(strong_default)
self.assertTrue(any("profile role must be test" in error for error in role_errors))
self.assertTrue(any("default profile must use standard" in error for error in tier_errors))
def test_developer_upgraded_default_requires_developer_strong(self) -> None:
valid = valid_orchestration()
wrong_tier = valid_orchestration()
wrong_tier["defaults"]["developerUpgraded"] = "codex-dev-standard"
wrong_role = valid_orchestration()
wrong_role["defaults"]["developerUpgraded"] = "cursor-test-standard"
self.assertEqual(worker_profiles.validate_orchestration(valid), [])
tier_errors = worker_profiles.validate_orchestration(wrong_tier)
role_errors = worker_profiles.validate_orchestration(wrong_role)
self.assertTrue(any("must use strong tier" in error for error in tier_errors))
self.assertTrue(any("profile role must be developer" in error for error in role_errors))
def test_malformed_scalar_types_return_errors_instead_of_raising(self) -> None:
for field in ("role", "cli", "tier", "reasoningEffort", "permissionMode"):
with self.subTest(profile_field=field):
profile = valid_orchestration()["profiles"]["codex-dev-standard"]
profile[field] = []
self.assertTrue(worker_profiles.validate_profile(profile))
routing = valid_orchestration()
routing["mode"] = []
self.assertTrue(worker_profiles.validate_orchestration(routing))
receipt = valid_receipt()
receipt["profileId"] = []
receipt["requested"]["cli"] = []
receipt["requested"]["tier"] = []
receipt["requested"]["permissionMode"] = []
receipt["receiptHash"] = worker_profiles.receipt_hash(receipt)
self.assertTrue(worker_profiles.validate_worker_receipt(receipt))
self.assertTrue(
worker_profiles.validate_worker_receipt(receipt, orchestration=[])
)
def test_orca_requires_defaults_profiles_and_allowed_worktree(self) -> None:
routing = valid_orchestration()
routing["allowedWorktrees"] = []
routing["profiles"] = {}
routing["defaults"] = {}
errors = worker_profiles.validate_orchestration(routing)
self.assertTrue(any("requires at least one path" in error for error in errors))
self.assertTrue(any("Orca mode requires profiles" in error for error in errors))
self.assertTrue(any("missing role 'developer'" in error for error in errors))
self.assertTrue(any("missing role 'test'" in error for error in errors))
class ArgvRendererTests(unittest.TestCase):
def test_codex_exact_safe_argv(self) -> None:
profile = valid_orchestration()["profiles"]["codex-dev-standard"]
argv = worker_profiles.render_worker_argv(
profile,
"/usr/local/bin/codex",
"/repo/demo",
)
self.assertEqual(
argv,
[
"/usr/local/bin/codex",
"--strict-config",
"--model",
"gpt-safe-dev",
"--config",
"model_reasoning_effort=medium",
"--sandbox",
"workspace-write",
"--ask-for-approval",
"never",
"--cd",
"/repo/demo",
],
)
def test_cursor_read_only_exact_safe_argv(self) -> None:
profile = valid_orchestration()["profiles"]["cursor-test-standard"]
argv = worker_profiles.render_worker_argv(
profile,
"/usr/local/bin/cursor-agent",
"/repo/demo",
)
self.assertEqual(
argv,
[
"/usr/local/bin/cursor-agent",
"--model",
"cursor-auto",
"--mode",
"plan",
"--sandbox",
"enabled",
"--workspace",
"/repo/demo",
],
)
def test_cursor_workspace_write_adds_auto_review_without_yolo(self) -> None:
profile = valid_orchestration()["profiles"]["cursor-dev-standard"]
argv = worker_profiles.render_worker_argv(
profile,
"/usr/local/bin/cursor-agent",
"/repo/demo",
)
self.assertEqual(
argv,
[
"/usr/local/bin/cursor-agent",
"--model",
"cursor-auto",
"--auto-review",
"--sandbox",
"enabled",
"--workspace",
"/repo/demo",
],
)
self.assertNotIn("--yolo", argv)
self.assertNotIn("--force", argv)
def test_renderer_rejects_wrong_executable_or_unsafe_worktree(self) -> None:
profile = valid_orchestration()["profiles"]["codex-dev-standard"]
with self.assertRaises(ValueError):
worker_profiles.render_worker_argv(
profile,
"/tmp/cursor-agent",
"/repo/demo",
)
with self.assertRaises(ValueError):
worker_profiles.render_worker_argv(
profile,
"/usr/local/bin/codex",
"/repo/demo/../outside",
)
for worktree in ("/repo/./demo", "/repo/demo/", "//repo/demo"):
with self.subTest(worktree=worktree), self.assertRaises(ValueError):
worker_profiles.render_worker_argv(
profile,
"/usr/local/bin/codex",
worktree,
)
class ReceiptValidationTests(unittest.TestCase):
def test_valid_receipt_is_bound_to_profile_and_routing(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
self.assertEqual(
worker_profiles.validate_worker_receipt(
receipt,
orchestration=routing,
task_ids={"TASK-001"},
),
[],
)
self.assertEqual(receipt["receiptHash"], worker_profiles.receipt_hash(receipt))
def test_receipt_rejects_unknown_fields_at_every_strict_level(self) -> None:
cases = (
((), "command"),
(("createdFor",), "command"),
(("worktree",), "command"),
(("requested",), "command"),
(("binding",), "command"),
)
for path, field in cases:
with self.subTest(path=path):
routing = valid_orchestration()
receipt = valid_receipt(routing)
target = receipt
for component in path:
target = target[component]
target[field] = "forged"
receipt["receiptHash"] = worker_profiles.receipt_hash(receipt)
errors = worker_profiles.validate_worker_receipt(
receipt,
orchestration=routing,
task_ids={"TASK-001"},
)
self.assertTrue(any("unknown field 'command'" in error for error in errors))
def test_receipt_rejects_profile_and_exact_argv_drift(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
receipt["requested"]["model"] = "gpt-safe-strong"
receipt["requested"]["argv"][3] = "gpt-safe-strong"
receipt["requested"]["argvHash"] = worker_profiles.canonical_sha256(
receipt["requested"]["argv"]
)
receipt["receiptHash"] = worker_profiles.receipt_hash(receipt)
errors = worker_profiles.validate_worker_receipt(
receipt,
orchestration=routing,
task_ids={"TASK-001"},
)
self.assertTrue(any("requested.model: does not match profile" in error for error in errors))
self.assertTrue(
any(
"requested.argv: does not match exact renderer" in error
for error in errors
)
)
def test_receipt_rejects_tampering_without_recomputed_hash(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
receipt["binding"]["handle"] = "forged-handle"
errors = worker_profiles.validate_worker_receipt(
receipt,
orchestration=routing,
task_ids={"TASK-001"},
)
self.assertTrue(any("receiptHash: does not match receipt" in error for error in errors))
def test_receipt_rejects_out_of_budget_attempt_empty_argv_and_id_drift(self) -> None:
routing = valid_orchestration()
attempt = valid_receipt(routing)
attempt["createdFor"]["attemptId"] = "TASK-001-A4"
attempt["receiptHash"] = worker_profiles.receipt_hash(attempt)
attempt_errors = worker_profiles.validate_worker_receipt(
attempt,
orchestration=routing,
task_ids={"TASK-001"},
)
empty_argv = valid_receipt(routing)
empty_argv["requested"]["argv"] = []
empty_argv["requested"]["argvHash"] = worker_profiles.canonical_sha256([])
empty_argv["receiptHash"] = worker_profiles.receipt_hash(empty_argv)
argv_errors = worker_profiles.validate_worker_receipt(
empty_argv,
orchestration=routing,
task_ids={"TASK-001"},
)
wrong_id = valid_receipt(routing)
wrong_id["id"] = "WR-" + "b" * 64
wrong_id["receiptHash"] = worker_profiles.receipt_hash(wrong_id)
id_errors = worker_profiles.validate_worker_receipt(
wrong_id,
orchestration=routing,
task_ids={"TASK-001"},
)
self.assertTrue(any("A1..A3" in error for error in attempt_errors))
self.assertTrue(any("at least 2 items" in error for error in argv_errors))
self.assertTrue(any("must equal 'WR-' + launchId" in error for error in id_errors))
def test_receipt_rejects_rehashed_launch_fingerprint_tampering(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
receipt["launchFingerprint"] = worker_profiles.canonical_sha256(
{"forged": True}
)
receipt["receiptHash"] = worker_profiles.receipt_hash(receipt)
errors = worker_profiles.validate_worker_receipt(
receipt,
orchestration=routing,
task_ids={"TASK-001"},
)
self.assertTrue(
any(
"launchFingerprint: does not match launch facts" in error
for error in errors
)
)
def test_receipt_slot_is_bounded_and_bound_into_launch_fingerprint(self) -> None:
routing = valid_orchestration()
invalid = valid_receipt(routing)
invalid["slot"] = 0
invalid["receiptHash"] = worker_profiles.receipt_hash(invalid)
invalid_errors = worker_profiles.validate_worker_receipt(
invalid,
orchestration=routing,
task_ids={"TASK-001"},
)
drifted = valid_receipt(routing)
drifted["slot"] = 2
drifted["receiptHash"] = worker_profiles.receipt_hash(drifted)
drifted_errors = worker_profiles.validate_worker_receipt(
drifted,
orchestration=routing,
task_ids={"TASK-001"},
)
self.assertTrue(any("slot: must be" in error for error in invalid_errors))
self.assertTrue(
any(
"launchFingerprint: does not match launch facts" in error
for error in drifted_errors
)
)
def test_receipt_with_non_json_data_returns_errors(self) -> None:
receipt = valid_receipt()
receipt["requested"]["argv"] = [object()]
errors = worker_profiles.validate_worker_receipt(receipt)
self.assertTrue(any("must contain canonical JSON data" in error for error in errors))
def test_receipt_rejects_wrong_worktree_task_and_binding(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
receipt["worktree"]["path"] = "/repo/other"
receipt["binding"]["observedWorktreePath"] = "/repo/elsewhere"
receipt["receiptHash"] = worker_profiles.receipt_hash(receipt)
errors = worker_profiles.validate_worker_receipt(
receipt,
orchestration=routing,
task_ids={"OTHER-TASK"},
)
self.assertTrue(any("unknown task 'TASK-001'" in error for error in errors))
self.assertTrue(any("is not in allowedWorktrees" in error for error in errors))
self.assertTrue(any("does not match worktree.path" in error for error in errors))
def test_receipt_requires_safe_environment_and_live_binding(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
receipt["requested"]["environmentPolicy"] = "inherit-all"
receipt["binding"]["connected"] = False
receipt["binding"]["writable"] = False
receipt["receiptHash"] = worker_profiles.receipt_hash(receipt)
errors = worker_profiles.validate_worker_receipt(
receipt,
orchestration=routing,
task_ids={"TASK-001"},
)
self.assertTrue(any("per-cli-allowlist-v1" in error for error in errors))
self.assertTrue(any("binding.connected: must be true" in error for error in errors))
self.assertTrue(any("binding.writable: must be true" in error for error in errors))
def test_receipt_list_rejects_duplicate_receipt_and_launch_ids(self) -> None:
routing = valid_orchestration()
first = valid_receipt(routing)
duplicate = copy.deepcopy(first)
errors = worker_profiles.validate_worker_receipts(
[first, duplicate],
routing,
task_ids={"TASK-001"},
)
self.assertTrue(any("duplicate receipt ID" in error for error in errors))
self.assertTrue(any("duplicate launch ID" in error for error in errors))
def test_document_requires_top_level_receipts_and_routing(self) -> None:
missing = {
"version": 1,
"project": {"name": "demo"},
"tasks": [],
}
errors = worker_profiles.validate_routing_document(missing)
self.assertEqual(errors, ["project.orchestration: is required"])
def test_valid_document_passes_and_manual_receipts_fail(self) -> None:
routing = valid_orchestration()
document = {
"version": 1,
"project": {"name": "demo", "orchestration": routing},
"workerReceipts": [valid_receipt(routing)],
"tasks": [{"id": "TASK-001", "title": "demo", "status": "open"}],
}
self.assertEqual(worker_profiles.validate_routing_document(document), [])
manual = {
"version": 1,
"project": {
"name": "demo",
"orchestration": {
"profileVersion": 1,
"mode": "manual",
"allowedWorktrees": [],
"modelAllowlist": {},
"profiles": {},
"defaults": {},
},
},
"workerReceipts": [valid_receipt(routing)],
"tasks": [{"id": "TASK-001", "title": "demo", "status": "open"}],
}
manual_errors = worker_profiles.validate_routing_document(manual)
self.assertTrue(
any("manual orchestration requires an empty list" in error for error in manual_errors)
)
def test_dispatch_receipt_allows_two_phase_for_exact_task_attempt_binding(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
role_dispatch = {
"profileId": receipt["profileId"],
"receiptId": receipt["id"],
"attemptId": "TASK-001-A1",
"taskId": None,
"dispatchId": None,
}
document = {
"version": 1,
"project": {"name": "demo", "orchestration": routing},
"workerReceipts": [receipt],
"tasks": [
{
"id": "TASK-001",
"title": "created for",
"status": "dispatched",
"dispatch": {"developer": role_dispatch},
},
],
}
self.assertEqual(worker_profiles.validate_routing_document(document), [])
role_dispatch["taskId"] = "orca-task-002"
role_dispatch["dispatchId"] = "orca-dispatch-002"
self.assertEqual(worker_profiles.validate_routing_document(document), [])
def test_dispatch_rejects_unknown_or_mismatched_receipt(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
role_dispatch = {
"profileId": "codex-dev-strong",
"receiptId": receipt["id"],
"attemptId": "TASK-001-A1",
"taskId": None,
"dispatchId": None,
}
document = {
"version": 1,
"project": {"name": "demo", "orchestration": routing},
"workerReceipts": [receipt],
"tasks": [
{
"id": "TASK-001",
"title": "demo",
"status": "open",
"dispatch": {"developer": role_dispatch},
}
],
}
errors = worker_profiles.validate_routing_document(document)
self.assertTrue(
any("profileId: does not match referenced receipt" in error for error in errors)
)
role_dispatch["receiptId"] = f"WR-{'b' * 64}"
errors = worker_profiles.validate_routing_document(document)
self.assertTrue(any("unknown receipt" in error for error in errors))
def test_dispatch_rejects_cross_task_role_and_attempt_receipts(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
link = {
"profileId": receipt["profileId"],
"receiptId": receipt["id"],
"attemptId": "TASK-001-A1",
"taskId": None,
"dispatchId": None,
}
document = {
"version": 1,
"project": {"name": "demo", "orchestration": routing},
"workerReceipts": [receipt],
"tasks": [
{"id": "TASK-001", "title": "receipt owner", "status": "open"},
{
"id": "TASK-002",
"title": "must not reuse receipt",
"status": "dispatched",
"dispatch": {"developer": link},
},
],
}
errors = worker_profiles.validate_routing_document(document)
self.assertTrue(any("must be current ACK task 'TASK-002'" in error for error in errors))
self.assertTrue(any("must belong to current ACK task 'TASK-002'" in error for error in errors))
document["tasks"][1]["id"] = "TASK-001"
link["attemptId"] = "TASK-001-A2"
errors = worker_profiles.validate_routing_document(document)
self.assertTrue(any("does not match referenced receipt" in error for error in errors))
link["attemptId"] = "TASK-001-A1"
document["tasks"][1]["dispatch"] = {"test": link}
errors = worker_profiles.validate_routing_document(document)
self.assertTrue(any("referenced receipt role must be test" in error for error in errors))
def test_dispatch_attempt_presence_tracks_receipt_presence(self) -> None:
routing = valid_orchestration()
receipt = valid_receipt(routing)
link = {
"profileId": receipt["profileId"],
"receiptId": None,
"attemptId": "TASK-001-A1",
"taskId": None,
"dispatchId": None,
}
document = {
"version": 1,
"project": {"name": "demo", "orchestration": routing},
"workerReceipts": [receipt],
"tasks": [
{
"id": "TASK-001",
"title": "demo",
"status": "open",
"dispatch": {"developer": link},
}
],
}
errors = worker_profiles.validate_routing_document(document)
self.assertTrue(any("must be null when receiptId is null" in error for error in errors))
link["receiptId"] = receipt["id"]
link["attemptId"] = None
errors = worker_profiles.validate_routing_document(document)
self.assertTrue(any("is required when receiptId is set" in error for error in errors))
def test_dispatch_requires_receipt_before_paired_runtime_ids(self) -> None:
routing = valid_orchestration()
document = {
"version": 1,
"project": {"name": "demo", "orchestration": routing},
"workerReceipts": [],
"tasks": [
{
"id": "TASK-001",
"title": "demo",
"status": "dispatched",
"dispatch": {
"developer": {
"profileId": "codex-dev-standard",
"receiptId": None,
"attemptId": None,
"taskId": "orca-task-001",
"dispatchId": None,
}
},
}
],
}
errors = worker_profiles.validate_routing_document(document)
self.assertTrue(any("must both be null or both be set" in error for error in errors))
self.assertTrue(any("required before runtime dispatch IDs" in error for error in errors))
if __name__ == "__main__":
unittest.main()