diff --git a/plugins/woocommerce-admin/client/customize-store/assembler-hub/sidebar/sidebar-navigation-screen-homepage.tsx b/plugins/woocommerce-admin/client/customize-store/assembler-hub/sidebar/sidebar-navigation-screen-homepage.tsx index 6115caca138..f280cfb0c0e 100644 --- a/plugins/woocommerce-admin/client/customize-store/assembler-hub/sidebar/sidebar-navigation-screen-homepage.tsx +++ b/plugins/woocommerce-admin/client/customize-store/assembler-hub/sidebar/sidebar-navigation-screen-homepage.tsx @@ -95,7 +95,13 @@ export const SidebarNavigationScreenHomepage = () => { }, [ homeTemplates ] ); useEffect( () => { - if ( selectedPattern || ! blocks.length || ! homePatterns.length ) { + if ( + selectedPattern || + ! blocks.length || + ! homePatterns.length || + isLoading || + isEditorLoading + ) { return; } @@ -117,7 +123,7 @@ export const SidebarNavigationScreenHomepage = () => { setSelectedPattern( currentSelectedPattern ); // eslint-disable-next-line react-hooks/exhaustive-deps -- we don't want to re-run this effect when currentSelectedPattern changes - }, [ blocks, homePatterns ] ); + }, [ blocks, homePatterns, isLoading, isEditorLoading ] ); const { context } = useContext( CustomizeStoreContext ); const aiOnline = context.flowType === FlowType.AIOnline; diff --git a/plugins/woocommerce/changelog/46127-add-e2e-homepage b/plugins/woocommerce/changelog/46127-add-e2e-homepage new file mode 100644 index 00000000000..71c7c89132a --- /dev/null +++ b/plugins/woocommerce/changelog/46127-add-e2e-homepage @@ -0,0 +1,4 @@ +Significance: patch +Type: dev +Comment: CYS - E2E tests: add homepage picker E2E tests + diff --git a/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js new file mode 100644 index 00000000000..0a33766c72b --- /dev/null +++ b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js @@ -0,0 +1,198 @@ +const { test: base, expect, request } = require( '@playwright/test' ); +const { AssemblerPage } = require( './assembler.page' ); +const { activateTheme, DEFAULT_THEME } = require( '../../../utils/themes' ); +const { setOption } = require( '../../../utils/options' ); + +const test = base.extend( { + pageObject: async ( { page }, use ) => { + const pageObject = new AssemblerPage( { page } ); + await use( pageObject ); + }, +} ); + +test.describe( 'Assembler -> Homepage', () => { + test.use( { storageState: process.env.ADMINSTATE } ); + + test.beforeAll( async ( { baseURL } ) => { + try { + // In some environments the tour blocks clicking other elements. + await setOption( + request, + baseURL, + 'woocommerce_customize_store_onboarding_tour_hidden', + 'yes' + ); + } catch ( error ) { + console.log( 'Store completed option not updated' ); + } + } ); + + test.afterAll( async ( { baseURL } ) => { + try { + // In some environments the tour blocks clicking other elements. + await setOption( + request, + baseURL, + 'woocommerce_customize_store_onboarding_tour_hidden', + 'no' + ); + await setOption( + request, + baseURL, + 'woocommerce_admin_customize_store_completed', + 'no' + ); + + await activateTheme( DEFAULT_THEME ); + } catch ( error ) { + console.log( 'Store completed option not updated' ); + } + } ); + + test.beforeEach( async ( { baseURL, pageObject } ) => { + await pageObject.setupSite( baseURL ); + await pageObject.waitForLoadingScreenFinish(); + const assembler = await pageObject.getAssembler(); + await assembler.getByText( 'Design your homepage' ).click(); + await assembler + .locator( '.components-placeholder__preview' ) + .waitFor( { state: 'hidden' } ); + } ); + + test( 'Available homepage should be displayed', async ( { + pageObject, + } ) => { + const assembler = await pageObject.getAssembler(); + + const homepages = assembler.locator( + '.block-editor-block-patterns-list__list-item' + ); + + await expect( homepages ).toHaveCount( 3 ); + } ); + + test( 'The selected homepage should be focused when is clicked', async ( { + pageObject, + } ) => { + const assembler = await pageObject.getAssembler(); + const homepage = assembler + .locator( '.block-editor-block-patterns-list__item' ) + .nth( 2 ); + + await homepage.click(); + await expect( homepage ).toHaveClass( /is-selected/ ); + } ); + + test( 'The selected homepage should be visible on the site preview', async ( { + pageObject, + } ) => { + const assembler = await pageObject.getAssembler(); + const editor = await pageObject.getEditor(); + + const homepages = await assembler + .locator( + '.block-editor-block-patterns-list__item:not(.is-selected)' + ) + .all(); + + const selectedHomepage = await assembler + .locator( '.block-editor-block-patterns-list__item.is-selected' ) + .all(); + + // This is necessary to ensure that the trigger works correctly for all the templates in the list because if the pattern is already selected, the trigger doesn't run. + const allHomepages = [ ...homepages, ...selectedHomepage ]; + + for ( const homepage of allHomepages ) { + await homepage.click(); + const homepageElements = await homepage + .locator( '.block-editor-block-list__layout > *' ) + .all(); + + const homepageElementsIds = await Promise.all( + homepageElements.map( ( element ) => + element.getAttribute( 'id' ) + ) + ); + + for ( const elementId of homepageElementsIds ) { + const element = editor.locator( `#${ elementId }` ); + await expect( element ).toBeVisible(); + } + } + } ); + + test( 'The Done button should be visible after clicking save', async ( { + pageObject, + page, + } ) => { + const assembler = await pageObject.getAssembler(); + const homepage = assembler + .locator( '.block-editor-block-patterns-list__item' ) + .nth( 2 ); + + await homepage.click(); + + const saveButton = assembler.getByText( 'Save' ); + const waitResponse = page.waitForResponse( + ( response ) => + response + .url() + .includes( + 'wp-json/wp/v2/templates/twentytwentyfour//home' + ) && response.status() === 200 + ); + + await saveButton.click(); + + await waitResponse; + + await expect( assembler.getByText( 'Done' ) ).toBeEnabled(); + } ); + + test( 'Selected homepage should be applied on the frontend', async ( { + pageObject, + page, + baseURL, + }, testInfo ) => { + testInfo.snapshotSuffix = ''; + const assembler = await pageObject.getAssembler(); + const homepage = assembler + .locator( '.block-editor-block-patterns-list__item' ) + .nth( 2 ); + + await homepage.click(); + + const saveButton = assembler.getByText( 'Save' ); + + const waitResponse = page.waitForResponse( + ( response ) => + response + .url() + .includes( + 'wp-json/wp/v2/templates/twentytwentyfour//home' + ) && response.status() === 200 + ); + + await saveButton.click(); + + await waitResponse; + + await page.goto( baseURL ); + // Get all the content between the header and the footer. + const homepageHTML = await page + .locator( + '//header/following-sibling::*[following-sibling::footer]' + ) + .all(); + + let index = 0; + for ( const element of homepageHTML ) { + await expect( + await element.getAttribute( 'class' ) + ).toMatchSnapshot( { + name: `selected-homepage-blocks-class-frontend-${ index }`, + } ); + index++; + } + } ); +} ); diff --git a/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-0-Chrome b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-0-Chrome new file mode 100644 index 00000000000..7c4d4c9e67c --- /dev/null +++ b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-0-Chrome @@ -0,0 +1 @@ +wp-block-media-text alignfull has-media-on-the-right is-stacked-on-mobile \ No newline at end of file diff --git a/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-1-Chrome b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-1-Chrome new file mode 100644 index 00000000000..10466a6812e --- /dev/null +++ b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-1-Chrome @@ -0,0 +1 @@ +wp-block-group alignwide is-vertical is-content-justification-center is-layout-flex wp-container-core-group-is-layout-6 wp-block-group-is-layout-flex \ No newline at end of file diff --git a/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-2-Chrome b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-2-Chrome new file mode 100644 index 00000000000..bcd94010cff --- /dev/null +++ b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-2-Chrome @@ -0,0 +1 @@ +wp-block-columns alignwide is-layout-flex wp-container-core-columns-is-layout-2 wp-block-columns-is-layout-flex \ No newline at end of file diff --git a/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-3-Chrome b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-3-Chrome new file mode 100644 index 00000000000..67ce569b6ff --- /dev/null +++ b/plugins/woocommerce/tests/e2e-pw/tests/customize-store/assembler/homepage.spec.js-snapshots/selected-homepage-blocks-class-frontend-3-Chrome @@ -0,0 +1 @@ +wp-block-group alignwide has-global-padding is-layout-constrained wp-container-core-group-is-layout-7 wp-block-group-is-layout-constrained \ No newline at end of file