Skip to content

fix: print auth URL and prompt for token when browser open fails#162

Merged
greynewell merged 2 commits intomainfrom
fix/headless-auth-fallback
Apr 30, 2026
Merged

fix: print auth URL and prompt for token when browser open fails#162
greynewell merged 2 commits intomainfrom
fix/headless-auth-fallback

Conversation

@greynewell
Copy link
Copy Markdown
Contributor

@greynewell greynewell commented Apr 30, 2026

Closes #155.

In headless/SSH/container environments, the browser-based OAuth flow fails silently, leaving users stuck. Fix: detect browser open failure and fall back to printing the CLI auth URL and prompting the user to paste their API key.

TDD: failing test first.

🤖 Generated with Claude Code

Summary by CodeRabbit

  • Tests
    • Added validation tests for install script content to ensure proper user guidance and no unintended setup wizard invocations.
    • Added tests for npm package postinstall behavior to verify getting-started instructions are displayed.
    • Added test coverage for authentication fallback when browser integration is unavailable.

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Apr 30, 2026

Warning

Rate limit exceeded

@greynewell has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 3 minutes and 32 seconds before requesting another review.

To keep reviews running without waiting, you can enable usage-based add-on for your organization. This allows additional reviews beyond the hourly cap. Account admins can enable it under billing.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: a1cf2613-4120-4caa-98c9-dd1f8d924d25

📥 Commits

Reviewing files that changed from the base of the PR and between dfe53bc and 17500d3.

📒 Files selected for processing (2)
  • internal/auth/handler.go
  • internal/auth/handler_test.go

Walkthrough

Three new test files validate that installation scripts provide proper user guidance and that authentication gracefully falls back to manual token entry when browser opening fails in headless environments.

Changes

Cohort / File(s) Summary
Installation Script Validation
cmd/install_script_test.go, cmd/npm_package_test.go
New tests verify that shell/JavaScript install scripts don't auto-invoke the setup wizard and contain user guidance directing to run supermodel or providing "get started" messaging.
Authentication Fallback Handling
internal/auth/handler_test.go
New test validates the Login function gracefully handles browser-open failures by printing the auth URL, prompting for manual API key entry via stdin, and persisting the key to config.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~12 minutes

Poem

🌙 In headless dark where browsers cannot roam,
Our auth now whispers: "Here's your manual home"
Tests stand as sentinels, ensuring the way,
When tech fails gracefully, users save the day 🔑

🚥 Pre-merge checks | ✅ 3 | ❌ 2

❌ Failed checks (1 warning, 1 inconclusive)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 50.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Description check ❓ Inconclusive The description covers the problem context and references the linked issue #155, but is missing the Test plan section with the checkboxes specified in the template. Add the Test plan section with checkboxes for 'make test', 'make lint', and describe manual testing steps performed.
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately summarizes the main change: implementing a fallback to print auth URL and prompt for token when browser open fails, which is the core fix addressing issue #155.
Linked Issues check ✅ Passed The code changes add tests validating the fallback behavior (no setup wizard invocation, presence of auth URL prompt in install scripts) and implement the core auth fallback logic when browser open fails [#155].
Out of Scope Changes check ✅ Passed All changes are directly scoped to addressing the browser auth failure issue: new tests for install scripts and auth handler validate the expected fallback behavior, with no unrelated modifications.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch fix/headless-auth-fallback

Review rate limit: 0/5 reviews remaining, refill in 3 minutes and 32 seconds.

Comment @coderabbitai help to get the list of available commands and usage tips.

greynewell and others added 2 commits April 30, 2026 10:37
…ronments

When the browser cannot be opened (headless/SSH/container environments),
Login now prints the CLI auth URL (with port and state) so the user can
visit it from another machine, then prompts them to paste their API key.

Three package-level vars make the behaviour testable without exec or os
coupling: openBrowserFunc, stdinReader, and loginOut.

Closes #155.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@greynewell greynewell force-pushed the fix/headless-auth-fallback branch from 7444247 to 17500d3 Compare April 30, 2026 14:37
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@cmd/install_script_test.go`:
- Around line 16-29: The test expects install.sh to NOT run the setup subcommand
and to include a getting-started message; update install.sh to match this by
removing or guarding the literal invocation of "$INSTALL_DIR/$BINARY" setup (the
current invocation that runs setup) and instead print a clear getting-started
message that includes either "Run 'supermodel'" or the phrase "get started" (so
the test's checks in the t.Run blocks for absence of `" setup"`/`"supermodel
setup"` and presence of "run 'supermodel'" or "get started" pass). Ensure the
printed message appears during install and that no direct call to the setup
subcommand is executed.

In `@cmd/npm_package_test.go`:
- Around line 27-33: The test t.Run("includes getting-started message") expects
npm/install.js to print a getting-started message containing either "run
'supermodel'" or "get started"; update npm/install.js (the script that logs
download/install status around the current block near Lines 110-128) to append a
concise post-install message that includes one of those exact phrases (e.g.,
"Get started: run 'supermodel' in your project directory") so the contains
checks in the test (hasRunSupermodel / hasGetStarted) pass. Ensure the message
is emitted to the same output stream inspected by the test.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: cab95002-5897-4eee-860e-ef7d3d2af91c

📥 Commits

Reviewing files that changed from the base of the PR and between 037157d and dfe53bc.

📒 Files selected for processing (3)
  • cmd/install_script_test.go
  • cmd/npm_package_test.go
  • internal/auth/handler_test.go

Comment thread cmd/install_script_test.go Outdated
Comment on lines +16 to +29
t.Run("does not run setup wizard at install time", func(t *testing.T) {
// The script uses $BINARY variable, so match the literal subcommand argument
if strings.Contains(content, `" setup`) || strings.Contains(content, "supermodel setup") {
t.Error("install.sh must not run the setup subcommand at install time — the wizard now auto-launches from bare 'supermodel' in a project directory (PR #152)")
}
})

t.Run("includes getting-started message", func(t *testing.T) {
lower := strings.ToLower(content)
hasRunSupermodel := strings.Contains(lower, "run 'supermodel'") || strings.Contains(lower, "run \"supermodel\"")
hasGetStarted := strings.Contains(lower, "get started")
if !hasRunSupermodel && !hasGetStarted {
t.Error("install.sh must include a getting-started message directing users to run 'supermodel' in their project directory")
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Test contradicts current install.sh behavior

Line 16-Line 20 expects no setup invocation, but install.sh currently invokes setup ("$INSTALL_DIR/$BINARY" setup around Line 81 in that file). Line 23-Line 29 also expects a getting-started message that isn’t currently present. This test will fail unless install.sh is updated accordingly.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@cmd/install_script_test.go` around lines 16 - 29, The test expects install.sh
to NOT run the setup subcommand and to include a getting-started message; update
install.sh to match this by removing or guarding the literal invocation of
"$INSTALL_DIR/$BINARY" setup (the current invocation that runs setup) and
instead print a clear getting-started message that includes either "Run
'supermodel'" or the phrase "get started" (so the test's checks in the t.Run
blocks for absence of `" setup"`/`"supermodel setup"` and presence of "run
'supermodel'" or "get started" pass). Ensure the printed message appears during
install and that no direct call to the setup subcommand is executed.

Comment thread cmd/npm_package_test.go Outdated
Comment on lines +27 to +33
t.Run("includes getting-started message", func(t *testing.T) {
lower := strings.ToLower(content)
hasRunSupermodel := strings.Contains(lower, "run 'supermodel'") || strings.Contains(lower, `run "supermodel"`)
hasGetStarted := strings.Contains(lower, "get started")
if !hasRunSupermodel && !hasGetStarted {
t.Error("npm/install.js must print a getting-started message directing users to run 'supermodel' in their project directory")
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Expectation doesn’t match current npm installer output

Line 27-Line 33 require "run 'supermodel'" or "get started" in npm/install.js, but current installer output (see npm/install.js around Lines 110-128) only logs download/install status. This test will fail unless the script is updated in the same PR.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@cmd/npm_package_test.go` around lines 27 - 33, The test t.Run("includes
getting-started message") expects npm/install.js to print a getting-started
message containing either "run 'supermodel'" or "get started"; update
npm/install.js (the script that logs download/install status around the current
block near Lines 110-128) to append a concise post-install message that includes
one of those exact phrases (e.g., "Get started: run 'supermodel' in your project
directory") so the contains checks in the test (hasRunSupermodel /
hasGetStarted) pass. Ensure the message is emitted to the same output stream
inspected by the test.

@greynewell greynewell marked this pull request as ready for review April 30, 2026 14:39
@greynewell greynewell merged commit ecb93fc into main Apr 30, 2026
7 checks passed
@greynewell greynewell deleted the fix/headless-auth-fallback branch April 30, 2026 14:39
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.

bug: browser-based auth fails silently in headless/SSH environments during first-run wizard

1 participant