Align authorization request digests with Go canonical wire profile
All checks were successful
CI Smoke / host-smoke (push) Successful in 0s
CI Smoke / container-smoke (push) Successful in 1s

Assistant: codex
Assistant-Model: gpt-6.1-sol
Assistant-Session: 01a126e1-76f8-7643-8cf3-e93336539ade
This commit is contained in:
tegwick 2026-10-11 19:47:45 +02:00
parent d5ff4c7421
commit 3ffb6a138e
7 changed files with 399 additions and 9 deletions

View file

@ -0,0 +1,47 @@
# Access request digest interoperability profile
Source-only consumer repair, 2026-10-11. The authoritative algorithm remains
Access Engine `api.RequestDigest` / `api.ApprovalBindingDigest` using Go
`encoding/json`. The opaque `sha256:` prefix is unchanged. This is not a policy
change, native authorization or reinterpretation of a previously served approval.
Existing served approvals retain their original immutable request and digest;
a mismatching request needs a new request/approval rather than rewriting evidence.
The consumer matches literal UTF-8 Unicode, JSON control-character escaping,
Go's default HTML escaping of `<`, `>` and `&`, and unconditional escaping of
U+2028/U+2029, including nested map keys. Invalid Unicode scalar strings fail
closed. Struct fields retain their documented order; nested maps sort by key.
Empty optional attribute maps and context are omitted, matching Go's struct tags.
The optional top-level advisory `purpose` is hashed if present; this does not
admit it on enforcement requests, whose Access endpoint rejects that field.
## Numeric profile
Access HTTP decoding puts JSON numbers in `map[string]any` into binary64
`float64`; arbitrary Python JSON serialization is therefore not equivalent.
This consumer admits finite binary64 floats using shortest round-trip digits,
Go's fixed notation interval `[1e-6, 1e21)`, normalized scientific exponents,
integer-valued float formatting and signed negative zero. Integers outside
`[-(2^53-1), 2^53-1]` fail closed to prevent silently hashing the rounded value
Go would decode. Non-finite values and unsupported non-JSON values fail closed.
Fractional finite values and Unicode catalogue names remain supported. This
profile uses the actual HTTP JSON decode path; arbitrary Go-native values such
as `json.Number` or pre-HTTP big integers are not claimed to match.
## Separate fingerprints
`execution_contract.catalog_target_digest` remains the descriptor-local sorted
JSON UTF-8 fingerprint without Go HTML escaping. Approval Engine's claim-binding
digest and owner body hashes retain their distinct algorithms. Only full Access
request and approval-free Access binding digest computation uses this profile.
Removing `context.approval` reproduces the pre-claim request digest; a full
claim-bearing request continues to hash the entire approval claim.
## Verification
The new tests build a real oracle against the installed Access Engine source
and call its exported digest functions after actual `json.Decode`. They cover
Unicode/HTML/separators, nested keys, exact approval joins, optional omission,
supported integer boundaries and explicit unsupported-number refusals. Existing
normal canonical/replay/approval/descriptor fixtures remain unmodified. No Go
algorithm, policy package, credentials, default or deployment is changed.

View file

@ -0,0 +1,156 @@
{
"schema": "source-preparation-receipt/v1",
"record_id": "SECRETS-CANONICAL-20261011-R1",
"completed_preparation_record_sha256": "c29911e5908ca757d5572530741660438c3d9d1b8962b2ae605cac399ca550f7",
"formal_owner_review": false,
"native_execution": false,
"counterexample_source": "/tmp/access-platform-compiler-review-receipt/docs/evidence/2026-10-11-task-execution/compiler-canonical-counterexample.json",
"counterexample_sha256": "eadd598e7ffceaf1431bb5ec3642afa8c230604da1422d324c21dba4d6411c45",
"go_oracle_source_sha256": "21e754617c2b82d673cef31b7075f8d177e4367782b63b20b37125587bf9e300",
"checks": {
"go_oracle_tests": 34,
"deterministic_float_samples": 256,
"focused_final": 186,
"original_fixture_files_modified": false
},
"prior_observations": [
{
"kind": "incomplete_stage",
"result": "Initial collection errors / missing repo assets; full tracked asset copy corrected staging only."
},
{
"kind": "sandbox_custody",
"result": "Initial full staged suite 612 passed, 16 failed, 1 skipped before fractional-support revision. Initial receipt proved only one unchanged-source reproduction. Revision r2 now runs the exact same sixteen failures against unchanged authoritative source, all sixteen reproduce untrusted-owner failure in this sandbox. Full final revised suite is not claimed green."
},
{
"kind": "superseded_preparation",
"result": "Initial integer-only float profile superseded before frozen candidate; final admits finite fractional binary64 values."
},
{
"kind": "outside-sandbox-baseline",
"result": "Unmodified actual source reproduces TypeError for companion-lane stub missing auth_args; all other custody failures disappear outside sandbox. Exact baseline log retained. Revised test accepts auth_args and verifies identity while preserving each-lane denial/backend refusal test."
}
],
"limits": [
"No policy or Go global algorithm change",
"No reinterpretation of prior served approvals",
"Large Python integers outside safe binary64 interval fail closed",
"No native proof or rollout",
"Independent review remains required"
],
"revision": "r3-existing-test-stub-contract",
"supersedes_receipt_sha256": "7776fd99177e97a3dfc167e8207d1cdeedecc7bb62ed3f9a53c379946dceb49d",
"baseline_verification": {
"unchanged_original_code_sha256": "0ec4c3f7304d68abd06a0d08dc459e4f1f7269da0e4258549662be9e57b39fd3",
"same_sandbox_environment": true,
"observed_tmp_owner_uid": 65534,
"executing_uid": 1000,
"tests_requested": 16,
"same_failures_reproduced": 16,
"per_test": [
{
"test": "tests/test_exec_owner.py::test_actual_bound_child_gets_only_selected_secret_and_fixed_environment",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner.py::test_config_changed_during_fetch_does_not_launch",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner.py::test_binding_changed_after_approval_refuses_before_fetch",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_companion_value_reaches_bound_child_and_is_redacted",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_companion_fetch_failure_starts_no_child",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_each_lane_is_gated_separately_before_backend",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_unresolvable_companion_refuses_before_any_gate",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_delivery_rechecks_companion_contract_before_any_read[missing]",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_delivery_rechecks_companion_contract_before_any_read[extra]",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_delivery_rechecks_companion_contract_before_any_read[env]",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_delivery_rechecks_companion_contract_before_any_read[field]",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_delivery_rechecks_companion_contract_before_any_read[lane]",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_delivery_rechecks_companion_contract_before_any_read[consent]",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_exec_owner_companions.py::test_delivery_rechecks_companion_contract_before_any_read[stage]",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_human_control.py::test_real_exec_handler_rejects_undeclared_claim_before_consume_backend_child",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
},
{
"test": "tests/test_integration_companions.py::test_two_lanes_reach_one_bound_owner",
"result": "failed",
"observed_failure": "exec owner path has an untrusted owner"
}
],
"baseline_observation_path": "/tmp/secrets-canonical-baseline-sixteen-observation.json",
"baseline_observation_sha256": "652badb08358ae90ea01d7777bd9c26b8778d38b1dc78b97f1fb4ee36dfd40ab",
"baseline_log_path": "/tmp/secrets-canonical-baseline-sixteen-tests.txt",
"baseline_log_sha256": "fa88af7b7c14780c63a7609d9da329688a53146aecb98a3b2b1ec736d6baf2c6",
"staged_full_log_path": "/tmp/secrets-canonical-go-final-tests.txt",
"staged_full_log_sha256": "67339d0b2045081f4df67c61e2388df507413057f417d9dd2d77da207fc0bb3e",
"full_final_revised_suite_green": true
},
"full_final_source_suite": {
"exit_code": 0,
"environment": "outside filesystem sandbox with explicit approved escalation",
"collected": 637,
"passed": 636,
"skipped": 1,
"log_path": "/tmp/secrets-canonical-v3-full-suite.txt",
"log_sha256": "b563940c02dfa8b8509dacb48ece3f017c2c841690cda37f0a51e6c7ba2203e0",
"collection_log_path": "/tmp/secrets-canonical-v3-collection.txt",
"collection_log_sha256": "40689fd881e4b16fffcf693b54e05fa169073e7abd884b44642a252d0236bf77",
"baseline_stub_failure_log_path": "/tmp/secrets-canonical-baseline-unsandboxed.txt",
"baseline_stub_failure_log_sha256": "92fd5edb071e1b74a0971642226e532b8f2edc9284b411339335f370c3816f1b",
"baseline_stub_exit_code": 1,
"canonical_code_sha256_unchanged_from_r1": "d58e5fd01ca2470a5d11a6b4f7e9d262a0c1565637e07b35466faa30e4991d14",
"native_estate_changes": false
}
}

View file

@ -0,0 +1,10 @@
{
"schema": "bounded-source-preparation/v1",
"record_id": "SECRETS-CANONICAL-20261011-R1",
"driver": "SECRETS-WP-0013-T01",
"status": "completed",
"scope": "Local canonical digest consumer repair and source tests only",
"formal_owner_assent": false,
"native_execution": false,
"workplan_task_status_change": false
}