feat: guest login credentials, stale-key handling, and sign-in link refresh#306
Draft
leggetter wants to merge 10 commits into
Draft
feat: guest login credentials, stale-key handling, and sign-in link refresh#306leggetter wants to merge 10 commits into
leggetter wants to merge 10 commits into
Conversation
Store guest_user_id, attest guest credentials on cli-auth login, and refresh guest sign-in URLs on listen start and via a TUI ticker. Co-authored-by: Cursor <cursoragent@cursor.com>
Add claim_guest, login, and create_new intents with TTY prompt, Cobra flags, and auth_intent on POST /cli-auth. MCP login defaults to claim_guest with guest credentials preserved on stale 401. Co-Authored-By: Claude <noreply@anthropic.com> Co-authored-by: Cursor <cursoragent@cursor.com>
Add guest-tagged acceptance tests and CI matrix slice for auth_intent on POST /cli-auth. Co-Authored-By: Claude <noreply@anthropic.com> Co-authored-by: Cursor <cursoragent@cursor.com>
Guest profiles always claim the Console sandbox on login. Use hookdeck logout then hookdeck login to attach the CLI to an existing Platform account. Remove the TTY three-way prompt. Co-Authored-By: Claude <noreply@anthropic.com> Co-authored-by: Cursor <cursoragent@cursor.com>
Guest profile presence alone selects claim_guest; drop Options and intent flags from the login command surface. Co-Authored-By: Claude <noreply@anthropic.com> Co-authored-by: Cursor <cursoragent@cursor.com>
When guest_url is set, a valid API key no longer short-circuits login. Preserve stale guest key on validate 401 and send guest credentials on POST /cli-auth. Remove auth_intent from StartLogin payload. Co-Authored-By: Claude <noreply@anthropic.com> Co-authored-by: Cursor <cursoragent@cursor.com>
Add unit test for guest profile with valid key reaching signup claim flow. Update guest acceptance test to assert guest_user_id/guest_api_key on POST after validate 401 without auth_intent. Co-Authored-By: Claude <noreply@anthropic.com> Co-authored-by: Cursor <cursoragent@cursor.com>
Cover profile update on success, fallback to saved URL on API error, and no-op when guest profile fields are missing. Co-Authored-By: Claude <noreply@anthropic.com> Co-authored-by: Cursor <cursoragent@cursor.com>
Guard empty link responses, defer refresh to async TUI path, unify persisting refresh through login.RefreshGuestSigninLink, and fix guest API error formatting. Co-authored-by: Cursor <cursoragent@cursor.com>
Redact guest_api_key from PerformRequest debug bodies and Authorization from debug headers. Write hookdeck login --local config as 0600. Co-authored-by: Cursor <cursoragent@cursor.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Companion PR
Coordinate with hookdeck/core #5233 — that PR owns API, Dashboard CliAuth, Console analytics, and L3 journeys. Merge core first, then this PR.
Why we're doing this
Same motivations as core #5233:
hookdeck loginafterlistenclaims and upgrades the same guest sandbox (signupGuest), so the developer keeps their Console work instead of landing on a disconnected account. The CLI sends guest attestation onPOST /cli-auth—guest_user_id+guest_api_keyso the server can prove the caller is that guest — which enables that in-place upgrade. Keeping one PostHogdistinct_idthrough guest → signup is the analytics consequence, not the primary user benefit.listensessions must not show an expired Console sign-in link; refresh the 1h/signin/guest?token=…URL automatically.Measurement note: only Journey A (default claim) gets a clean, linked conversion. Journeys B and C leave the guest sandbox behind; those conversions are not linked to the guest person (see core #5233).
CLI behaviour (no flags — follows CLI profile)
Behaviour is driven by what's stored in the profile after
listen/logout. There is noauth_intentflag and no TTY prompt.POST /cli-authbodyguest_urlset)guest_user_id+guest_api_key(guest attestation)hookdeck logout(guest fields cleared)device_nameonlyCLI Guest Sandbox Abandonedon corePath B note: use this when you already have a Hookdeck Platform (Dashboard) account and want the CLI on that org. Without
hookdeck logoutfirst, the CLI still has guest credentials and the default sends you to signup (path A), not sign-in.Claim path details (A)
StartLoginso the user can complete signup /signupGuest.guest_user_id+guest_api_keyso the server can prove the caller is that guest).Existing Platform account (B)
hookdeck logoutclearsguest_user_id,guest_api_key, andguest_urlfrom the profile.hookdeck loginsends device name only → Dashboard signin URL.Listen guest URL (separate from
hookdeck login)The TUI link to open Console in a browser (
/signin/guest?token=…). This is not thehookdeck loginclaim flow.RefreshGuestSigninLinkon listen start and ~50m TUI tick →POST /cli/guest/signin-link(core endpoint).MCP
hookdeck_loginfollows the same guest vs logged-out rules.Code changes
pkg/login/client_login.go— guest credentials on POST; stale-key handling; logout clears guest fieldspkg/login/guest_link.go— refresh helper + listen integrationpkg/login/guest_link_test.go— refresh success, API error fallback, missing profile no-optest/acceptance/guest_login_acceptance_test.go— guest POST body vs after logoutTest plan
go test ./...go test -tags=guest ./test/acceptance/...— guest profile POST body vs after logoutgo test ./test/acceptance/...— stale validate 401 → browser flow (login_auth_acceptance_test.go)pkg/login/guest_link_test.goDepends on
core #5233:
origin_guest_user_id, guest attestation (guest_user_id+guest_api_keyonPOST /cli-authso the server can prove the caller is that guest),POST /cli/guest/signin-link, CliAuth guest-claim completion.