From 933408a0fb588a74a084563c3728b904bf9b7b16 Mon Sep 17 00:00:00 2001 From: Rick Caplan Date: Tue, 14 Jan 2025 21:26:38 +0000 Subject: [PATCH] updates localized field hooks and tests --- .../checkout/hooks/localized-fields.ts | 19 ++-- .../hooks/tests/localized-fields.test.ts | 87 +++++++++++++++++-- 2 files changed, 93 insertions(+), 13 deletions(-) diff --git a/packages/ui-extensions-react/src/surfaces/checkout/hooks/localized-fields.ts b/packages/ui-extensions-react/src/surfaces/checkout/hooks/localized-fields.ts index 710d60bb3..3eb00601a 100644 --- a/packages/ui-extensions-react/src/surfaces/checkout/hooks/localized-fields.ts +++ b/packages/ui-extensions-react/src/surfaces/checkout/hooks/localized-fields.ts @@ -15,7 +15,7 @@ import {useSubscription} from './subscription'; */ export function useLocalizedFields< Target extends RenderExtensionTarget = RenderExtensionTarget, ->(keys: LocalizedFieldKey[]): (LocalizedField | undefined)[] | undefined { +>(keys?: LocalizedFieldKey[]): LocalizedField[] { const {localizedFields} = useApi(); if (!localizedFields) { @@ -27,10 +27,19 @@ export function useLocalizedFields< const localizedFieldsData = useSubscription(localizedFields); if (!keys?.length) { - return undefined; + return localizedFieldsData; } - return keys.map((key) => { - return localizedFieldsData?.find(({key: fieldKey}) => fieldKey === key); - }); + return localizedFieldsData.filter(({key}) => keys.includes(key)); +} + +/** + * Returns the current localized field or undefined for the specified + * localized field key and re-renders your component if the value changes. + */ +export function useLocalizedField< + Target extends RenderExtensionTarget = RenderExtensionTarget, +>(key: LocalizedFieldKey): LocalizedField | undefined { + const fields = useLocalizedFields([key]); + return fields[0]; } diff --git a/packages/ui-extensions-react/src/surfaces/checkout/hooks/tests/localized-fields.test.ts b/packages/ui-extensions-react/src/surfaces/checkout/hooks/tests/localized-fields.test.ts index 3e683fab3..1fe2e7a50 100644 --- a/packages/ui-extensions-react/src/surfaces/checkout/hooks/tests/localized-fields.test.ts +++ b/packages/ui-extensions-react/src/surfaces/checkout/hooks/tests/localized-fields.test.ts @@ -1,6 +1,6 @@ import type {LocalizedField} from '@shopify/ui-extensions/checkout'; -import {useLocalizedFields} from '../localized-fields'; +import {useLocalizedFields, useLocalizedField} from '../localized-fields'; import {mount, createMockStatefulRemoteSubscribable} from './mount'; @@ -19,7 +19,30 @@ describe('useLocalizedFields', () => { ); }); - it('returns an array containing undefined if no localized fields match the passed keys', () => { + it('returns all localized fields if no keys are passed', () => { + const localizedFields: LocalizedField[] = [ + { + key: 'TAX_CREDENTIAL_BR', + title: 'CPF/CNPJ', + value: 'test-value', + }, + { + key: 'SHIPPING_CREDENTIAL_BR', + title: 'CPF/CNPJ', + value: 'test-value', + }, + ]; + + const extensionApi = { + localizedFields: createMockStatefulRemoteSubscribable(localizedFields), + }; + + const {value} = mount.hook(() => useLocalizedFields(), {extensionApi}); + + expect(value).toStrictEqual(localizedFields); + }); + + it('returns an empty array if no localized fields match the passed keys', () => { const localizedFields: LocalizedField[] = [ { key: 'TAX_CREDENTIAL_BR', @@ -76,7 +99,7 @@ describe('useLocalizedFields', () => { expect(value).toMatchObject([localizedFields[0], localizedFields[2]]); }); - it('returns an array of localized fields for matching fields and undefined for non-matching fields', () => { + it('returns an array of localized fields for any matching fields', () => { const localizedFields: LocalizedField[] = [ { key: 'TAX_CREDENTIAL_MX', @@ -109,10 +132,58 @@ describe('useLocalizedFields', () => { {extensionApi}, ); - expect(value).toMatchObject([ - localizedFields[0], - undefined, - localizedFields[2], - ]); + expect(value).toMatchObject([localizedFields[0], localizedFields[2]]); + }); +}); + +describe('useLocalizedField', () => { + it('returns the localized field that matches the passed key', async () => { + const localizedFields: LocalizedField[] = [ + { + key: 'TAX_CREDENTIAL_MX', + title: 'Tax credential MX', + value: 'test-value-1', + }, + { + key: 'SHIPPING_CREDENTIAL_MX', + title: 'Shipping credential MX', + value: 'test-value-2', + }, + { + key: 'TAX_CREDENTIAL_USE_MX', + title: 'Tax credential use MX', + value: 'test-value-3', + }, + ]; + + const extensionApi = { + localizedFields: createMockStatefulRemoteSubscribable(localizedFields), + }; + + const {value} = mount.hook( + () => useLocalizedField('TAX_CREDENTIAL_USE_MX'), + { + extensionApi, + }, + ); + + expect(value).toStrictEqual(localizedFields[2]); + }); + + it('returns undefined if no localized field matches the passed key', async () => { + const localizedFields: LocalizedField[] = []; + + const extensionApi = { + localizedFields: createMockStatefulRemoteSubscribable(localizedFields), + }; + + const {value} = mount.hook( + () => useLocalizedField('TAX_CREDENTIAL_USE_MX'), + { + extensionApi, + }, + ); + + expect(value).toBeUndefined(); }); });