feat(KB-136): add sign-in hint when no providers are authenticated

- Show 'Sign in to at least one provider to get started' message when all OAuth providers are unauthenticated
- Provider rows remain visible below the hint for easy sign-in
- Hide hint automatically when at least one provider is authenticated
- Add tests for both hint-visible and hint-hidden states
This commit is contained in:
Dustin Byrne
2026-03-27 20:23:26 -04:00
parent 28bbcb9fdb
commit 74955c8472
2 changed files with 49 additions and 2 deletions

View File

@@ -457,7 +457,13 @@ export function SettingsModal({ onClose, addToast, initialSection }: SettingsMod
No OAuth providers available
</div>
) : (
authProviders.map((provider) => (
<>
{!authProviders.some(p => p.authenticated) && (
<div className="settings-empty-state settings-muted">
Sign in to at least one provider to get started.
</div>
)}
{authProviders.map((provider) => (
<div key={provider.id} className="auth-provider-row">
<div className="auth-provider-info">
<strong>{provider.name}</strong>
@@ -490,7 +496,8 @@ export function SettingsModal({ onClose, addToast, initialSection }: SettingsMod
)}
</div>
</div>
))
))}
</>
)}
<small className="auth-hint">
Login and logout take effect immediately no need to save.

View File

@@ -523,4 +523,44 @@ describe("SettingsModal", () => {
// Authentication content should NOT be visible
expect(screen.queryByText("✗ Not authenticated")).toBeNull();
});
it("shows sign-in hint when no providers are authenticated", async () => {
(fetchAuthStatus as ReturnType<typeof vi.fn>).mockResolvedValueOnce({
providers: [
{ id: "anthropic", name: "Anthropic", authenticated: false },
{ id: "github", name: "GitHub", authenticated: false },
],
});
render(<SettingsModal onClose={onClose} addToast={addToast} />);
await waitFor(() => expect(fetchSettings).toHaveBeenCalled());
fireEvent.click(screen.getByText("Authentication"));
await waitFor(() => expect(fetchAuthStatus).toHaveBeenCalled());
expect(screen.getByText("Sign in to at least one provider to get started.")).toBeTruthy();
// Provider rows should still be visible
expect(screen.getByText("Anthropic")).toBeTruthy();
expect(screen.getByText("GitHub")).toBeTruthy();
});
it("hides sign-in hint when at least one provider is authenticated", async () => {
(fetchAuthStatus as ReturnType<typeof vi.fn>).mockResolvedValueOnce({
providers: [
{ id: "anthropic", name: "Anthropic", authenticated: true },
{ id: "github", name: "GitHub", authenticated: false },
],
});
render(<SettingsModal onClose={onClose} addToast={addToast} />);
await waitFor(() => expect(fetchSettings).toHaveBeenCalled());
fireEvent.click(screen.getByText("Authentication"));
await waitFor(() => expect(fetchAuthStatus).toHaveBeenCalled());
expect(screen.queryByText("Sign in to at least one provider to get started.")).toBeNull();
// Provider rows should still be visible
expect(screen.getByText("Anthropic")).toBeTruthy();
expect(screen.getByText("GitHub")).toBeTruthy();
});
});