Skip to content

Move the hosted MCP handshake to AWS - #93

Merged
thetangstr merged 12 commits into
mainfrom
codex/aws-migration
Aug 8, 2026
Merged

Move the hosted MCP handshake to AWS#93
thetangstr merged 12 commits into
mainfrom
codex/aws-migration

Conversation

@thetangstr

Copy link
Copy Markdown
Owner

Summary

  • add the non-custodial bilateral party handshake tools and durable coordinator state
  • provision the locked EC2 + Docker Compose + Caddy + SSM deployment target
  • preserve legacy MCP behavior while adding migration parity, health, and rollback assets

Verification

  • full root npm test across workspaces and infrastructure
  • live AWS health and 36-tool discovery
  • G3 native MCP handshake: AUTHORIZED, paymentMoved:false
  • P4 two-stranger run through the hosted coordinator

Deployment note

Source remains fail-closed for validator cardinality. Production enables the explicit degraded-mode override for the current testnet.

Create a guarded one-host AWS provisioner and bootstrap asset so B2 can be replayed without hidden manual steps.

Constraint: AWS account 570035913370 in us-west-2; default VPC public subnet; key name clockchain-mcp; SSH limited to executor public /32.

Rejected: broad infrastructure framework or reusable module | the task needs one cautious reproducible host provisioner with small repo impact.

Confidence: high

Scope-risk: narrow

Directive: Refuse partial pre-existing B2 resources instead of guessing whether to adopt or mutate them.

Tested: bash -n infra/scripts/provision-clockchain-mcp-host.sh infra/scripts/clockchain-mcp-user-data.sh; provisioned EC2/EIP/IAM/SG/SSM resources in AWS; SSH verified cloud-init, Docker hello-world, instance-role SSM read, no /home/ubuntu/.aws; npm test.

Not-tested: Application deployment on the host; B3 service/runtime wiring.
Wrap AWS CLI with a disposable HOME and prove the instance-role SSM path during bootstrap so B2 leaves no ~/.aws cache behind.

Constraint: B2 requires the literal aws command to work through the EC2 role while /home/ubuntu/.aws remains absent.

Rejected: AWS_CONFIG_FILE and AWS_SHARED_CREDENTIALS_FILE redirects | AWS CLI v2 still writes cli/cache/session.db beneath HOME.

Confidence: high

Scope-risk: narrow

Directive: Keep runtime AWS CLI calls behind the disposable-HOME wrapper; do not add static instance credentials.

Tested: bash syntax and diff checks; fake CLI cache/exit-status probe; live instance-role PING read with pre/post ~/.aws assertions.

Not-tested: Replacement instance bootstrap from a newly provisioned AMI.
The side-by-side stack now fetches SSM secrets without residue, waits for a real MCP healthcheck, and preserves the locked TLS and rate-limit cutover behavior.

Constraint: One EC2 host, Docker Compose, Caddy, and SSM Parameter Store are fixed by the execution plan.

Rejected: Detached startup without health gating | systemd could report success while MCP was crash-looping.

Confidence: high

Scope-risk: moderate

Directive: Keep production TLS on-demand until its DNS record flips; never expose MCP port 8080 on the host.

Tested: root npm test; npm run build; infra 7/7; bash syntax; Compose config; resolved healthcheck execution; Caddy validation.

Not-tested: Public test-host TLS awaits the mcp-aws DNS record.
The parity gate now compares bounded health, quota, timestamp, immutable block, and bidirectional ledger semantics before DNS cutover.

Constraint: Ambiguous ledger writes must never be retried automatically.

Rejected: Shape-only parity | Shape-compatible endpoints can still serve different chain data or security limits.

Confidence: high

Scope-risk: moderate

Directive: Run this gate only with an intentional known block and disposable parity action reference.

Tested: parity 17/17; MCP 148/148; npm run build; full npm test.

Not-tested: Live AWS endpoint awaits mcp-aws DNS and B3 deployment.
…or risk

Constraint: Validator count is explicitly non-blocking for this migration parity run.
Rejected: Weakening parity writes by default | production safety must remain fail-closed.
Confidence: high
Scope-risk: narrow
Directive: Use --allow-degraded true only for an explicit operator-approved parity run.
Tested: focused parity tests 18/18; MCP package tests 149/149; npm test; npm run build; git diff --check
Not-tested: live chain parity pending this commit
Constraint: After the DNS flip both MCP hostnames reach one process keyed by client IP.
Rejected: Reusing independent-backend quota deltas | four requests against one bucket move in paired increments.
Confidence: high
Scope-risk: narrow
Directive: Use --shared-backend true only after proving both names resolve to the same service.
Tested: focused parity tests 21/21; MCP package tests 152/152; npm test; npm run build; git diff --check
Not-tested: live post-cutover parity pending this commit
Constraint: P2 AWS deploy-assets slice limited to external host compose, wrapper secret materialization, and SSM IAM scope in owned infra files only.

Rejected: Exposing host ports or exporting host secrets into compose env | the host contract requires no network ingress and file-backed secrets.

Confidence: high

Scope-risk: narrow

Directive: Keep host SecureStrings file-backed under /clockchain/host/* and avoid widening the EC2 SSM resource policy beyond explicit prefixes.

Tested: node --test infra/test/deploy-assets.test.mjs; npm test; npm run build; bash -n infra/clockchain-mcp/compose-up.sh; bash -n infra/scripts/provision-clockchain-mcp-host.sh; git diff --check

Not-tested: Live AWS provisioning or production docker compose deployment.
The systemd unit runs without sudo's SUDO_UID compatibility hint, so Git must trust only the exact handshake checkout for each validation command.

Constraint: The handshake checkout stays owned by the unprivileged deploy user while the compose wrapper runs as root.

Rejected: A persistent system-wide safe.directory entry | it adds mutable host configuration outside the reviewed deploy assets.

Confidence: high

Scope-risk: narrow

Directive: Keep safe.directory scoped to HANDSHAKE_APP_ROOT and preserve the clean-checkout SHA guard.

Tested: node --test infra/test/deploy-assets.test.mjs; npm test; npm run build; bash -n infra/clockchain-mcp/compose-up.sh; git diff --check; live systemd-shaped Git reproduction on i-0d6765d143da7e1ea.

Not-tested: None for this compatibility fix.
Canonical protocol validation, signed relay envelopes, durable principal-scoped state, and read-only EVM verification form the reusable base for MCP orchestration.

Constraint: Party keys must remain client-side and relay messages are untrusted coordination data.

Rejected: Trusting relay order or persisting party key material | both violate the bilateral authorization boundary.

Confidence: high

Scope-risk: moderate

Directive: Preserve exact canonical wire shapes, bounded RPC reads, and fail-closed replay checks.

Tested: MCP package suite passed 236/236; primitive protocol, relay, state, and EVM suites included.

Not-tested: Live relay and public EVM behavior are deferred to G3.
Five MCP tools now drive both public roles through signed relay artifacts, verified Clockchain anchors, evidence upload, and certificate retrieval while state stays isolated by the resolved caller principal.

Constraint: P3 permits only caller-produced EIP-191 signatures; no party key may touch the server.

Rejected: Server-side wallet custody or relay-trusted state transitions | both would erase the intended authority boundary.

Confidence: high

Scope-risk: broad

Directive: Keep the five-tool schema keyless, derive principals from the resolved auth branch, and preserve artifact/descriptor cross-bindings.

Tested: MCP package suite passed 236/236; full payer and requestor coordinator flows, retry recovery, degraded override, and certificate checks passed; independent review PASS.

Not-tested: Public MCP-to-relay-to-Clockchain G3 remains a live post-deploy gate.
The EC2 compose contract now mounts a named state volume and threads relay, EVM RPC, and explicit degraded-mode configuration through the existing SSM-backed launcher.

Constraint: Production may tolerate low validator participation, but source defaults must remain fail-closed.

Rejected: Ephemeral container state or a source-level degraded default | either loses sessions or weakens every deployment.

Confidence: high

Scope-risk: moderate

Directive: Enable degraded mode only through an operator-scoped runtime override and keep MCP state on the named volume.

Tested: Full monorepo npm test passed; deployment asset suite passed 17/17 including resolved compose and wrapper failure paths.

Not-tested: EC2 volume creation and systemd override are verified during the live deployment step.
Constraint: Docker Compose versions render bind metadata as either an empty object or create_host_path metadata.

Rejected: Exact resolved JSON deep equality for the bind mount | it made CI version-sensitive without proving deployment safety.

Confidence: high

Scope-risk: narrow

Directive: Assert deployment contracts semantically when Compose injects version-owned metadata.

Tested: node --test infra/test/deploy-assets.test.mjs; npm test

Not-tested: GitHub Actions rerun on both Node matrix jobs.
@thetangstr
thetangstr merged commit d016ad6 into main Aug 8, 2026
2 checks passed
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