Skip to content

Sign in to Skillhook Cloud with the browser: cloud login and the agent's setup tool - #26

Merged
JOsacky merged 2 commits into
mainfrom
claude/skillhook-login-ux-80dbb6
Oct 9, 2026
Merged

JOsacky merged 2 commits into
mainfrom
claude/skillhook-login-ux-80dbb6

Conversation

@JOsacky

@JOsacky JOsacky commented Oct 9, 2026

Copy link
Copy Markdown
Member

skillhook cloud login no longer asks for a key copied out of the dashboard. It signs in with the browser, RFC 8628's device flow, the way the Car Image CLI does: it shows a code, opens the cloud's sign-in page, the person approves the code there for an organisation they administer (choosing read, run or admin access), and the cloud hands the waiting CLI a new organisation API key, once. The skillhook-cloud MCP server's skillhook_cloud_setup does the same for an agent, so an agent without a terminal connects the cloud's tools: it opens the person's browser and gets the link and the code to show, never the key.

The cloud side is MeterApp/skillhook-cloud#58 (/api/auth/device/* and /activate); it deploys before a release carries this. Against a cloud without those endpoints, login says to use --key.

What changed

  • src/cloud/login.ts (new): browserLogin starts a sign-in (POST /api/auth/device/code, sending only "skillhook CLI on ", the key's name on the dashboard), reports the page and the code, then polls POST /api/auth/device/token (5 s more after slow_down, doubling up to 30 s while the cloud cannot answer) until the key, a cancel or the ten-minute expiry. It refuses under SKILLHOOK_NO_CLOUD and to plain http, and only opens an https page (loopback http in tests). openBrowser uses open / xdg-open with argv, never a shell, and not over SSH or on Linux without a display.
  • skillhook cloud login: without --key it signs in with the browser; the link and the code go to stderr, so --json still answers on stdout; --no-browser only prints the link; in CI it refuses and points at --key - or the environment. The key the cloud hands over is kept at once (keepApiKey: .env, mode 600, with its cloud), then read back with /api/v1/me for the message. --key shc_…, --key - and a bare --key (asked for at a terminal) keep a key made on the dashboard, as before. The question of which cloud to use when the kept key's and the machine's differ is asked before a sign-in too. CliIO gains openUrl and sleep: the real IO opens the browser, test IOs never do.
  • skillhook mcp --cloud: skillhook_cloud_setup {wait_seconds?} starts the sign-in when it would help (no key, a malformed or refused one; not the kill switch, plain http or an unreachable cloud), returns at once with url, code, browser_opened, expires_in_seconds, and on approval keeps the key and loads the catalogue (tools/list_changed); called again it reports the same sign-in or waits for it, and after a cancelled one starts another. It signs in only to the cloud the key would go to, and says so when SKILLHOOK_CLOUD_API_KEY in its environment would win over a kept key. connectCloud now reports the error's code and status.
  • Messages that sent people to Settings → API keys to make a key first (no key, a refused key, a missing scope, a tool beyond the key) say skillhook cloud login instead. cloudRequest reads error_description from OAuth-style errors.
  • FakeCloud answers /api/auth/device/* from a per-poll script. Docs: docs/cloud.md, docs/mcp.md, docs/security.md, README.md, llms.txt, skills/skillhook-cloud/SKILL.md, AGENTS.md (the outbound requests rule names the sign-in requests), and the changelog under Unreleased. No version bump: nothing is published by this merge.

Verified

  • npm run check on the branch merged with main (0.9.1): typecheck, 331 tests in 46 files, build, schema check, release metadata. New tests: the CLI sign-in (the prompt on stderr, the browser opened once and not with --no-browser, the exact poll waits through pending, slow_down, a 500 and approval, the key kept and never printed, cancel and expiry kept nothing, an older cloud, CI, the kill switch, plain http), and the MCP setup tool (link and code at once, the same sign-in when asked again, approval loads the tools, a cancelled one starts over, an environment key, plain http refused).
  • End to end against a local Skillhook Cloud running MeterApp/skillhook-cloud#58: the built CLI printed the link and the code, approving on /activate logged it in (.env mode 600, the key never printed, skillhook cloud overview worked with it), and Cancel made it exit 1 with "The sign-in was not approved: The sign-in was cancelled in the browser." The built skillhook mcp --cloud, driven over stdio, returned the link and the code from skillhook_cloud_setup without opening a browser (SSH_CONNECTION set); after the approval, wait_seconds returned connected: true, 31 tools loaded and describe_cloud answered with the new key.

🤖 Generated with Claude Code

JOsacky and others added 2 commits October 9, 2026 10:27
…k_cloud_setup

`skillhook cloud login` signs in with RFC 8628's device flow against the cloud's
/api/auth/device endpoints: it shows a code, opens the cloud's sign-in page (not
over SSH, not on Linux without a display, never with --no-browser), polls until a
person approves the code there, and keeps the organisation API key the cloud makes
for this computer and hands over once. `--key shc_…|-` and a bare `--key` (asked
for at a terminal) keep a key made on the dashboard; in CI login asks for those
instead of waiting for a person.

The skillhook-cloud MCP server's skillhook_cloud_setup does the same for an agent:
without a working key it opens the person's browser and returns the link and the
code, keeps the key once they approved and loads the cloud's tools. The agent never
sees the key and cannot pick the cloud; HTTPS and SKILLHOOK_NO_CLOUD are enforced
inside the sign-in itself.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…n-ux-80dbb6

# Conflicts:
#	AGENTS.md
#	CHANGELOG.md
#	llms.txt
@JOsacky
JOsacky enabled auto-merge (squash) October 9, 2026 14:37
@JOsacky
JOsacky merged commit 22a1179 into main Oct 9, 2026
6 checks passed
@JOsacky
JOsacky deleted the claude/skillhook-login-ux-80dbb6 branch October 9, 2026 14:39
@JOsacky JOsacky mentioned this pull request Oct 9, 2026
JOsacky added a commit that referenced this pull request Oct 9, 2026
## What

Version bump to 0.10.0 (`npm run release -- minor`): `package.json`,
`package-lock.json`, the three plugin manifests, and the Unreleased
changelog section moved under `## 0.10.0` (one entry re-wrapped, and it
now says the cloud side is live on https://skillhook.dev). When this
merges, the Release workflow tags `v0.10.0` and dispatches Publish.

`npm run check` passes locally (typecheck, 331 tests in 46 files, build,
schema and release metadata checks).

## Changes since 0.9.1

- `skillhook cloud login` signs in with the browser instead of asking
for a key copied from the dashboard, and the `skillhook-cloud` MCP
server's `skillhook_cloud_setup` does the same for an agent. See #26.

The cloud side (MeterApp/skillhook-cloud#58) is deployed: on
https://skillhook.dev, `POST /api/auth/device/code` answers a code and
`https://skillhook.dev/activate`, the token endpoint answers
`authorization_pending` until approval, and `/activate` sends a
signed-out visitor to sign in first (checked before opening this).

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-authored-by: Claude Opus 5.5 <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