Commit b3dc54fb289 for woocommerce
commit b3dc54fb2893cf3d8733f5557e9d4c8350905026
Author: Ann <annchichi@users.noreply.github.com>
Date: Wed Jul 22 12:03:41 2026 +0800
Clarify shipping zone save action when adding a method (#66343)
* Fix shipping zone save button after adding method
* Add changelog entry for shipping zone save button fix
* Fix shipping zone e2e region selector
* Use exact shipping zone e2e region selector
* Stabilize shipping zone e2e region picker
* Handle empty shipping zone saves
* Clarify shipping zone method save action
* Update changelog for shipping zone save action
* Update Blocks shipping test for save action
* Clean up shipping zone test by ID
diff --git a/plugins/woocommerce/changelog/update-shipping-zone-method-save-action b/plugins/woocommerce/changelog/update-shipping-zone-method-save-action
new file mode 100644
index 00000000000..3c6be095b49
--- /dev/null
+++ b/plugins/woocommerce/changelog/update-shipping-zone-method-save-action
@@ -0,0 +1,4 @@
+Significance: patch
+Type: update
+
+Clarify that adding a shipping method also saves the shipping zone.
diff --git a/plugins/woocommerce/includes/admin/settings/views/html-admin-page-shipping-zone-methods.php b/plugins/woocommerce/includes/admin/settings/views/html-admin-page-shipping-zone-methods.php
index 948f9886478..9a258d0cf4e 100644
--- a/plugins/woocommerce/includes/admin/settings/views/html-admin-page-shipping-zone-methods.php
+++ b/plugins/woocommerce/includes/admin/settings/views/html-admin-page-shipping-zone-methods.php
@@ -160,7 +160,7 @@ do_action( 'woocommerce_shipping_zone_after_methods_table', $zone );
<div class="wc-backbone-modal-buttons">
<button id="btn-back" class="button button-large wc-backbone-modal-back-{{ data.status === 'new' ? 'active' : 'inactive' }}"><?php esc_html_e( 'Back', 'woocommerce' ); ?></button>
<button id="btn-ok" data-status='{{ data.status }}' class="button button-primary button-large">
- <div class="wc-backbone-modal-action-{{ data.status === 'new' ? 'active' : 'inactive' }}"><?php esc_html_e( 'Create and save', 'woocommerce' ); ?></div>
+ <div class="wc-backbone-modal-action-{{ data.status === 'new' ? 'active' : 'inactive' }}"><?php esc_html_e( 'Save zone and method', 'woocommerce' ); ?></div>
<div class="wc-backbone-modal-action-{{ data.status === 'existing' ? 'active' : 'inactive' }}"><?php esc_html_e( 'Save', 'woocommerce' ); ?></div>
</button>
</div>
diff --git a/plugins/woocommerce/tests/e2e/tests/blocks/cart/cart-checkout-block-shipping.block_theme.spec.ts b/plugins/woocommerce/tests/e2e/tests/blocks/cart/cart-checkout-block-shipping.block_theme.spec.ts
index 57dd9713013..8fb7c442948 100644
--- a/plugins/woocommerce/tests/e2e/tests/blocks/cart/cart-checkout-block-shipping.block_theme.spec.ts
+++ b/plugins/woocommerce/tests/e2e/tests/blocks/cart/cart-checkout-block-shipping.block_theme.spec.ts
@@ -63,7 +63,7 @@ test.describe( 'Shopper → Shipping', () => {
await admin.page.getByText( 'Flat rate' ).click();
await admin.page.getByRole( 'button', { name: 'Continue' } ).click();
await admin.page
- .getByRole( 'button', { name: 'Create and save' } )
+ .getByRole( 'button', { name: 'Save zone and method' } )
.click();
await expect( admin.page.getByText( 'Flat rate' ) ).toBeVisible();
if (
diff --git a/plugins/woocommerce/tests/e2e/tests/shipping/shipping-zones.spec.ts b/plugins/woocommerce/tests/e2e/tests/shipping/shipping-zones.spec.ts
index 95802f60406..d3f40d47c34 100644
--- a/plugins/woocommerce/tests/e2e/tests/shipping/shipping-zones.spec.ts
+++ b/plugins/woocommerce/tests/e2e/tests/shipping/shipping-zones.spec.ts
@@ -2,7 +2,7 @@
* External dependencies
*/
import { faker } from '@faker-js/faker';
-import { WC_API_PATH } from '@woocommerce/e2e-utils-playwright';
+import { ApiClient, WC_API_PATH } from '@woocommerce/e2e-utils-playwright';
/**
* Internal dependencies
@@ -14,6 +14,16 @@ function rand() {
return faker.string.alphanumeric( 5 );
}
+async function deleteZoneById( restApi: ApiClient, zoneId?: number ) {
+ if ( zoneId === undefined ) {
+ return;
+ }
+
+ await restApi.delete( `${ WC_API_PATH }/shipping/zones/${ zoneId }`, {
+ force: true,
+ } );
+}
+
const test = baseTest.extend( {
storageState: ADMIN_STATE_PATH,
zone: async ( { restApi }, use ) => {
@@ -110,3 +120,74 @@ test( 'can delete the shipping zone method', async ( { page, zone } ) => {
/You can add multiple shipping methods within this zone. Only customers within the zone will see them.*/
);
} );
+
+test( 'saves an unsaved shipping zone when adding a method', async ( {
+ page,
+ restApi,
+} ) => {
+ const zoneName = `Unsaved zone ${ rand() }`;
+ let createdZoneId: number | undefined;
+
+ try {
+ await page.goto(
+ 'wp-admin/admin.php?page=wc-settings&tab=shipping&zone_id=new'
+ );
+ await page.getByLabel( 'Zone name' ).fill( zoneName );
+ await page
+ .getByRole( 'combobox', { name: 'Start typing to filter zones' } )
+ .fill( 'United States' );
+ await page
+ .getByRole( 'checkbox', {
+ name: 'United States (US)',
+ exact: true,
+ } )
+ .click();
+ await page.keyboard.press( 'Escape' );
+ await expect( page.locator( '.select2-container--open' ) ).toBeHidden();
+
+ await expect( page.locator( '#submit' ) ).toBeEnabled();
+
+ await page
+ .getByRole( 'button', { name: 'Add shipping method' } )
+ .click();
+ await page.getByText( 'Flat rate' ).click();
+ const addMethodResponsePromise = page.waitForResponse( ( response ) => {
+ return response
+ .url()
+ .includes( 'action=woocommerce_shipping_zone_add_method' );
+ } );
+ await page.getByRole( 'button', { name: 'Continue' } ).click();
+ const addMethodResponse = await addMethodResponsePromise;
+ const addMethodResponseBody = await addMethodResponse.json();
+ createdZoneId = addMethodResponseBody.data.zone_id;
+
+ const dialogMessages: string[] = [];
+ page.on( 'dialog', async ( dialog ) => {
+ dialogMessages.push( dialog.message() );
+ await dialog.accept();
+ } );
+
+ await page
+ .getByRole( 'button', { name: 'Save zone and method' } )
+ .click();
+
+ await expect(
+ page.locator( '.wc-shipping-zone-method-title', {
+ hasText: 'Flat rate',
+ } )
+ ).toBeVisible();
+ await expect( page.locator( '#submit' ) ).toBeDisabled();
+ await expect( page.locator( '.blockUI' ) ).toHaveCount( 0 );
+
+ await page.reload();
+ await expect( page.getByLabel( 'Zone name' ) ).toHaveValue( zoneName );
+ await expect(
+ page.locator( '.wc-shipping-zone-method-title', {
+ hasText: 'Flat rate',
+ } )
+ ).toBeVisible();
+ expect( dialogMessages ).toEqual( [] );
+ } finally {
+ await deleteZoneById( restApi, createdZoneId );
+ }
+} );