From 419124d389a511d35a81ee069880460b7e9ff2c8 Mon Sep 17 00:00:00 2001 From: vvillait88 Date: Thu, 14 May 2026 10:41:48 -0700 Subject: [PATCH] test: lock the public-surface barrel exports Add tests asserting every TEC-302 lift-up helper is importable from its documented path. Triggered by a Node-side gap on loadUCPSigningKeyFromEnv: the helper was defined in src/identity/ucp-jwks.ts but never re-exported from src/index.ts, and the helper's own test imported from the module path so it never noticed. Consumers couldn't import it from the documented top-level barrel until the export was patched. Python's barrel was correct the first time around but the same gap could hit any future helper. These tests give us a single-failure signal in CI whenever a future helper lands in a submodule and is forgotten in the __init__.py re-export. Covers: hash_operator_token, load_ucp_signing_key_from_env + LoadUCPSigningKeyOptions, detect_rail_from_headers, zero_amount_carve_out, usd_to_atomic, classify_orchestration_error, classify_x402_settle_result, extract_payment_signer, read_x402_payment_header. Co-Authored-By: Claude Opus 4.7 (1M context) --- tests/test_public_surface.py | 58 ++++++++++++++++++++++++++++++++++++ 1 file changed, 58 insertions(+) create mode 100644 tests/test_public_surface.py diff --git a/tests/test_public_surface.py b/tests/test_public_surface.py new file mode 100644 index 0000000..b1e7b0f --- /dev/null +++ b/tests/test_public_surface.py @@ -0,0 +1,58 @@ +"""Public-API surface tests. + +Locks the documented public surface so a future helper that lands in a module +but is forgotten in the submodule barrel re-export +(``agentscore_commerce..__init__``) fails CI. Mirrors the node-commerce +sibling at ``node-commerce/tests/public-surface.test.ts``. + +The trigger was a Node-side gap on ``loadUCPSigningKeyFromEnv`` during the TEC-302 +lift-up: the helper was defined in ``src/identity/ucp-jwks.ts`` but never +re-exported from ``src/index.ts``. Python had the helper barrel-exported correctly +the first time, but the same gap could hit any future helper; assert every +TEC-302 lift-up entry is importable from its documented path. +""" + +from __future__ import annotations + + +def test_identity_barrel_exports_hash_operator_token() -> None: + """``hash_operator_token`` is importable from ``agentscore_commerce.identity``.""" + from agentscore_commerce import identity as barrel + from agentscore_commerce.identity import tokens as module + + assert barrel.hash_operator_token is module.hash_operator_token + + +def test_identity_barrel_exports_ucp_env_loader() -> None: + """``load_ucp_signing_key_from_env`` + ``LoadUCPSigningKeyOptions`` reachable from the identity barrel.""" + from agentscore_commerce import identity as barrel + from agentscore_commerce.identity import ucp_jwks as module + + assert barrel.load_ucp_signing_key_from_env is module.load_ucp_signing_key_from_env + assert barrel.LoadUCPSigningKeyOptions is module.LoadUCPSigningKeyOptions + + +def test_payment_barrel_exports_detect_rail_zero_settle_usd_to_atomic() -> None: + from agentscore_commerce.payment import ( + detect_rail_from_headers, + usd_to_atomic, + zero_amount_carve_out, + ) + + assert callable(detect_rail_from_headers) + assert callable(zero_amount_carve_out) + assert callable(usd_to_atomic) + + +def test_payment_barrel_exports_classify_helpers() -> None: + from agentscore_commerce.payment import classify_orchestration_error, classify_x402_settle_result + + assert callable(classify_orchestration_error) + assert callable(classify_x402_settle_result) + + +def test_payment_barrel_exports_signer_helpers() -> None: + from agentscore_commerce.payment import extract_payment_signer, read_x402_payment_header + + assert callable(extract_payment_signer) + assert callable(read_x402_payment_header)