From 558525aa6eccfe89c0955d04434dd6e2d8e0ce0b Mon Sep 17 00:00:00 2001 From: Thomas Roberts <5656702+opr@users.noreply.github.com> Date: Fri, 23 Apr 2021 10:42:36 +0100 Subject: [PATCH] Prevent unwanted parts of address being displayed (https://github.com/woocommerce/woocommerce-blocks/pull/4038) * Add emptyHiddenAddressFields function * Add tests for emptyHiddenAddressFields * Remove address fields that should be hidden before processing checkout * Empty hidden address fields before displaying in shipping calculator * Refactor emptyHiddenAddressFields so we only iterate once * Fix test for emptyHiddenAddressFields * Import default address fields from @woocommerce/settings * Import emptyHiddenAddressFields * Copy address first before emptying fields * Modify address directly instead of copying it * Copy address variable instead of mutating it directly * Add files to TS project * Return the new address rather than the parameter * Don't clean address fields in the presentation layer * Clean address in useStoreCart before it gets sent to components --- .../cart-checkout/shipping-location/index.js | 1 + .../base/context/hooks/cart/use-store-cart.ts | 10 +++++--- .../cart-checkout/checkout/processor/index.js | 13 +++++++--- .../assets/js/base/context/tsconfig.json | 2 ++ .../assets/js/base/utils/address.js | 24 +++++++++++++++++++ .../assets/js/base/utils/test/address.ts | 24 +++++++++++++++++++ 6 files changed, 68 insertions(+), 6 deletions(-) create mode 100644 plugins/woocommerce-blocks/assets/js/base/utils/test/address.ts diff --git a/plugins/woocommerce-blocks/assets/js/base/components/cart-checkout/shipping-location/index.js b/plugins/woocommerce-blocks/assets/js/base/components/cart-checkout/shipping-location/index.js index 872753152d9..8ca9634f54d 100644 --- a/plugins/woocommerce-blocks/assets/js/base/components/cart-checkout/shipping-location/index.js +++ b/plugins/woocommerce-blocks/assets/js/base/components/cart-checkout/shipping-location/index.js @@ -17,6 +17,7 @@ const ShippingLocation = ( { address } ) => { if ( Object.values( address ).length === 0 ) { return null; } + const shippingCountries = getSetting( 'shippingCountries', {} ); const shippingStates = getSetting( 'shippingStates', {} ); const formattedCountry = diff --git a/plugins/woocommerce-blocks/assets/js/base/context/hooks/cart/use-store-cart.ts b/plugins/woocommerce-blocks/assets/js/base/context/hooks/cart/use-store-cart.ts index 1ca3fa68d7a..6c4c4bc458e 100644 --- a/plugins/woocommerce-blocks/assets/js/base/context/hooks/cart/use-store-cart.ts +++ b/plugins/woocommerce-blocks/assets/js/base/context/hooks/cart/use-store-cart.ts @@ -15,7 +15,10 @@ import type { CartResponseBillingAddress, CartResponseShippingAddress, } from '@woocommerce/types'; -import { fromEntriesPolyfill } from '@woocommerce/base-utils'; +import { + emptyHiddenAddressFields, + fromEntriesPolyfill, +} from '@woocommerce/base-utils'; /** * Internal dependencies @@ -171,6 +174,7 @@ export const useStoreCart = ( const cartFees = cartData.fees.map( ( fee: CartResponseFeeItem ) => decodeValues( fee ) ); + return { cartCoupons: cartData.coupons, cartItems: cartData.items || [], @@ -183,8 +187,8 @@ export const useStoreCart = ( cartTotals, cartIsLoading, cartErrors, - billingAddress, - shippingAddress, + billingAddress: emptyHiddenAddressFields( billingAddress ), + shippingAddress: emptyHiddenAddressFields( shippingAddress ), extensions: cartData.extensions || {}, shippingRates: cartData.shippingRates || [], shippingRatesLoading, diff --git a/plugins/woocommerce-blocks/assets/js/base/context/providers/cart-checkout/checkout/processor/index.js b/plugins/woocommerce-blocks/assets/js/base/context/providers/cart-checkout/checkout/processor/index.js index 111fca2d403..adff051e086 100644 --- a/plugins/woocommerce-blocks/assets/js/base/context/providers/cart-checkout/checkout/processor/index.js +++ b/plugins/woocommerce-blocks/assets/js/base/context/providers/cart-checkout/checkout/processor/index.js @@ -10,7 +10,10 @@ import { useState, useMemo, } from '@wordpress/element'; -import { formatStoreApiErrorMessage } from '@woocommerce/base-utils'; +import { + emptyHiddenAddressFields, + formatStoreApiErrorMessage, +} from '@woocommerce/base-utils'; /** * Internal dependencies @@ -164,8 +167,12 @@ const CheckoutProcessor = () => { setIsProcessingOrder( true ); removeNotice( 'checkout' ); let data = { - billing_address: currentBillingData.current, - shipping_address: currentShippingAddress.current, + billing_address: emptyHiddenAddressFields( + currentBillingData.current + ), + shipping_address: emptyHiddenAddressFields( + currentShippingAddress.current + ), customer_note: orderNotes, should_create_account: shouldCreateAccount, }; diff --git a/plugins/woocommerce-blocks/assets/js/base/context/tsconfig.json b/plugins/woocommerce-blocks/assets/js/base/context/tsconfig.json index 29a43587ffb..029deada79e 100644 --- a/plugins/woocommerce-blocks/assets/js/base/context/tsconfig.json +++ b/plugins/woocommerce-blocks/assets/js/base/context/tsconfig.json @@ -8,6 +8,8 @@ "../../settings/blocks/index.ts", "../../base/hooks/index.js", "../utils/type-guards.ts", + "../../base/utils/", + "../../data/", "../../type-defs" ], "exclude": [ "**/test/**" ] diff --git a/plugins/woocommerce-blocks/assets/js/base/utils/address.js b/plugins/woocommerce-blocks/assets/js/base/utils/address.js index 05523fa8aaf..964adfc7c89 100644 --- a/plugins/woocommerce-blocks/assets/js/base/utils/address.js +++ b/plugins/woocommerce-blocks/assets/js/base/utils/address.js @@ -1,3 +1,9 @@ +/** + * External dependencies + */ +import { defaultAddressFields } from '@woocommerce/settings'; +import prepareAddressFields from '@woocommerce/base-components/cart-checkout/address-form/prepare-address-fields'; + /** * pluckAddress takes a full address object and returns relevant fields for calculating * shipping, so we can track when one of them change to update rates. @@ -21,3 +27,21 @@ export const pluckAddress = ( { city: city.trim(), postcode: postcode ? postcode.replace( ' ', '' ).toUpperCase() : '', } ); + +/** + * Sets fields to an empty string in an address if they are hidden by the settings in countryLocale. + * + * @param {Object} address The address to empty fields from. + * @return {Object} The address with hidden fields values removed. + */ +export const emptyHiddenAddressFields = ( address ) => { + const fields = Object.keys( defaultAddressFields ); + const addressFields = prepareAddressFields( fields, {}, address.country ); + const newAddress = Object.assign( {}, address ); + addressFields.forEach( ( field ) => { + if ( field.hidden ) { + newAddress[ field.key ] = ''; + } + } ); + return newAddress; +}; diff --git a/plugins/woocommerce-blocks/assets/js/base/utils/test/address.ts b/plugins/woocommerce-blocks/assets/js/base/utils/test/address.ts new file mode 100644 index 00000000000..8f454ad2058 --- /dev/null +++ b/plugins/woocommerce-blocks/assets/js/base/utils/test/address.ts @@ -0,0 +1,24 @@ +/** + * External dependencies + */ +import { emptyHiddenAddressFields } from '@woocommerce/base-utils'; + +describe( 'emptyHiddenAddressFields', () => { + it( "Removes state from an address where the country doesn't use states", () => { + const address = { + first_name: 'Jonny', + last_name: 'Awesome', + company: 'WordPress', + address_1: '123 Address Street', + address_2: 'Address 2', + city: 'Vienna', + postcode: '1120', + country: 'AT', + state: 'CA', // This should be removed. + email: 'jonny.awesome@email.com', + phone: '', + }; + const filteredAddress = emptyHiddenAddressFields( address ); + expect( filteredAddress ).toHaveProperty( 'state', '' ); + } ); +} );