Skip to content

Commit 06f39cb

Browse files
authored
Add tests to check Publish site button displays when required (#2191)
* Add tests to check if the Publish site button displays only when there are no connected sites
1 parent fcfd66d commit 06f39cb

File tree

1 file changed

+133
-5
lines changed

1 file changed

+133
-5
lines changed

src/components/tests/site-management-actions.test.tsx

Lines changed: 133 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { render, screen } from '@testing-library/react';
1+
import { render, screen, waitFor } from '@testing-library/react';
22
import { userEvent } from '@testing-library/user-event';
33
import { Provider } from 'react-redux';
44
import {
@@ -8,11 +8,30 @@ import {
88
import { SyncSitesProvider } from 'src/hooks/sync-sites';
99
import { ContentTabsProvider } from 'src/hooks/use-content-tabs';
1010
import { store } from 'src/stores';
11+
import { connectedSitesApi } from 'src/stores/sync/connected-sites';
12+
13+
const mockGetConnectedWpcomSites = jest.fn();
14+
const mockUpdateSingleConnectedWpcomSite = jest.fn();
1115

1216
jest.mock( 'src/lib/get-ipc-api', () => ( {
13-
getIpcApi: () => ( {
14-
getConnectedWpcomSites: jest.fn().mockResolvedValue( [] ),
15-
updateSingleConnectedWpcomSite: jest.fn().mockResolvedValue( {} ),
17+
getIpcApi: jest.fn( () => ( {
18+
getConnectedWpcomSites: mockGetConnectedWpcomSites,
19+
updateSingleConnectedWpcomSite: mockUpdateSingleConnectedWpcomSite,
20+
} ) ),
21+
} ) );
22+
23+
// Mock useSiteDetails to return the site passed via context
24+
jest.mock( 'src/hooks/use-site-details', () => ( {
25+
useSiteDetails: () => ( {
26+
selectedSite: { id: 'site-1', running: false },
27+
} ),
28+
} ) );
29+
30+
// Mock useAuth to return a dummy user
31+
jest.mock( 'src/hooks/use-auth', () => ( {
32+
useAuth: () => ( {
33+
user: { id: 1 },
34+
isAuthenticated: true,
1635
} ),
1736
} ) );
1837

@@ -23,7 +42,14 @@ const defaultProps = {
2342
} as SiteManagementActionProps;
2443
describe( 'SiteManagementActions', () => {
2544
beforeEach( () => {
26-
jest.clearAllMocks();
45+
// Reset mock calls but preserve implementations
46+
mockGetConnectedWpcomSites.mockClear();
47+
mockUpdateSingleConnectedWpcomSite.mockClear();
48+
// Set default return values
49+
mockGetConnectedWpcomSites.mockResolvedValue( [] );
50+
mockUpdateSingleConnectedWpcomSite.mockResolvedValue( {} );
51+
// Clear RTK Query cache between tests
52+
store.dispatch( connectedSitesApi.util.resetApiState() );
2753
} );
2854
const renderWithProvider = ( children: React.ReactElement ) => {
2955
return render(
@@ -80,4 +106,106 @@ describe( 'SiteManagementActions', () => {
80106
);
81107
expect( screen.getByRole( 'button', { name: 'Start' } ) ).toBeVisible();
82108
} );
109+
110+
describe( 'PublishSiteButton', () => {
111+
it( 'should render "Publish site" button when no sites are connected', async () => {
112+
renderWithProvider(
113+
<SiteManagementActions
114+
{ ...defaultProps }
115+
selectedSite={ { running: false, id: 'site-1' } as SiteDetails }
116+
/>
117+
);
118+
// Wait for the async query to resolve
119+
const publishButton = await screen.findByRole( 'button', { name: 'Publish site' } );
120+
expect( publishButton ).toBeInTheDocument();
121+
expect( publishButton ).toBeVisible();
122+
} );
123+
124+
it( 'should not render "Publish site" button when one site is connected', async () => {
125+
// Set up mock to return connected sites and clear the cache
126+
mockGetConnectedWpcomSites.mockResolvedValue( [
127+
{
128+
id: 1,
129+
localSiteId: 'site-1',
130+
url: 'https://example.wordpress.com',
131+
name: 'Example Site',
132+
},
133+
] );
134+
// Clear the cache again after changing the mock
135+
store.dispatch( connectedSitesApi.util.resetApiState() );
136+
137+
renderWithProvider(
138+
<SiteManagementActions
139+
{ ...defaultProps }
140+
selectedSite={ { running: false, id: 'site-1' } as SiteDetails }
141+
/>
142+
);
143+
144+
// First wait for the Start button to ensure component is fully rendered
145+
await screen.findByRole( 'button', { name: 'Start' } );
146+
147+
// Then wait for Publish site button to disappear - it may appear briefly before query resolves
148+
await waitFor(
149+
() => {
150+
const publishButton = screen.queryByRole( 'button', { name: 'Publish site' } );
151+
expect( publishButton ).not.toBeInTheDocument();
152+
},
153+
{ timeout: 1000 }
154+
);
155+
} );
156+
157+
it( 'should not render "Publish site" button when multiple sites are connected', async () => {
158+
// Set up mock to return multiple connected sites and clear the cache
159+
mockGetConnectedWpcomSites.mockResolvedValue( [
160+
{
161+
id: 1,
162+
localSiteId: 'site-1',
163+
url: 'https://example1.wordpress.com',
164+
name: 'Example Site 1',
165+
},
166+
{
167+
id: 2,
168+
localSiteId: 'site-1',
169+
url: 'https://example2.wordpress.com',
170+
name: 'Example Site 2',
171+
},
172+
] );
173+
// Clear the cache again after changing the mock
174+
store.dispatch( connectedSitesApi.util.resetApiState() );
175+
176+
renderWithProvider(
177+
<SiteManagementActions
178+
{ ...defaultProps }
179+
selectedSite={ { running: false, id: 'site-1' } as SiteDetails }
180+
/>
181+
);
182+
183+
// First wait for the Start button to ensure component is fully rendered
184+
await screen.findByRole( 'button', { name: 'Start' } );
185+
186+
// Then wait for Publish site button to disappear - it may appear briefly before query resolves
187+
await waitFor(
188+
() => {
189+
const publishButton = screen.queryByRole( 'button', { name: 'Publish site' } );
190+
expect( publishButton ).not.toBeInTheDocument();
191+
},
192+
{ timeout: 1000 }
193+
);
194+
} );
195+
196+
it( 'should render "Publish site" button alongside "Running" button when no sites are connected', async () => {
197+
mockGetConnectedWpcomSites.mockResolvedValue( [] );
198+
renderWithProvider(
199+
<SiteManagementActions
200+
{ ...defaultProps }
201+
selectedSite={ { running: true, id: 'site-1' } as SiteDetails }
202+
/>
203+
);
204+
// Both buttons should be present
205+
const runningButton = screen.getByRole( 'button', { name: 'Running' } );
206+
const publishButton = await screen.findByRole( 'button', { name: 'Publish site' } );
207+
expect( runningButton ).toBeVisible();
208+
expect( publishButton ).toBeVisible();
209+
} );
210+
} );
83211
} );

0 commit comments

Comments
 (0)