Skip to content

feat(transport): multi-host Transport seam + /verify evidence endpoint#1

Open
imonacloud wants to merge 5 commits into
mainfrom
feat/multi-host
Open

feat(transport): multi-host Transport seam + /verify evidence endpoint#1
imonacloud wants to merge 5 commits into
mainfrom
feat/multi-host

Conversation

@imonacloud

Copy link
Copy Markdown
Member

Summary

  • Adds chp_core/transport.pyTransport Protocol (async, @runtime_checkable), LocalTransport (wraps LocalCapabilityHost), and HttpTransport (wraps RemoteCapabilityHost via asyncio.to_thread)
  • Adds GET /verify/{correlation_id} to the HTTP server, returning ChainVerificationResult as JSON; adds sync RemoteCapabilityHost.invoke_envelope() and RemoteCapabilityHost.verify() client methods
  • Exports Transport, LocalTransport, HttpTransport from chp_core/__init__.py
  • All 752 tests pass; conformance suite (29 checks) passes

Test plan

  • pytest packages/python/tests/ — 752 tests green
  • python conformance/runner.py — 29/29 PASS
  • python -c "import json,glob; ..." — 27 schemas OK
  • LocalTransport and HttpTransport both satisfy isinstance(x, Transport) at runtime

🤖 Generated with Claude Code

imonacloud and others added 5 commits June 9, 2026 15:00
Spec (chp-v0.1.md):
- §5: add payload validation SHOULD/MUST + duplicate registration semantics
- §6: strengthen append-only from SHOULD to MUST
- §9: enumerate standard denial codes table
- §10: add replay query bounds recommendation (cap: 10,000)
- §13: add conformance tagging requirement

Implementation (host.py):
- Input schema validation against input_schema before handler runs
  (denial code: input_schema_validation_failed)
- Replay query capped at MAX_REPLAY_LIMIT=10_000 to prevent memory exhaustion
- Thread-safe capability registry via RLock on _capabilities dict
- Duplicate registration emits warnings.warn instead of silent overwrite
- Full traceback in execution_failed evidence (removed limit=3)

Onboarding:
- Add AGENTS.md — machine-first orientation for AI agents (invariants,
  commands, navigation, pitfalls); follows AGENTS.md open spec
- Add docs/llms.txt — ultra-compact protocol reference for LLM context windows
- Redirect three legacy docs (onboarding, agent-prompt, capability-lookup-prompt)
  from Zenoh-era content to current entry points

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…flag, remote resilience, test coverage

Pillar 1 — Input validation at public API boundaries
- Empty capability_id now denies with capability_not_found before _resolve()
- Unknown mode strings caught early in ainvoke() with unsupported_mode denial
- jsonschema ValidationError split from generic Exception; denial now includes path of failing field in details

Pillar 2 — ReplayResult.truncated
- types.py: add truncated: bool = False field to ReplayResult
- host.py: replay_result() sets truncated=True when result was capped by MAX_REPLAY_LIMIT
- schemas/replay-result.schema.json: add truncated property
- spec/chp-v0.1.md §10: add MUST sentence for truncated flag
- docs/llms.txt: update ReplayResult fields line

Pillar 3 — RemoteCapabilityHost resilience
- _send() catches URLError → ConnectionError and OSError → ConnectionError
- Non-dict 200 responses raise RuntimeError("non-JSON response: ...")
- Body capped at 500 chars in error messages

Pillar 4 — Test coverage gaps
- test_local_host.py: unsupported_mode, empty_capability_id, unknown_mode_string, input_schema_error_includes_field_path; truncated and disabled-capability assertions
- test_http.py: connection refused, non-JSON 200, HTTP 500 remote tests; HTTPServerEdgeCaseTests class (404, malformed body)
- test_conformance_runner.py: new file — 4 subprocess self-tests verifying passing sample passes and broken samples fail expected checks

745 tests pass, 29/29 conformance checks pass, 42/42 alignment checks pass.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Conformance suite (26 → 29 checks):
- Added check_standard_denial_codes — uses passed-in host directly to test denial code values
- Added check_input_schema_validation — isolated host registers typed capability; bad payload denied, good succeeds
- Added check_evidence_hash_chain — verifies 64-char hex content_hash and prev_hash linkage
- Added --sample flag with 4 modes: passing, failing-no-evidence, failing-non-standard-codes, failing-no-hash-chain
- Refactored sample_failing_hosts.py: BrokenNoEvidenceHost, BrokenNonStandardCodesHost, BrokenNoHashChainHost

Schemas:
- evidence-event.schema.json: add content_hash and prev_hash optional fields with ^[a-f0-9]{64}$ pattern
- denial-reason.schema.json: add description and examples listing all 8 standard denial codes
- replay-query.schema.json: add maximum: 10000 on limit field, reference spec §10

Docs:
- README: merge duplicate quickstart, fix test command, fix alignment command, update repo map (14 entries)
- CONTRIBUTING.md: update test command to pytest, add check-alignment step (41 checks), add AGENTS.md note
- docs/roadmap.md: add 12 shipped milestones v0.3.5–v0.6.3, update Up Next to v0.7 candidates

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add a transport abstraction so clients can reach a CHP host over any
backend (HTTP first; Zenoh/gRPC pluggable later):

- chp_core/transport.py: Transport Protocol (async ainvoke_envelope,
  discover, replay_result, health, supports) + LocalTransport (in-process)
  and HttpTransport (stdlib HTTP via RemoteCapabilityHost, run off-loop).
- http.py: RemoteCapabilityHost.invoke_envelope() and .verify(); new
  GET /verify/{correlation_id} route returning the SHA256 chain result.
- Export Transport / LocalTransport / HttpTransport from the package.

Additive; existing surface unchanged. 752 tests green.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant