Skip to content

The sandbox demo client can now reach ateapi - #2468

Open
Ziyi Tan (Ziy1-Tan) wants to merge 1 commit into
agent-substrate:mainfrom
Ziy1-Tan:sandbox-client-auth
Open

Ziyi Tan (Ziy1-Tan) wants to merge 1 commit into
agent-substrate:mainfrom
Ziy1-Tan:sandbox-client-auth

Conversation

@Ziy1-Tan

@Ziy1-Tan Ziyi Tan (Ziy1-Tan) commented Oct 11, 2026 •

Copy link
Copy Markdown

ateapi requires mTLS or a JWT bearer token, and an out-of-cluster client has
neither. The sandbox client dialed the gRPC endpoint with plain TLS and no
credentials, so ResumeActor failed with missing bearer token and the README's
walkthrough could not be run as written.

 demos/sandbox/client
   newAteClient
-    dialAteAPI(endpoint)
-      grpc.NewClient(plain TLS, InsecureSkipVerify)
+    ateclient.NewClient(ctx, "", "", endpoint, "", false)
-  ResumeActor
   REPL → POST router /process
   on exit → SuspendActor

demos/claude-code-multiplex/ui names this client as the pattern it follows, and
dials the same endpoint through internal/ateclient:

cli, err := ateclient.NewClient(context.Background(), "", "", ateapiAddr, "", false)

After this change both demos connect identically: one auto port-forward to
svc/api when no endpoint is given, one minted ate-client ServiceAccount
token, one verification of ateapi's serving cert against the live
ClusterTrustBundle, and the same endpoint-override escape hatch (--ateapi
here, ATEAPI_ADDR there).

ResumeActor is dropped as well. A request through the router wakes a suspended
actor on its own, so the call was redundant and it was the first thing to fail.
Suspend-on-exit stays: multiplex does not drive actors at all, reading worker and
actor state and pod logs, so it has no equivalent to align on, while this client
drives them through the router and its README documents the exit-suspends
transition.

Breaking change

--ateapi now defaults to empty, meaning auto port-forward to svc/api, instead
of localhost:8080. A caller that omitted the flag and relied on its own
port-forward now reaches svc/api instead. The client also needs a kube context
with access to the ate-system namespace, which it did not before. Passing
--ateapi=localhost:8080 explicitly, as the README did, still works.

Verified against a demo-sandbox-microvm atespace, because a gVisor sandbox
cannot start on the test host. The client binary came from this branch; the
atespace did not.

Connecting to ateapi (endpoint=""; empty = auto port-forward to svc/api)...
sandbox> pwd            → /
sandbox> ls -la /tmp    → ...
sandbox> cat /tmp/b.txt → Hello
Suspending actor my-sandbox-1...
Actor suspended successfully.
  • Tests pass: no automated test. demos/sandbox/client is a main package
    that drives HTTP from stdin and had none before this change either.
  • Appropriate changes to documentation are included in the PR:
    demos/sandbox/README.md drops the API port-forward step and lists the kube
    context as a prerequisite.

@Ziy1-Tan
Ziyi Tan (Ziy1-Tan) force-pushed the sandbox-client-auth branch 2 times, most recently from 0241fa0 to 1645497 Compare October 11, 2026 14:52
@Ziy1-Tan Ziyi Tan (Ziy1-Tan) changed the title sandbox client: authenticate to ateapi instead of dialing it raw The sandbox demo client can now reach ateapi Oct 11, 2026
ateapi requires mTLS or a JWT bearer token, and an out-of-cluster client has
neither. The client dialed the gRPC endpoint with plain TLS and no credentials,
so ResumeActor failed with "missing bearer token" and the README's walkthrough
could not be run as written.

Use internal/ateclient, the path kubectl-ate and the claude-code-multiplex UI
already take: it port-forwards svc/api when no endpoint is given, verifies
ateapi's serving cert against the live ClusterTrustBundle, and mints an
ate-client ServiceAccount token from the kube context. The --ateapi flag now
defaults to empty and targets an endpoint the caller forwarded themselves.

Drop the explicit ResumeActor call too. A request through the router wakes a
suspended actor on its own, so the call was redundant, and it was the first
thing to fail. Suspend-on-exit stays: multiplex does not drive actors at all,
while this client drives them through the router and the README documents the
exit-suspends transition.
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