mirror of
https://github.com/supabase/supabase.git
synced 2026-09-22 13:37:53 +08:00
1131e3e2ce
## What kind of change does this PR introduce? Bug fix / design-system alignment for the legacy `Button` from `ui`. ## What is the current behavior? Omitting `variant` on the legacy `Button` falls back to brand-green `primary`. That makes accidental greens easy, and it is hard to spot the real main action on busy pages. ## What is the new behavior? - Legacy `Button` now defaults to neutral `default` - Intentional primary CTAs (create, save, submit, marketing CTAs, and matching `ButtonTooltip` usages) now set `variant="primary"` so their appearance is unchanged - Neutral actions that previously relied on the old fallback (cancel, close, back, dashboard nav, and similar) become grey/white - Design-system docs updated; regression tests cover the new default `Button_Shadcn_` is unchanged. It already uses its own CVA default. This is PR 1 of 2 in a stack. PR 2 drops now-redundant `variant="default"` props. ## To test Studio (http://localhost:8082): - `/sign-in`: Sign in stays green - Open a project → Database → Tables: New table stays green - Auth → Users → Invite: Invite user stays green; Cancel / dismiss controls stay neutral - Project Settings → General: edit a field so Cancel and Save appear. Cancel is neutral, Save is green Design system (http://localhost:3003): - Components → Button: default demo is neutral; primary demo is green; featured preview is the default variant Marketing (optional): - www header: Start your project stays green; logged-in Dashboard is neutral <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit - **Style** - Buttons now default to a neutral style, while primary actions across Studio, documentation, marketing pages, forms, dialogs, and error states use prominent primary styling. - Updated button examples and previews clarify the distinction between default and primary variants. - Event registration now includes a directional arrow icon. - **Tests** - Added coverage confirming default button styling and explicit primary styling behave as expected. - Updated related test fixtures to use primary styling where appropriate. <!-- end of auto-generated comment: release notes by coderabbit.ai -->
103 lines
3.8 KiB
TypeScript
103 lines
3.8 KiB
TypeScript
import { screen } from '@testing-library/react'
|
|
import userEvent from '@testing-library/user-event'
|
|
import { useState } from 'react'
|
|
import { Button } from 'ui'
|
|
import { beforeEach, describe, expect, test, vi } from 'vitest'
|
|
|
|
import {
|
|
CHATGPT_IDENTITY_PROVIDER,
|
|
GITHUB_IDENTITY_PROVIDER,
|
|
type ExternalIdentityProviderConfig,
|
|
} from '@/lib/external-identity-providers'
|
|
import SignUpPage from '@/pages/sign-up'
|
|
import { customRender } from '@/tests/lib/custom-render'
|
|
|
|
const mocks = vi.hoisted(() => ({
|
|
focusProvider: undefined as ExternalIdentityProviderConfig | undefined,
|
|
}))
|
|
|
|
vi.mock('@/components/interfaces/SignIn/SignInWithExternalProvider', () => ({
|
|
SignInWithExternalProvider: ({ provider }: { provider: ExternalIdentityProviderConfig }) => (
|
|
<Button variant="primary">Continue with {provider.displayName}</Button>
|
|
),
|
|
}))
|
|
|
|
vi.mock('@/components/interfaces/SignIn/SignUpForm', () => ({
|
|
SignUpForm: ({ onSuccess }: { onSuccess?: () => void }) => {
|
|
const [isSubmitted, setIsSubmitted] = useState(false)
|
|
|
|
return (
|
|
<>
|
|
<Button
|
|
variant="primary"
|
|
onClick={() => {
|
|
setIsSubmitted(true)
|
|
onSuccess?.()
|
|
}}
|
|
>
|
|
Complete email sign-up
|
|
</Button>
|
|
{isSubmitted && <div>Check your email</div>}
|
|
</>
|
|
)
|
|
},
|
|
}))
|
|
|
|
vi.mock('@/hooks/misc/useEnabledIdentityProviders', () => ({
|
|
useEnabledIdentityProviders: () => [GITHUB_IDENTITY_PROVIDER, CHATGPT_IDENTITY_PROVIDER],
|
|
}))
|
|
|
|
vi.mock('@/hooks/misc/useInboundBranding', () => ({
|
|
useInboundBranding: () => ({ focusProvider: mocks.focusProvider }),
|
|
}))
|
|
|
|
vi.mock('@/hooks/misc/useIsFeatureEnabled', () => ({
|
|
useIsFeatureEnabled: () => ({
|
|
dashboardAuthSignUp: true,
|
|
dashboardAuthSignInWithSso: false,
|
|
dashboardAuthSignInWithEmail: true,
|
|
}),
|
|
}))
|
|
|
|
describe('SignUpPage', () => {
|
|
beforeEach(() => {
|
|
mocks.focusProvider = undefined
|
|
})
|
|
|
|
test('hides social sign-up options after email sign-up succeeds', async () => {
|
|
const user = userEvent.setup()
|
|
customRender(<SignUpPage dehydratedState={undefined} />)
|
|
|
|
expect(screen.getByRole('button', { name: 'Continue with GitHub' })).toBeInTheDocument()
|
|
expect(screen.getByRole('button', { name: 'Continue with ChatGPT' })).toBeInTheDocument()
|
|
expect(screen.getByText('or')).toBeInTheDocument()
|
|
expect(screen.queryByText('Check your email')).not.toBeInTheDocument()
|
|
|
|
await user.click(screen.getByRole('button', { name: 'Complete email sign-up' }))
|
|
|
|
expect(screen.queryByRole('button', { name: 'Continue with GitHub' })).not.toBeInTheDocument()
|
|
expect(screen.queryByRole('button', { name: 'Continue with ChatGPT' })).not.toBeInTheDocument()
|
|
expect(screen.queryByText('or')).not.toBeInTheDocument()
|
|
expect(screen.getByText('Check your email')).toBeInTheDocument()
|
|
expect(screen.getByRole('link', { name: 'Sign in' })).toHaveAttribute('href', '/sign-in')
|
|
})
|
|
|
|
test('hides the focused provider after email sign-up succeeds', async () => {
|
|
const user = userEvent.setup()
|
|
mocks.focusProvider = GITHUB_IDENTITY_PROVIDER
|
|
customRender(<SignUpPage dehydratedState={undefined} />)
|
|
|
|
expect(screen.getByRole('button', { name: 'Continue with GitHub' })).toBeInTheDocument()
|
|
expect(screen.queryByText('Check your email')).not.toBeInTheDocument()
|
|
|
|
await user.click(screen.getByRole('button', { name: 'Show other options' }))
|
|
await user.click(screen.getByRole('button', { name: 'Complete email sign-up' }))
|
|
|
|
expect(screen.queryByRole('button', { name: 'Continue with GitHub' })).not.toBeInTheDocument()
|
|
expect(screen.queryByRole('button', { name: 'Continue with ChatGPT' })).not.toBeInTheDocument()
|
|
expect(screen.queryByText('or')).not.toBeInTheDocument()
|
|
expect(screen.getByText('Check your email')).toBeInTheDocument()
|
|
expect(screen.getByRole('link', { name: 'Sign in' })).toHaveAttribute('href', '/sign-in')
|
|
})
|
|
})
|