diff --git a/src/App.test.tsx b/src/App.test.tsx index 091597addd..7955527432 100644 --- a/src/App.test.tsx +++ b/src/App.test.tsx @@ -177,55 +177,52 @@ describe('App', () => { server.use( http.get('/internal/user', (info) => { if (hasSession) { - return HttpResponse.json(internalUser, { status: 200 }) + return HttpResponse.json(internalUser) } else { - return HttpResponse.json({}, { status: 200 }) + return HttpResponse.json({}) } }), http.get('/internal/users/current', (info) => { - return HttpResponse.json({}, { status: 200 }) + return HttpResponse.json({}) }), graphql.query('DetailOwner', (info) => - HttpResponse.json({ data: { owner: 'codecov' } }, { status: 200 }) + HttpResponse.json({ data: { owner: 'codecov' } }) ), graphql.query('CurrentUser', (info) => { if (hasLoggedInUser) { - return HttpResponse.json({ data: user }, { status: 200 }) + return HttpResponse.json({ data: user }) } - HttpResponse.json({ data: {} }, { status: 200 }) + HttpResponse.json({ data: {} }) }), graphql.query('GetPlanData', (info) => { - return HttpResponse.json({ data: {} }, { status: 200 }) + return HttpResponse.json({ data: {} }) }), graphql.query('OwnerTier', (info) => { - return HttpResponse.json({ data: {} }, { status: 200 }) + return HttpResponse.json({ data: {} }) }), graphql.query('Seats', (info) => { - return HttpResponse.json({ data: {} }, { status: 200 }) + return HttpResponse.json({ data: {} }) }), graphql.query('HasAdmins', (info) => { - return HttpResponse.json({ data: {} }, { status: 200 }) + return HttpResponse.json({ data: {} }) }), graphql.query('owner', (info) => { - return HttpResponse.json( - { data: { owner: { isAdmin: true } } }, - { status: 200 } - ) + return HttpResponse.json({ data: { owner: { isAdmin: true } } }) }), graphql.query('MyContexts', (info) => { - return HttpResponse.json({ data: {} }, { status: 200 }) + return HttpResponse.json({ data: {} }) }), graphql.query('GetOktaConfig', (info) => { - return HttpResponse.json({ data: {} }, { status: 200 }) + return HttpResponse.json({ data: {} }) }), graphql.query('OwnerPageData', (info) => { - return HttpResponse.json({ data: {} }, { status: 200 }) + return HttpResponse.json({ data: {} }) }), graphql.mutation('updateDefaultOrganization', (info) => { - return HttpResponse.json({ data: {} }, { status: 200 }) + return HttpResponse.json({ data: {} }) }), graphql.query('GetRepoOverview', (info) => { - return HttpResponse.json({ data: mockRepoOverview }, { status: 200 }) + return HttpResponse.json({ data: mockRepoOverview }) }) ) } diff --git a/src/layouts/BaseLayout/BaseLayout.spec.tsx b/src/layouts/BaseLayout/BaseLayout.test.tsx similarity index 87% rename from src/layouts/BaseLayout/BaseLayout.spec.tsx rename to src/layouts/BaseLayout/BaseLayout.test.tsx index 2f115316d2..5512aadf13 100644 --- a/src/layouts/BaseLayout/BaseLayout.spec.tsx +++ b/src/layouts/BaseLayout/BaseLayout.test.tsx @@ -1,8 +1,9 @@ import { QueryClient, QueryClientProvider } from '@tanstack/react-query' -import { render, screen, waitFor } from '@testing-library/react' -import { graphql, rest } from 'msw' -import { setupServer } from 'msw/node' +import { cleanup, render, screen, waitFor } from '@testing-library/react' +import { graphql, http, HttpResponse } from 'msw2' +import { setupServer } from 'msw2/node' import { MemoryRouter, Route, useLocation } from 'react-router-dom' +import { type Mock } from 'vitest' import config from 'config' @@ -12,16 +13,24 @@ import { useInternalUser, useUser } from 'services/user' import BaseLayout from './BaseLayout' -jest.mock('services/image') -const mockedUseImage = useImage as jest.Mock -jest.mock('services/impersonate') -const mockedUseImpersonate = useImpersonate as jest.Mock -jest.mock('shared/GlobalTopBanners', () => () => 'GlobalTopBanners') -jest.mock('./InstallationHelpBanner', () => () => 'InstallationHelpBanner') -jest.mock('pages/TermsOfService', () => () => 'TermsOfService') -jest.mock('pages/DefaultOrgSelector', () => () => 'DefaultOrgSelector') -jest.mock('layouts/Header', () => () => 'Header') -jest.mock('layouts/Footer', () => () => 'Footer') +vi.mock('services/image') +const mockedUseImage = useImage as Mock + +vi.mock('services/impersonate') +const mockedUseImpersonate = useImpersonate as Mock + +vi.mock('shared/GlobalTopBanners', () => ({ + default: () => 'GlobalTopBanners', +})) +vi.mock('./InstallationHelpBanner', () => ({ + default: () => 'InstallationHelpBanner', +})) +vi.mock('pages/TermsOfService', () => ({ default: () => 'TermsOfService' })) +vi.mock('pages/DefaultOrgSelector', () => ({ + default: () => 'DefaultOrgSelector', +})) +vi.mock('layouts/Header', () => ({ default: () => 'Header' })) +vi.mock('layouts/Footer', () => ({ default: () => 'Footer' })) const mockOwner = { owner: { @@ -183,7 +192,8 @@ beforeAll(() => { afterEach(() => { queryClient.clear() server.resetHandlers() - jest.resetAllMocks() + vi.clearAllMocks() + cleanup() }) afterAll(() => { @@ -212,32 +222,31 @@ describe('BaseLayout', () => { mockedUseImpersonate.mockReturnValue({ isImpersonating }) server.use( - rest.get('/internal/user', (req, res, ctx) => { - return res(ctx.status(200), ctx.json(internalUser)) + http.get('/internal/user', (info) => { + return HttpResponse.json(internalUser) + }), + graphql.query('CurrentUser', (info) => { + return HttpResponse.json({ data: currentUser }) + }), + graphql.query('DetailOwner', (info) => { + return HttpResponse.json({ data: mockOwner }) + }), + http.get('/internal/:provider/:owner/account-details', (info) => { + return HttpResponse.json({}) }), - graphql.query('CurrentUser', (_, res, ctx) => - res(ctx.status(200), ctx.data(currentUser)) - ), - graphql.query('DetailOwner', (_, res, ctx) => - res(ctx.status(200), ctx.data(mockOwner)) - ), - rest.get('/internal/:provider/:owner/account-details', (_, res, ctx) => - res(ctx.status(200), ctx.json({})) - ), // Self hosted only - graphql.query('HasAdmins', (_, res, ctx) => - res(ctx.status(200), ctx.data({})) - ), - graphql.query('Seats', (_, res, ctx) => - res(ctx.status(200), ctx.data({})) - ), - graphql.query('TermsOfService', (_, res, ctx) => - res(ctx.status(200), ctx.data({})) - ), - graphql.query('UseMyOrganizations', (_, res, ctx) => - res( - ctx.status(200), - ctx.data({ + graphql.query('HasAdmins', (info) => { + return HttpResponse.json({ data: {} }) + }), + graphql.query('Seats', (info) => { + return HttpResponse.json({ data: {} }) + }), + graphql.query('TermsOfService', (info) => { + return HttpResponse.json({ data: {} }) + }), + graphql.query('UseMyOrganizations', (info) => { + return HttpResponse.json({ + data: { myOrganizationsData: { me: { myOrganizations: { @@ -246,15 +255,15 @@ describe('BaseLayout', () => { }, }, }, - }) - ) - ), - graphql.mutation('updateDefaultOrganization', (req, res, ctx) => - res(ctx.status(200), ctx.data({})) - ), - rest.get('/internal/users/current', (_, res, ctx) => - res(ctx.status(200), ctx.json({})) - ) + }, + }) + }), + graphql.mutation('updateDefaultOrganization', (info) => { + return HttpResponse.json({ data: {} }) + }), + http.get('/internal/users/current', (info) => { + return HttpResponse.json({}) + }) ) } diff --git a/src/layouts/BaseLayout/InstallationHelpBanner/InstallationHelpBanner.spec.jsx b/src/layouts/BaseLayout/InstallationHelpBanner/InstallationHelpBanner.test.jsx similarity index 80% rename from src/layouts/BaseLayout/InstallationHelpBanner/InstallationHelpBanner.spec.jsx rename to src/layouts/BaseLayout/InstallationHelpBanner/InstallationHelpBanner.test.jsx index 5f1d817fdc..6a559cbe6d 100644 --- a/src/layouts/BaseLayout/InstallationHelpBanner/InstallationHelpBanner.spec.jsx +++ b/src/layouts/BaseLayout/InstallationHelpBanner/InstallationHelpBanner.test.jsx @@ -1,9 +1,10 @@ import { QueryClient, QueryClientProvider } from '@tanstack/react-query' -import { render, screen, waitFor } from '@testing-library/react' +import { cleanup, render, screen, waitFor } from '@testing-library/react' import userEvent from '@testing-library/user-event' -import { graphql } from 'msw' -import { setupServer } from 'msw/node' +import { graphql, HttpResponse } from 'msw2' +import { setupServer } from 'msw2/node' import { MemoryRouter, Route, Switch } from 'react-router-dom' +import { vi } from 'vitest' import InstallationHelpBanner from './InstallationHelpBanner' @@ -16,10 +17,13 @@ const server = setupServer() beforeAll(() => { server.listen() }) + beforeEach(() => { + cleanup() queryClient.clear() server.resetHandlers() }) + afterAll(() => { server.close() }) @@ -40,35 +44,33 @@ const wrapper = describe('InstallationHelpBanner', () => { function setup() { - const mutation = jest.fn() + const mutation = vi.fn() - const mockSetItem = jest.spyOn(window.localStorage.__proto__, 'setItem') - const mockGetItem = jest.spyOn(window.localStorage.__proto__, 'getItem') + const mockSetItem = vi.spyOn(window.localStorage.__proto__, 'setItem') + const mockGetItem = vi.spyOn(window.localStorage.__proto__, 'getItem') server.use( - graphql.query('IsSyncing', (req, res, ctx) => { - return res( - ctx.status(200), - ctx.data({ + graphql.query('IsSyncing', (info) => { + return HttpResponse.json({ + data: { me: { isSyncing: false, }, - }) - ) + }, + }) }), - graphql.mutation('SyncData', (req, res, ctx) => { - mutation(req.variables) + graphql.mutation('SyncData', (info) => { + mutation(info.variables) - return res( - ctx.status(200), - ctx.data({ + return HttpResponse.json({ + data: { syncWithGitProvider: { me: { isSyncing: true, }, }, - }) - ) + }, + }) }) ) @@ -146,9 +148,9 @@ describe('InstallationHelpBanner', () => { wrapper: wrapper(), }) - const dismissButton = await screen.findByRole('button', { - name: 'x.svg', - }) + const dismissButton = await screen.findByTestId( + 'dismiss-install-help-banner' + ) expect(dismissButton).toBeInTheDocument() }) @@ -161,9 +163,9 @@ describe('InstallationHelpBanner', () => { wrapper: wrapper(), }) - const dismissButton = await screen.findByRole('button', { - name: 'x.svg', - }) + const dismissButton = await screen.findByTestId( + 'dismiss-install-help-banner' + ) expect(dismissButton).toBeInTheDocument() await user.click(dismissButton) @@ -184,9 +186,9 @@ describe('InstallationHelpBanner', () => { wrapper: wrapper(), }) - const dismissButton = await screen.findByRole('button', { - name: 'x.svg', - }) + const dismissButton = await screen.findByTestId( + 'dismiss-install-help-banner' + ) expect(dismissButton).toBeInTheDocument() await user.click(dismissButton) diff --git a/src/layouts/BaseLayout/InstallationHelpBanner/index.js b/src/layouts/BaseLayout/InstallationHelpBanner/index.ts similarity index 100% rename from src/layouts/BaseLayout/InstallationHelpBanner/index.js rename to src/layouts/BaseLayout/InstallationHelpBanner/index.ts diff --git a/src/layouts/BaseLayout/hooks/useUserAccessGate.spec.tsx b/src/layouts/BaseLayout/hooks/useUserAccessGate.test.tsx similarity index 96% rename from src/layouts/BaseLayout/hooks/useUserAccessGate.spec.tsx rename to src/layouts/BaseLayout/hooks/useUserAccessGate.test.tsx index ba9910dad7..3bfc94ce0a 100644 --- a/src/layouts/BaseLayout/hooks/useUserAccessGate.spec.tsx +++ b/src/layouts/BaseLayout/hooks/useUserAccessGate.test.tsx @@ -1,7 +1,7 @@ import { QueryClient, QueryClientProvider } from '@tanstack/react-query' -import { renderHook, waitFor } from '@testing-library/react' -import { graphql, rest } from 'msw' -import { setupServer } from 'msw/node' +import { cleanup, renderHook, waitFor } from '@testing-library/react' +import { delay, graphql, http, HttpResponse } from 'msw2' +import { setupServer } from 'msw2/node' import { MemoryRouter, Route } from 'react-router-dom' import config from 'config' @@ -10,7 +10,7 @@ import { User } from 'services/user' import { useUserAccessGate } from './useUserAccessGate' -jest.spyOn(console, 'error') +vi.spyOn(console, 'error') const queryClient = new QueryClient({ defaultOptions: { @@ -221,6 +221,7 @@ beforeAll(() => { }) beforeEach(() => { + cleanup() queryClient.clear() server.resetHandlers() }) @@ -251,33 +252,33 @@ describe('useUserAccessGate', () => { internalUser: internalUserHasSyncedProviders, } ) { - const mockMutationVariables = jest.fn() + const mockMutationVariables = vi.fn() server.use( - rest.get('/internal/user', (req, res, ctx) => { - return res(ctx.status(200), ctx.json(internalUser)) + http.get('/internal/user', (info) => { + return HttpResponse.json(internalUser) }), - graphql.query('CurrentUser', (req, res, ctx) => { - return res(ctx.status(200), ctx.data(user)) + graphql.query('CurrentUser', (info) => { + return HttpResponse.json({ data: user }) }), - graphql.mutation('updateDefaultOrganization', (req, res, ctx) => { - mockMutationVariables(req.variables) + graphql.mutation('updateDefaultOrganization', async (info) => { + mockMutationVariables(info.variables) if (delayMutation) { - return res(ctx.delay(1000), ctx.status(200), ctx.data({})) + await delay(1000) + return HttpResponse.json({}) } - return res( - ctx.status(200), - ctx.data({ + return HttpResponse.json({ + data: { updateDefaultOrganization: { defaultOrg: { username: 'criticalRole', }, }, - }) - ) + }, + }) }) ) @@ -286,7 +287,7 @@ describe('useUserAccessGate', () => { } } - afterEach(() => jest.resetAllMocks) + afterEach(() => vi.resetAllMocks) describe.each([ [ diff --git a/src/layouts/BaseLayout/index.js b/src/layouts/BaseLayout/index.ts similarity index 100% rename from src/layouts/BaseLayout/index.js rename to src/layouts/BaseLayout/index.ts