From d71d7fcb1e7a215fa6058e7813aa21911c71f6d9 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 14 May 2024 09:38:25 +0700 Subject: [PATCH 01/37] feat: add track tax --- src/ROUTES.ts | 4 + src/SCREENS.ts | 1 + .../ModalStackNavigators/index.tsx | 1 + .../FULL_SCREEN_TO_RHP_MAPPING.ts | 1 + src/libs/Navigation/linkingConfig/config.ts | 3 + src/libs/Navigation/types.ts | 4 + .../PolicyDistanceRateDetailsPage.tsx | 17 +++ ...cyDistanceRateTaxReclaimableOnEditPage.tsx | 107 ++++++++++++++++++ .../PolicyDistanceRatesSettingsPage.tsx | 29 ++++- 9 files changed, 165 insertions(+), 2 deletions(-) create mode 100644 src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx diff --git a/src/ROUTES.ts b/src/ROUTES.ts index 39a090635655..16b06baafc7c 100644 --- a/src/ROUTES.ts +++ b/src/ROUTES.ts @@ -757,6 +757,10 @@ const ROUTES = { route: 'settings/workspaces/:policyID/distance-rates/:rateID/edit', getRoute: (policyID: string, rateID: string) => `settings/workspaces/${policyID}/distance-rates/${rateID}/edit` as const, }, + WORKSPACE_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT: { + route: 'settings/workspaces/:policyID/distance-rates/:rateID/tax-reclaimable/edit', + getRoute: (policyID: string, rateID: string) => `settings/workspaces/${policyID}/distance-rates/${rateID}/tax-reclaimable/edit` as const, + }, // Referral program promotion REFERRAL_DETAILS_MODAL: { route: 'referral/:contentType', diff --git a/src/SCREENS.ts b/src/SCREENS.ts index c43247623508..0fbd4243caea 100644 --- a/src/SCREENS.ts +++ b/src/SCREENS.ts @@ -305,6 +305,7 @@ const SCREENS = { DISTANCE_RATES_SETTINGS: 'Distance_Rates_Settings', DISTANCE_RATE_DETAILS: 'Distance_Rate_Details', DISTANCE_RATE_EDIT: 'Distance_Rate_Edit', + DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT: 'Distance_Rate_Tax_Reclaimable_On_Edit', }, EDIT_REQUEST: { diff --git a/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx b/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx index 4373c2b63823..de0b8487cf9a 100644 --- a/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx +++ b/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx @@ -247,6 +247,7 @@ const SettingsModalStackNavigator = createModalStackNavigator require('../../../../pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.DISTANCE_RATE_DETAILS]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateDetailsPage').default as React.ComponentType, [SCREENS.WORKSPACE.DISTANCE_RATE_EDIT]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateEditPage').default as React.ComponentType, + [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAGS_SETTINGS]: () => require('../../../../pages/workspace/tags/WorkspaceTagsSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAG_SETTINGS]: () => require('../../../../pages/workspace/tags/TagSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAG_LIST_VIEW]: () => require('../../../../pages/workspace/tags/WorkspaceViewTagsPage').default as React.ComponentType, diff --git a/src/libs/Navigation/linkingConfig/FULL_SCREEN_TO_RHP_MAPPING.ts b/src/libs/Navigation/linkingConfig/FULL_SCREEN_TO_RHP_MAPPING.ts index d7c92328ee04..982685130e20 100755 --- a/src/libs/Navigation/linkingConfig/FULL_SCREEN_TO_RHP_MAPPING.ts +++ b/src/libs/Navigation/linkingConfig/FULL_SCREEN_TO_RHP_MAPPING.ts @@ -75,6 +75,7 @@ const FULL_SCREEN_TO_RHP_MAPPING: Partial> = { SCREENS.WORKSPACE.CREATE_DISTANCE_RATE, SCREENS.WORKSPACE.DISTANCE_RATES_SETTINGS, SCREENS.WORKSPACE.DISTANCE_RATE_EDIT, + SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT, SCREENS.WORKSPACE.DISTANCE_RATE_DETAILS, ], }; diff --git a/src/libs/Navigation/linkingConfig/config.ts b/src/libs/Navigation/linkingConfig/config.ts index da1f7b2fddfc..5a8cb77c0055 100644 --- a/src/libs/Navigation/linkingConfig/config.ts +++ b/src/libs/Navigation/linkingConfig/config.ts @@ -412,6 +412,9 @@ const config: LinkingOptions['config'] = { [SCREENS.WORKSPACE.DISTANCE_RATE_EDIT]: { path: ROUTES.WORKSPACE_DISTANCE_RATE_EDIT.route, }, + [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT]: { + path: ROUTES.WORKSPACE_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT.route, + }, [SCREENS.WORKSPACE.TAGS_SETTINGS]: { path: ROUTES.WORKSPACE_TAGS_SETTINGS.route, }, diff --git a/src/libs/Navigation/types.ts b/src/libs/Navigation/types.ts index df707c5a7c7d..b5f996273392 100644 --- a/src/libs/Navigation/types.ts +++ b/src/libs/Navigation/types.ts @@ -210,6 +210,10 @@ type SettingsNavigatorParamList = { policyID: string; rateID: string; }; + [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT]: { + policyID: string; + rateID: string; + }; [SCREENS.WORKSPACE.TAGS_SETTINGS]: { policyID: string; }; diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index a75fc74c33cc..405de59eabfe 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -54,6 +54,9 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const editRateValue = () => { Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_EDIT.getRoute(policyID, rateID)); }; + const editTaxReclaimableOnValue = () => { + Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT.getRoute(policyID, rateID)); + }; const toggleRate = () => { if (!rate.enabled || canDisableRate) { @@ -138,6 +141,20 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail onPress={editRateValue} /> + clearErrorFields('rate')} + > + + setIsWarningModalVisible(false)} isVisible={isWarningModalVisible} diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx new file mode 100644 index 000000000000..364073c4c9fd --- /dev/null +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -0,0 +1,107 @@ +import type {StackScreenProps} from '@react-navigation/stack'; +import React, {useCallback} from 'react'; +import {Keyboard} from 'react-native'; +import {withOnyx} from 'react-native-onyx'; +import type {OnyxEntry} from 'react-native-onyx'; +import AmountForm from '@components/AmountForm'; +import FormProvider from '@components/Form/FormProvider'; +import InputWrapperWithRef from '@components/Form/InputWrapper'; +import type {FormOnyxValues} from '@components/Form/types'; +import HeaderWithBackButton from '@components/HeaderWithBackButton'; +import ScreenWrapper from '@components/ScreenWrapper'; +import useAutoFocusInput from '@hooks/useAutoFocusInput'; +import useLocalize from '@hooks/useLocalize'; +import useThemeStyles from '@hooks/useThemeStyles'; +import Navigation from '@libs/Navigation/Navigation'; +import {validateRateValue} from '@libs/PolicyDistanceRatesUtils'; +import type {SettingsNavigatorParamList} from '@navigation/types'; +import AccessOrNotFoundWrapper from '@pages/workspace/AccessOrNotFoundWrapper'; +import * as Policy from '@userActions/Policy'; +import CONST from '@src/CONST'; +import ONYXKEYS from '@src/ONYXKEYS'; +import type SCREENS from '@src/SCREENS'; +import INPUT_IDS from '@src/types/form/PolicyDistanceRateEditForm'; +import type * as OnyxTypes from '@src/types/onyx'; + +type PolicyDistanceRateEditPageOnyxProps = { + /** Policy details */ + policy: OnyxEntry; +}; + +type PolicyDistanceRateEditPageProps = PolicyDistanceRateEditPageOnyxProps & StackScreenProps; + +function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDistanceRateEditPageProps) { + const styles = useThemeStyles(); + const {translate, toLocaleDigit} = useLocalize(); + const {inputCallbackRef} = useAutoFocusInput(); + + const policyID = route.params.policyID; + const rateID = route.params.rateID; + const customUnits = policy?.customUnits ?? {}; + const customUnit = customUnits[Object.keys(customUnits)[0]]; + const rate = customUnit.rates[rateID]; + const currency = rate.currency ?? CONST.CURRENCY.USD; + const currentRateValue = (rate.rate ?? 0).toString(); + + const submitRate = (values: FormOnyxValues) => { + Policy.updatePolicyDistanceRateValue(policyID, customUnit, [{...rate, rate: Number(values.rate) * CONST.POLICY.CUSTOM_UNIT_RATE_BASE_OFFSET}]); + Keyboard.dismiss(); + Navigation.goBack(); + }; + + const validate = useCallback( + (values: FormOnyxValues) => validateRateValue(values, currency, toLocaleDigit), + [currency, toLocaleDigit], + ); + + return ( + + + Navigation.goBack()} + /> + + + + + + ); +} + +PolicyDistanceRateTaxReclaimableOnEditPage.displayName = 'PolicyDistanceRateTaxReclaimableOnEditPage'; + +export default withOnyx({ + policy: { + key: ({route}) => `${ONYXKEYS.COLLECTION.POLICY}${route.params.policyID}`, + }, +})(PolicyDistanceRateTaxReclaimableOnEditPage); diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index d756084e5e49..d31b2b4ff8a5 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -1,5 +1,5 @@ import type {StackScreenProps} from '@react-navigation/stack'; -import React from 'react'; +import React, { useCallback } from 'react'; import {View} from 'react-native'; import type {OnyxEntry} from 'react-native-onyx'; import {withOnyx} from 'react-native-onyx'; @@ -20,6 +20,9 @@ import ONYXKEYS from '@src/ONYXKEYS'; import type SCREENS from '@src/SCREENS'; import type * as OnyxTypes from '@src/types/onyx'; import type {CustomUnit} from '@src/types/onyx/Policy'; +import Switch from '@components/Switch'; +import Text from '@components/Text'; +import TextLink from '@components/TextLink'; import CategorySelector from './CategorySelector'; import UnitSelector from './UnitSelector'; @@ -36,7 +39,6 @@ type PolicyDistanceRatesSettingsPageProps = PolicyDistanceRatesSettingsPageOnyxP function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: PolicyDistanceRatesSettingsPageProps) { const styles = useThemeStyles(); const {translate} = useLocalize(); - const policyID = route.params.policyID; const customUnits = policy?.customUnits ?? {}; const customUnit = customUnits[Object.keys(customUnits)[0]]; @@ -65,6 +67,10 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli Policy.clearPolicyDistanceRatesErrorFields(policyID, customUnitID, {...errorFields, [fieldName]: null}); }; + const onToggleTrackTax = useCallback(()=>{ + + },[]) + return ( )} + + + + Track Tax + + + + {!policy?.tax?.trackingEnabled && + Taxes must be enabled on the workspace to use this feature. Head over to {}}>More features to make that change. + } + + From 8d3eaf7738227185bddcc03859107cee66af4429 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 14 May 2024 16:43:35 +0700 Subject: [PATCH 02/37] feat: add tax rate --- .../PolicyDistanceRateDetailsPage.tsx | 33 ++++++++- ...olicyDistanceRateTaxRateSelectionModal.tsx | 71 +++++++++++++++++++ 2 files changed, 103 insertions(+), 1 deletion(-) create mode 100644 src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 405de59eabfe..0b57ced69d5d 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -1,5 +1,5 @@ import type {StackScreenProps} from '@react-navigation/stack'; -import React, {useState} from 'react'; +import React, {useMemo, useState} from 'react'; import {View} from 'react-native'; import {withOnyx} from 'react-native-onyx'; import type {OnyxEntry} from 'react-native-onyx'; @@ -26,6 +26,8 @@ import ROUTES from '@src/ROUTES'; import type SCREENS from '@src/SCREENS'; import type * as OnyxTypes from '@src/types/onyx'; import type {Rate} from '@src/types/onyx/Policy'; +import type { ListItemType } from './PolicyDistanceRateTaxRateSelectionModal'; +import PolicyDistanceRateTaxRateSelectionModal from './PolicyDistanceRateTaxRateSelectionModal'; type PolicyDistanceRateDetailsPageOnyxProps = { /** Policy details */ @@ -40,6 +42,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const {windowWidth} = useWindowDimensions(); const [isWarningModalVisible, setIsWarningModalVisible] = useState(false); const [isDeleteModalVisible, setIsDeleteModalVisible] = useState(false); + const [isTaxRateSelectionModalVisible, setIsTaxRateSelectionModalVisible] = useState(false); const policyID = route.params.policyID; const rateID = route.params.rateID; @@ -50,6 +53,19 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const canDeleteRate = Object.values(customUnit.rates).filter((distanceRate) => distanceRate.enabled).length > 1 || !rate.enabled; const canDisableRate = Object.values(customUnit.rates).filter((distanceRate) => distanceRate.enabled).length > 1; const errorFields = rate.errorFields; + const defaultTaxRateID = policy?.taxRates?.defaultExternalID ?? ''; + const taxRate = `${policy?.taxRates?.taxes[defaultTaxRateID].name} (${policy?.taxRates?.taxes[defaultTaxRateID].value})` + const taxRateItems: ListItemType[] = useMemo(()=>{ + const taxes = policy?.taxRates?.taxes; + const result = Object.entries(taxes ?? {}).map(([key, value]) => ({ + value: value.value, + text: `${value.name} (${value.value})`, + isSelected: defaultTaxRateID === key, + keyForList: key + })); + return result + },[policy, defaultTaxRateID]) + const editRateValue = () => { Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_EDIT.getRoute(policyID, rateID)); @@ -141,6 +157,21 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail onPress={editRateValue} /> + + setIsTaxRateSelectionModalVisible(true)} + /> + {}} + onClose={()=> setIsTaxRateSelectionModalVisible(false)} + /> + void; + + /** Function to call when the user closes the role selection modal */ + onClose: () => void; +}; + +function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateChange, onClose}: WorkspaceMemberDetailsPageProps) { + // const {translate} = useLocalize(); + const styles = useThemeStyles(); + + return ( + onClose?.()} + onModalHide={onClose} + hideModalContentWhileAnimating + useNativeDriver + > + + + + item.isSelected)?.keyForList} + /> + + + + ); +} + +PolicyDistanceRateTaxRateSelectionModal.displayName = 'PolicyDistanceRateTaxRateSelectionModal'; + +export type {ListItemType}; + +export default PolicyDistanceRateTaxRateSelectionModal; From 0cf9a2c2096e4627ff007691b344eb5e3972821b Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Wed, 15 May 2024 15:29:18 +0700 Subject: [PATCH 03/37] fix: add EnableDistanceRequestTax api --- src/libs/API/types.ts | 1 + .../ModalStackNavigators/index.tsx | 3 +- src/libs/actions/Policy.ts | 54 +++++++++++++ .../PolicyDistanceRateDetailsPage.tsx | 76 ++++++++++--------- ...olicyDistanceRateTaxRateSelectionModal.tsx | 2 +- ...cyDistanceRateTaxReclaimableOnEditPage.tsx | 2 +- .../PolicyDistanceRatesSettingsPage.tsx | 64 +++++++++------- src/types/onyx/Policy.ts | 1 + 8 files changed, 138 insertions(+), 65 deletions(-) diff --git a/src/libs/API/types.ts b/src/libs/API/types.ts index 8fe704ff220e..7400f561359e 100644 --- a/src/libs/API/types.ts +++ b/src/libs/API/types.ts @@ -206,6 +206,7 @@ const WRITE_COMMANDS = { ADD_BILLING_CARD_AND_REQUEST_WORKSPACE_OWNER_CHANGE: 'AddBillingCardAndRequestPolicyOwnerChange', SET_POLICY_DISTANCE_RATES_UNIT: 'SetPolicyDistanceRatesUnit', SET_POLICY_DISTANCE_RATES_DEFAULT_CATEGORY: 'SetPolicyDistanceRatesDefaultCategory', + ENABLE_DISTANCE_REQUEST_TAX: 'EnableDistanceRequestTax', UPDATE_POLICY_DISTANCE_RATE_VALUE: 'UpdatePolicyDistanceRateValue', SET_POLICY_DISTANCE_RATES_ENABLED: 'SetPolicyDistanceRatesEnabled', DELETE_POLICY_DISTANCE_RATES: 'DeletePolicyDistanceRates', diff --git a/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx b/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx index de0b8487cf9a..b3174b72e277 100644 --- a/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx +++ b/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx @@ -247,7 +247,8 @@ const SettingsModalStackNavigator = createModalStackNavigator require('../../../../pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.DISTANCE_RATE_DETAILS]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateDetailsPage').default as React.ComponentType, [SCREENS.WORKSPACE.DISTANCE_RATE_EDIT]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateEditPage').default as React.ComponentType, - [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage').default as React.ComponentType, + [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT]: () => + require('../../../../pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAGS_SETTINGS]: () => require('../../../../pages/workspace/tags/WorkspaceTagsSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAG_SETTINGS]: () => require('../../../../pages/workspace/tags/TagSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAG_LIST_VIEW]: () => require('../../../../pages/workspace/tags/WorkspaceViewTagsPage').default as React.ComponentType, diff --git a/src/libs/actions/Policy.ts b/src/libs/actions/Policy.ts index 3332932f97c7..583ca5f5b753 100644 --- a/src/libs/actions/Policy.ts +++ b/src/libs/actions/Policy.ts @@ -4461,6 +4461,59 @@ function enablePolicyWorkflows(policyID: string, enabled: boolean) { } } +function enableDistanceRequestTax(policyID: string, customUnitName: string, customUnitID: string, attributes: Attributes) { + const policy = getPolicy(policyID); + const onyxData: OnyxData = { + optimisticData: [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + customUnits: { + [customUnitID]: { + attributes, + }, + }, + pendingFields: { + customUnits: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE, + }, + }, + }, + ], + successData: [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + pendingFields: { + customUnits: null, + }, + }, + }, + ], + failureData: [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + customUnits: { + [customUnitID]: { + attributes: policy.customUnits ? policy.customUnits[customUnitID].attributes : null, + }, + }, + }, + }, + ], + }; + + const params = { + customUnitName, + customUnitID, + attributes, + }; + API.write(WRITE_COMMANDS.ENABLE_DISTANCE_REQUEST_TAX, params, onyxData); +} + function renamePolicyTaglist(policyID: string, policyTagListName: {oldName: string; newName: string}, policyTags: OnyxEntry) { const newName = policyTagListName.newName; const oldName = policyTagListName.oldName; @@ -5264,6 +5317,7 @@ export { enablePolicyTags, enablePolicyTaxes, enablePolicyWorkflows, + enableDistanceRequestTax, openPolicyDistanceRatesPage, openPolicyMoreFeaturesPage, generateCustomUnitID, diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 0b57ced69d5d..238ecea64dfa 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -26,7 +26,7 @@ import ROUTES from '@src/ROUTES'; import type SCREENS from '@src/SCREENS'; import type * as OnyxTypes from '@src/types/onyx'; import type {Rate} from '@src/types/onyx/Policy'; -import type { ListItemType } from './PolicyDistanceRateTaxRateSelectionModal'; +import type {ListItemType} from './PolicyDistanceRateTaxRateSelectionModal'; import PolicyDistanceRateTaxRateSelectionModal from './PolicyDistanceRateTaxRateSelectionModal'; type PolicyDistanceRateDetailsPageOnyxProps = { @@ -48,24 +48,24 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const rateID = route.params.rateID; const customUnits = policy?.customUnits ?? {}; const customUnit = customUnits[Object.keys(customUnits)[0]]; + const isTrackTaxEnabled = customUnit.attributes.taxEnabled; const rate = customUnit.rates[rateID]; const currency = rate.currency ?? CONST.CURRENCY.USD; const canDeleteRate = Object.values(customUnit.rates).filter((distanceRate) => distanceRate.enabled).length > 1 || !rate.enabled; const canDisableRate = Object.values(customUnit.rates).filter((distanceRate) => distanceRate.enabled).length > 1; const errorFields = rate.errorFields; const defaultTaxRateID = policy?.taxRates?.defaultExternalID ?? ''; - const taxRate = `${policy?.taxRates?.taxes[defaultTaxRateID].name} (${policy?.taxRates?.taxes[defaultTaxRateID].value})` - const taxRateItems: ListItemType[] = useMemo(()=>{ + const taxRate = `${policy?.taxRates?.taxes[defaultTaxRateID].name} (${policy?.taxRates?.taxes[defaultTaxRateID].value})`; + const taxRateItems: ListItemType[] = useMemo(() => { const taxes = policy?.taxRates?.taxes; const result = Object.entries(taxes ?? {}).map(([key, value]) => ({ value: value.value, text: `${value.name} (${value.value})`, isSelected: defaultTaxRateID === key, - keyForList: key + keyForList: key, })); - return result - },[policy, defaultTaxRateID]) - + return result; + }, [policy, defaultTaxRateID]); const editRateValue = () => { Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_EDIT.getRoute(policyID, rateID)); @@ -157,35 +157,39 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail onPress={editRateValue} /> - - setIsTaxRateSelectionModalVisible(true)} - /> - {}} - onClose={()=> setIsTaxRateSelectionModalVisible(false)} - /> - - clearErrorFields('rate')} - > - - + {isTrackTaxEnabled && ( + + setIsTaxRateSelectionModalVisible(true)} + /> + {}} + onClose={() => setIsTaxRateSelectionModalVisible(false)} + /> + + )} + {isTrackTaxEnabled && ( + clearErrorFields('rate')} + > + + + )} setIsWarningModalVisible(false)} isVisible={isWarningModalVisible} diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx index 06c897f7e2ae..1a7df8b437fc 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx @@ -48,7 +48,7 @@ function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateCha includePaddingTop={false} > diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx index 364073c4c9fd..67c497281236 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -67,7 +67,7 @@ function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDista shouldEnableMaxHeight > Navigation.goBack()} /> diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index d31b2b4ff8a5..847136cf7a59 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -1,5 +1,5 @@ import type {StackScreenProps} from '@react-navigation/stack'; -import React, { useCallback } from 'react'; +import React from 'react'; import {View} from 'react-native'; import type {OnyxEntry} from 'react-native-onyx'; import {withOnyx} from 'react-native-onyx'; @@ -7,6 +7,9 @@ import HeaderWithBackButton from '@components/HeaderWithBackButton'; import OfflineWithFeedback from '@components/OfflineWithFeedback'; import ScreenWrapper from '@components/ScreenWrapper'; import type {ListItem} from '@components/SelectionList/types'; +import Switch from '@components/Switch'; +import Text from '@components/Text'; +import TextLink from '@components/TextLink'; import type {UnitItemType} from '@components/UnitPicker'; import useLocalize from '@hooks/useLocalize'; import useThemeStyles from '@hooks/useThemeStyles'; @@ -20,9 +23,6 @@ import ONYXKEYS from '@src/ONYXKEYS'; import type SCREENS from '@src/SCREENS'; import type * as OnyxTypes from '@src/types/onyx'; import type {CustomUnit} from '@src/types/onyx/Policy'; -import Switch from '@components/Switch'; -import Text from '@components/Text'; -import TextLink from '@components/TextLink'; import CategorySelector from './CategorySelector'; import UnitSelector from './UnitSelector'; @@ -43,6 +43,7 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli const customUnits = policy?.customUnits ?? {}; const customUnit = customUnits[Object.keys(customUnits)[0]]; const customUnitID = customUnit?.customUnitID ?? ''; + const isTrackTaxEnabled = customUnit.attributes.taxEnabled; const defaultCategory = customUnits[customUnitID].defaultCategory; const defaultUnit = customUnits[customUnitID].attributes.unit; @@ -67,10 +68,10 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli Policy.clearPolicyDistanceRatesErrorFields(policyID, customUnitID, {...errorFields, [fieldName]: null}); }; - const onToggleTrackTax = useCallback(()=>{ - - },[]) - + const onToggleTrackTax = (isOn: boolean) => { + const attributes = {...customUnits[customUnitID].attributes, taxEnabled: isOn}; + Policy.enableDistanceRequestTax(policyID, customUnit.name, customUnitID, attributes); + }; return ( )} - - - - Track Tax - - + + + + Track Tax + - {!policy?.tax?.trackingEnabled && - Taxes must be enabled on the workspace to use this feature. Head over to {}}>More features to make that change. - } - - + + {!policy?.tax?.trackingEnabled && ( + + + Taxes must be enabled on the workspace to use this feature. Head over to{' '} + {}} + > + More features + {' '} + to make that change. + + + )} + diff --git a/src/types/onyx/Policy.ts b/src/types/onyx/Policy.ts index 53c76286985d..be318342eeff 100644 --- a/src/types/onyx/Policy.ts +++ b/src/types/onyx/Policy.ts @@ -19,6 +19,7 @@ type Rate = OnyxCommon.OnyxValueWithOfflineFeedback<{ type Attributes = { unit: Unit; + taxEnabled?: boolean; }; type CustomUnit = OnyxCommon.OnyxValueWithOfflineFeedback<{ From 496b79140ec23a7282cd81817d6260309f9a4158 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Thu, 23 May 2024 16:05:07 +0700 Subject: [PATCH 04/37] fix: enableDistanceRequestTax params --- src/libs/actions/Policy.ts | 9 ++++++--- .../distanceRates/PolicyDistanceRateDetailsPage.tsx | 3 +-- 2 files changed, 7 insertions(+), 5 deletions(-) diff --git a/src/libs/actions/Policy.ts b/src/libs/actions/Policy.ts index 1ef09f9aab09..ca1214043f46 100644 --- a/src/libs/actions/Policy.ts +++ b/src/libs/actions/Policy.ts @@ -4501,9 +4501,12 @@ function enableDistanceRequestTax(policyID: string, customUnitName: string, cust }; const params = { - customUnitName, - customUnitID, - attributes, + policyID, + customUnit: JSON.stringify({ + customUnitName, + customUnitID, + attributes, + }), }; API.write(WRITE_COMMANDS.ENABLE_DISTANCE_REQUEST_TAX, params, onyxData); } diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 0feae31a175a..44169b4585c0 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -51,7 +51,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const customUnit = customUnits[Object.keys(customUnits)[0]]; const rate = customUnit?.rates[rateID]; const currency = rate?.currency ?? CONST.CURRENCY.USD; - + const isTrackTaxEnabled = customUnit.attributes.taxEnabled; const defaultTaxRateID = policy?.taxRates?.defaultExternalID ?? ''; const taxRate = `${policy?.taxRates?.taxes[defaultTaxRateID].name} (${policy?.taxRates?.taxes[defaultTaxRateID].value})`; @@ -66,7 +66,6 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail return result; }, [policy, defaultTaxRateID]); - // Rates can be disabled or deleted as long as in the remaining rates there is always at least one enabled rate and there are no pending delete action const canDisableOrDeleteRate = Object.values(customUnit?.rates).some( (distanceRate: Rate) => distanceRate?.enabled && rateID !== distanceRate?.customUnitRateID && distanceRate?.pendingAction !== CONST.RED_BRICK_ROAD_PENDING_ACTION.DELETE, From b32b35060b79f3461df9c24e9ff0df8a0e2ba6db Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Thu, 23 May 2024 16:28:05 +0700 Subject: [PATCH 05/37] fix: add navigation to more features --- .../distanceRates/PolicyDistanceRatesSettingsPage.tsx | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index 2190b495981a..9744f5e3cae9 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -14,12 +14,14 @@ import type {UnitItemType} from '@components/UnitPicker'; import useLocalize from '@hooks/useLocalize'; import useThemeStyles from '@hooks/useThemeStyles'; import * as ErrorUtils from '@libs/ErrorUtils'; +import Navigation from '@libs/Navigation/Navigation'; import * as OptionsListUtils from '@libs/OptionsListUtils'; import type {SettingsNavigatorParamList} from '@navigation/types'; import AccessOrNotFoundWrapper from '@pages/workspace/AccessOrNotFoundWrapper'; import * as Policy from '@userActions/Policy'; import CONST from '@src/CONST'; import ONYXKEYS from '@src/ONYXKEYS'; +import ROUTES from '@src/ROUTES'; import type SCREENS from '@src/SCREENS'; import type * as OnyxTypes from '@src/types/onyx'; import type {CustomUnit} from '@src/types/onyx/Policy'; @@ -135,7 +137,7 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli Taxes must be enabled on the workspace to use this feature. Head over to{' '} {}} + onPress={() => Navigation.navigate(ROUTES.WORKSPACE_MORE_FEATURES.getRoute(policyID))} > More features {' '} From 386bd5d218f8ba36d1c9fd6bfc9acb4454a12e3d Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 28 May 2024 00:00:48 +0700 Subject: [PATCH 06/37] feature: add tax claimable in distance rates --- src/ONYXKEYS.ts | 3 ++ src/languages/en.ts | 2 + src/libs/API/types.ts | 1 + src/libs/PolicyDistanceRatesUtils.ts | 15 ++++++- .../PolicyDistanceRateDetailsPage.tsx | 9 ++-- ...cyDistanceRateTaxReclaimableOnEditPage.tsx | 44 ++++++++++--------- ...icyDistanceRateTaxReclaimableOnEditForm.ts | 18 ++++++++ src/types/form/index.ts | 1 + src/types/onyx/Policy.ts | 4 ++ 9 files changed, 73 insertions(+), 24 deletions(-) create mode 100644 src/types/form/PolicyDistanceRateTaxReclaimableOnEditForm.ts diff --git a/src/ONYXKEYS.ts b/src/ONYXKEYS.ts index ddf37fba2354..1aff574d63c2 100755 --- a/src/ONYXKEYS.ts +++ b/src/ONYXKEYS.ts @@ -391,6 +391,8 @@ const ONYXKEYS = { POLICY_CREATE_DISTANCE_RATE_FORM: 'policyCreateDistanceRateForm', POLICY_CREATE_DISTANCE_RATE_FORM_DRAFT: 'policyCreateDistanceRateFormDraft', POLICY_DISTANCE_RATE_EDIT_FORM: 'policyDistanceRateEditForm', + POLICY_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT_FORM: 'policyDistanceRateTaxReclaimableOnEditForm', + POLICY_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT_FORM_DRAFT: 'policyDistanceRateTaxReclaimableOnEditFormDraft', POLICY_DISTANCE_RATE_EDIT_FORM_DRAFT: 'policyDistanceRateEditFormDraft', CLOSE_ACCOUNT_FORM: 'closeAccount', CLOSE_ACCOUNT_FORM_DRAFT: 'closeAccountDraft', @@ -530,6 +532,7 @@ type OnyxFormValuesMapping = { [ONYXKEYS.FORMS.WORKSPACE_NEW_TAX_FORM]: FormTypes.WorkspaceNewTaxForm; [ONYXKEYS.FORMS.POLICY_CREATE_DISTANCE_RATE_FORM]: FormTypes.PolicyCreateDistanceRateForm; [ONYXKEYS.FORMS.POLICY_DISTANCE_RATE_EDIT_FORM]: FormTypes.PolicyDistanceRateEditForm; + [ONYXKEYS.FORMS.POLICY_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT_FORM]: FormTypes.PolicyDistanceRateTaxReclaimableOnEditForm; [ONYXKEYS.FORMS.WORKSPACE_TAX_NAME_FORM]: FormTypes.WorkspaceTaxNameForm; [ONYXKEYS.FORMS.WORKSPACE_TAX_VALUE_FORM]: FormTypes.WorkspaceTaxValueForm; [ONYXKEYS.FORMS.NEW_CHAT_NAME_FORM]: FormTypes.NewChatNameForm; diff --git a/src/languages/en.ts b/src/languages/en.ts index 85470bd17a67..818b44243dcd 100755 --- a/src/languages/en.ts +++ b/src/languages/en.ts @@ -2221,6 +2221,8 @@ export default { foreignDefault: 'Foreign currency default', customTaxName: 'Custom tax name', value: 'Value', + taxReclaimableOn: 'Tax reclaimable on', + taxRate: 'Tax rate', error: { taxRateAlreadyExists: 'This tax name is already in use.', valuePercentageRange: 'Please enter a valid percentage between 0 and 100.', diff --git a/src/libs/API/types.ts b/src/libs/API/types.ts index 153de74dd1ec..88eeaf7eeef0 100644 --- a/src/libs/API/types.ts +++ b/src/libs/API/types.ts @@ -421,6 +421,7 @@ type WriteCommandParameters = { [WRITE_COMMANDS.RENAME_POLICY_TAX]: Parameters.RenamePolicyTaxParams; [WRITE_COMMANDS.SET_POLICY_DISTANCE_RATES_UNIT]: Parameters.SetPolicyDistanceRatesUnitParams; [WRITE_COMMANDS.SET_POLICY_DISTANCE_RATES_DEFAULT_CATEGORY]: Parameters.SetPolicyDistanceRatesDefaultCategoryParams; + [WRITE_COMMANDS.ENABLE_DISTANCE_REQUEST_TAX]: Parameters.SetPolicyDistanceRatesDefaultCategoryParams; // eslint-disable-next-line @typescript-eslint/no-explicit-any [WRITE_COMMANDS.UPDATE_POLICY_CONNECTION_CONFIG]: Parameters.UpdatePolicyConnectionConfigParams; diff --git a/src/libs/PolicyDistanceRatesUtils.ts b/src/libs/PolicyDistanceRatesUtils.ts index db739cc3b8c7..ae473923c34e 100644 --- a/src/libs/PolicyDistanceRatesUtils.ts +++ b/src/libs/PolicyDistanceRatesUtils.ts @@ -9,6 +9,8 @@ import * as NumberUtils from './NumberUtils'; type RateValueForm = typeof ONYXKEYS.FORMS.WORKSPACE_RATE_AND_UNIT_FORM | typeof ONYXKEYS.FORMS.POLICY_CREATE_DISTANCE_RATE_FORM | typeof ONYXKEYS.FORMS.POLICY_DISTANCE_RATE_EDIT_FORM; +type TaxReclaimableForm = typeof ONYXKEYS.FORMS.POLICY_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT_FORM; + function validateRateValue(values: FormOnyxValues, currency: string, toLocaleDigit: (arg: string) => string): FormInputErrors { const errors: FormInputErrors = {}; const parsedRate = MoneyRequestUtils.replaceAllDigits(values.rate, toLocaleDigit); @@ -24,6 +26,17 @@ function validateRateValue(values: FormOnyxValues, currency: stri return errors; } +function validateTaxClaimableValue(values: FormOnyxValues, rate: Rate): FormInputErrors { + const errors: FormInputErrors = {}; + if (rate.rate) { + return errors; + } + if (rate.rate && Number(values.taxClaimableValue) > rate.rate / 100) { + errors.taxClaimableValue = 'workspace.reimburse.invalidRateError'; + } + return errors; +} + /** * Get the optimistic rate name in a way that matches BE logic * @param rates @@ -33,4 +46,4 @@ function getOptimisticRateName(rates: Record): string { return existingRatesWithSameName.length ? `${CONST.CUSTOM_UNITS.DEFAULT_RATE} ${existingRatesWithSameName.length}` : CONST.CUSTOM_UNITS.DEFAULT_RATE; } -export {validateRateValue, getOptimisticRateName}; +export {validateRateValue, getOptimisticRateName, validateTaxClaimableValue}; diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index d85d5c879980..ad833e285f9f 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -51,6 +51,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const customUnit = customUnits[Object.keys(customUnits)[0]]; const rate = customUnit?.rates[rateID]; const currency = rate?.currency ?? CONST.CURRENCY.USD; + const taxClaimablePercentage = rate.attributes?.taxClaimablePercentage; const isTrackTaxEnabled = customUnit.attributes.taxEnabled; const defaultTaxRateID = policy?.taxRates?.defaultExternalID ?? ''; @@ -98,6 +99,8 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail }; const rateValueToDisplay = CurrencyUtils.convertAmountToDisplayString(rate?.rate, currency); + const taxClaimableValueToDisplay = + taxClaimablePercentage && rate.rate ? `${CurrencyUtils.getLocalizedCurrencySymbol(currency)}${((taxClaimablePercentage * rate.rate) / 100).toFixed(1)}` : ''; const unitToDisplay = translate(`common.${customUnit?.attributes?.unit ?? CONST.CUSTOM_UNITS.DISTANCE_UNIT_MILES}`); const threeDotsMenuItems = [ @@ -170,7 +173,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail setIsTaxRateSelectionModalVisible(true)} /> @@ -191,8 +194,8 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail > diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx index 67c497281236..4578c2ae23ad 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -13,26 +13,27 @@ import useAutoFocusInput from '@hooks/useAutoFocusInput'; import useLocalize from '@hooks/useLocalize'; import useThemeStyles from '@hooks/useThemeStyles'; import Navigation from '@libs/Navigation/Navigation'; -import {validateRateValue} from '@libs/PolicyDistanceRatesUtils'; +import {validateTaxClaimableValue} from '@libs/PolicyDistanceRatesUtils'; import type {SettingsNavigatorParamList} from '@navigation/types'; import AccessOrNotFoundWrapper from '@pages/workspace/AccessOrNotFoundWrapper'; import * as Policy from '@userActions/Policy'; import CONST from '@src/CONST'; import ONYXKEYS from '@src/ONYXKEYS'; import type SCREENS from '@src/SCREENS'; -import INPUT_IDS from '@src/types/form/PolicyDistanceRateEditForm'; +import INPUT_IDS from '@src/types/form/PolicyDistanceRateTaxReclaimableOnEditForm'; import type * as OnyxTypes from '@src/types/onyx'; -type PolicyDistanceRateEditPageOnyxProps = { +type PolicyDistanceRateTaxReclaimableOnEditPageOnyxProps = { /** Policy details */ policy: OnyxEntry; }; -type PolicyDistanceRateEditPageProps = PolicyDistanceRateEditPageOnyxProps & StackScreenProps; +type PolicyDistanceRateTaxReclaimableOnEditPageProps = PolicyDistanceRateTaxReclaimableOnEditPageOnyxProps & + StackScreenProps; -function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDistanceRateEditPageProps) { +function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDistanceRateTaxReclaimableOnEditPageProps) { const styles = useThemeStyles(); - const {translate, toLocaleDigit} = useLocalize(); + const {translate} = useLocalize(); const {inputCallbackRef} = useAutoFocusInput(); const policyID = route.params.policyID; @@ -41,18 +42,21 @@ function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDista const customUnit = customUnits[Object.keys(customUnits)[0]]; const rate = customUnit.rates[rateID]; const currency = rate.currency ?? CONST.CURRENCY.USD; - const currentRateValue = (rate.rate ?? 0).toString(); - - const submitRate = (values: FormOnyxValues) => { - Policy.updatePolicyDistanceRateValue(policyID, customUnit, [{...rate, rate: Number(values.rate) * CONST.POLICY.CUSTOM_UNIT_RATE_BASE_OFFSET}]); + const currentTaxReclaimableOnValue = rate.attributes?.taxClaimablePercentage && rate.rate ? (rate.attributes.taxClaimablePercentage * rate.rate) / 100 : ''; + const submitTaxReclaimableOn = (values: FormOnyxValues) => { + Policy.updatePolicyDistanceRateValue(policyID, customUnit, [ + { + ...rate, + attributes: { + taxClaimablePercentage: rate.rate ? (Number(values.taxClaimableValue) * 100) / rate.rate : undefined, + }, + }, + ]); Keyboard.dismiss(); Navigation.goBack(); }; - const validate = useCallback( - (values: FormOnyxValues) => validateRateValue(values, currency, toLocaleDigit), - [currency, toLocaleDigit], - ); + const validate = useCallback((values: FormOnyxValues) => validateTaxClaimableValue(values, rate), [rate]); return ( Navigation.goBack()} /> ({ +export default withOnyx({ policy: { key: ({route}) => `${ONYXKEYS.COLLECTION.POLICY}${route.params.policyID}`, }, diff --git a/src/types/form/PolicyDistanceRateTaxReclaimableOnEditForm.ts b/src/types/form/PolicyDistanceRateTaxReclaimableOnEditForm.ts new file mode 100644 index 000000000000..b41facf3604f --- /dev/null +++ b/src/types/form/PolicyDistanceRateTaxReclaimableOnEditForm.ts @@ -0,0 +1,18 @@ +import type {ValueOf} from 'type-fest'; +import type Form from './Form'; + +const INPUT_IDS = { + TAX_CLAIMABLE_VALUE: 'taxClaimableValue', +} as const; + +type InputID = ValueOf; + +type PolicyDistanceRateTaxReclaimableOnEditForm = Form< + InputID, + { + [INPUT_IDS.TAX_CLAIMABLE_VALUE]: string; + } +>; + +export type {PolicyDistanceRateTaxReclaimableOnEditForm}; +export default INPUT_IDS; diff --git a/src/types/form/index.ts b/src/types/form/index.ts index b3e46733a44e..16ecea881328 100644 --- a/src/types/form/index.ts +++ b/src/types/form/index.ts @@ -46,6 +46,7 @@ export type {WorkspaceTaxNameForm} from './WorkspaceTaxNameForm'; export type {WorkspaceTaxValueForm} from './WorkspaceTaxValueForm'; export type {WorkspaceTaxCustomName} from './WorkspaceTaxCustomName'; export type {PolicyCreateDistanceRateForm} from './PolicyCreateDistanceRateForm'; +export type {PolicyDistanceRateTaxReclaimableOnEditForm} from './PolicyDistanceRateTaxReclaimableOnEditForm'; export type {PolicyDistanceRateEditForm} from './PolicyDistanceRateEditForm'; export type {WalletAdditionalDetailsForm} from './WalletAdditionalDetailsForm'; export type {NewChatNameForm} from './NewChatNameForm'; diff --git a/src/types/onyx/Policy.ts b/src/types/onyx/Policy.ts index be318342eeff..80b7dcb5f217 100644 --- a/src/types/onyx/Policy.ts +++ b/src/types/onyx/Policy.ts @@ -15,6 +15,10 @@ type Rate = OnyxCommon.OnyxValueWithOfflineFeedback<{ enabled?: boolean; errors?: OnyxCommon.Errors; errorFields?: OnyxCommon.ErrorFields; + attributes?: { + taxClaimablePercentage?: number; + taxRateExternalID?: string; + }; }>; type Attributes = { From d2ab2c146c99c582dcd3c9bafd3fc3219bd13d95 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 28 May 2024 00:25:19 +0700 Subject: [PATCH 07/37] fix: add tax rate in distace rate unit --- src/languages/en.ts | 1 + src/libs/PolicyDistanceRatesUtils.ts | 6 ++--- .../PolicyDistanceRateDetailsPage.tsx | 27 ++++++++++++++----- ...olicyDistanceRateTaxRateSelectionModal.tsx | 6 ++--- ...cyDistanceRateTaxReclaimableOnEditPage.tsx | 1 + 5 files changed, 28 insertions(+), 13 deletions(-) diff --git a/src/languages/en.ts b/src/languages/en.ts index 818b44243dcd..e63b9ccff8d2 100755 --- a/src/languages/en.ts +++ b/src/languages/en.ts @@ -2230,6 +2230,7 @@ export default { deleteFailureMessage: 'An error occurred while deleting the tax rate. Please try again or ask Concierge for help.', updateFailureMessage: 'An error occurred while updating the tax rate. Please try again or ask Concierge for help.', createFailureMessage: 'An error occurred while creating the tax rate. Please try again or ask Concierge for help.', + updateTaxClaimableFailureMessage: 'The reclaimable portion must be less than the distance rate amount.', }, deleteTaxConfirmation: 'Are you sure you want to delete this tax?', deleteMultipleTaxConfirmation: ({taxAmount}) => `Are you sure you want to delete ${taxAmount} taxes?`, diff --git a/src/libs/PolicyDistanceRatesUtils.ts b/src/libs/PolicyDistanceRatesUtils.ts index ae473923c34e..b61f9d684a2f 100644 --- a/src/libs/PolicyDistanceRatesUtils.ts +++ b/src/libs/PolicyDistanceRatesUtils.ts @@ -28,11 +28,11 @@ function validateRateValue(values: FormOnyxValues, currency: stri function validateTaxClaimableValue(values: FormOnyxValues, rate: Rate): FormInputErrors { const errors: FormInputErrors = {}; - if (rate.rate) { + if (!rate.rate) { return errors; } - if (rate.rate && Number(values.taxClaimableValue) > rate.rate / 100) { - errors.taxClaimableValue = 'workspace.reimburse.invalidRateError'; + if (Number(values.taxClaimableValue) > rate.rate / 100) { + errors.taxClaimableValue = 'workspace.taxes.error.updateTaxClaimableFailureMessage'; } return errors; } diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index ad833e285f9f..0b4e71f52e84 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -1,6 +1,6 @@ import type {StackScreenProps} from '@react-navigation/stack'; import React, {useMemo, useState} from 'react'; -import {View} from 'react-native'; +import {Keyboard, View} from 'react-native'; import {withOnyx} from 'react-native-onyx'; import type {OnyxEntry} from 'react-native-onyx'; import ConfirmModal from '@components/ConfirmModal'; @@ -52,20 +52,20 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const rate = customUnit?.rates[rateID]; const currency = rate?.currency ?? CONST.CURRENCY.USD; const taxClaimablePercentage = rate.attributes?.taxClaimablePercentage; + const taxRateExternalID = rate.attributes?.taxRateExternalID; const isTrackTaxEnabled = customUnit.attributes.taxEnabled; - const defaultTaxRateID = policy?.taxRates?.defaultExternalID ?? ''; - const taxRate = `${policy?.taxRates?.taxes[defaultTaxRateID].name} (${policy?.taxRates?.taxes[defaultTaxRateID].value})`; + const taxRate = taxRateExternalID ? `${policy?.taxRates?.taxes[taxRateExternalID].name} (${policy?.taxRates?.taxes[taxRateExternalID].value})` : ''; const taxRateItems: ListItemType[] = useMemo(() => { const taxes = policy?.taxRates?.taxes; const result = Object.entries(taxes ?? {}).map(([key, value]) => ({ - value: value.value, + value: key, text: `${value.name} (${value.value})`, - isSelected: defaultTaxRateID === key, + isSelected: taxRateExternalID === key, keyForList: key, })); return result; - }, [policy, defaultTaxRateID]); + }, [policy, taxRateExternalID]); // Rates can be disabled or deleted as long as in the remaining rates there is always at least one enabled rate and there are no pending delete action const canDisableOrDeleteRate = Object.values(customUnit?.rates).some( @@ -98,6 +98,19 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail setIsDeleteModalVisible(false); }; + const onTaxRateChange = (newTaxRate: ListItemType) => { + Policy.updatePolicyDistanceRateValue(policyID, customUnit, [ + { + ...rate, + attributes: { + ...rate.attributes, + taxRateExternalID: newTaxRate.value, + }, + }, + ]); + Keyboard.dismiss(); + }; + const rateValueToDisplay = CurrencyUtils.convertAmountToDisplayString(rate?.rate, currency); const taxClaimableValueToDisplay = taxClaimablePercentage && rate.rate ? `${CurrencyUtils.getLocalizedCurrencySymbol(currency)}${((taxClaimablePercentage * rate.rate) / 100).toFixed(1)}` : ''; @@ -180,7 +193,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail {}} + onTaxRateChange={onTaxRateChange} onClose={() => setIsTaxRateSelectionModalVisible(false)} /> diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx index 1a7df8b437fc..e10f9461b466 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx @@ -5,7 +5,7 @@ import Modal from '@components/Modal'; import ScreenWrapper from '@components/ScreenWrapper'; import SelectionList from '@components/SelectionList'; import RadioListItem from '@components/SelectionList/RadioListItem'; -// import useLocalize from '@hooks/useLocalize'; +import useLocalize from '@hooks/useLocalize'; import useThemeStyles from '@hooks/useThemeStyles'; import CONST from '@src/CONST'; @@ -31,7 +31,7 @@ type WorkspaceMemberDetailsPageProps = { }; function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateChange, onClose}: WorkspaceMemberDetailsPageProps) { - // const {translate} = useLocalize(); + const {translate} = useLocalize(); const styles = useThemeStyles(); return ( @@ -48,7 +48,7 @@ function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateCha includePaddingTop={false} > diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx index 4578c2ae23ad..bafe4c15ba82 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -48,6 +48,7 @@ function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDista { ...rate, attributes: { + ...rate.attributes, taxClaimablePercentage: rate.rate ? (Number(values.taxClaimableValue) * 100) / rate.rate : undefined, }, }, From 37b65f75fdd4f325fca1d638f7761dc9faa96f33 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 28 May 2024 00:32:23 +0700 Subject: [PATCH 08/37] update en.ts --- src/languages/es.ts | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/languages/es.ts b/src/languages/es.ts index e0349d00e706..8eeb3d169997 100644 --- a/src/languages/es.ts +++ b/src/languages/es.ts @@ -2257,6 +2257,8 @@ export default { foreignDefault: 'Moneda extranjera por defecto', customTaxName: 'Nombre del impuesto', value: 'Valor', + taxRate: 'Tasa de impuesto', + taxReclaimableOn: 'Impuesto recuperable en', error: { taxRateAlreadyExists: 'Ya existe un impuesto con este nombre.', customNameRequired: 'El nombre del impuesto es obligatorio.', @@ -2264,6 +2266,7 @@ export default { deleteFailureMessage: 'Se ha producido un error al intentar eliminar la tasa de impuesto. Por favor, inténtalo más tarde.', updateFailureMessage: 'Se ha producido un error al intentar modificar la tasa de impuesto. Por favor, inténtalo más tarde.', createFailureMessage: 'Se ha producido un error al intentar crear la tasa de impuesto. Por favor, inténtalo más tarde.', + updateTaxClaimableFailureMessage: 'La porción reclamable debe ser menor que el monto de la tarifa a distancia.', }, deleteTaxConfirmation: '¿Estás seguro de que quieres eliminar este impuesto?', deleteMultipleTaxConfirmation: ({taxAmount}) => `¿Estás seguro de que quieres eliminar ${taxAmount} impuestos?`, From d7cf692501e83122c1e57e7cf7d929d8a90f285f Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Wed, 29 May 2024 22:48:33 +0700 Subject: [PATCH 09/37] rename function update tax rate and tax claimable --- src/libs/actions/Policy/Policy.ts | 144 ++++++++++++++++++ .../PolicyDistanceRateDetailsPage.tsx | 2 +- ...cyDistanceRateTaxReclaimableOnEditPage.tsx | 2 +- 3 files changed, 146 insertions(+), 2 deletions(-) diff --git a/src/libs/actions/Policy/Policy.ts b/src/libs/actions/Policy/Policy.ts index 1dccb10c1889..ca0daf5b849d 100644 --- a/src/libs/actions/Policy/Policy.ts +++ b/src/libs/actions/Policy/Policy.ts @@ -4442,6 +4442,148 @@ function updatePolicyDistanceRateValue(policyID: string, customUnit: CustomUnit, API.write(WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_RATE_VALUE, params, {optimisticData, successData, failureData}); } +function updateDistanceTaxClaimableValue(policyID: string, customUnit: CustomUnit, customUnitRates: Rate[]) { + const currentRates = customUnit.rates; + const optimisticRates: Record = {}; + const successRates: Record = {}; + const failureRates: Record = {}; + const rateIDs = customUnitRates.map((rate) => rate.customUnitRateID); + + for (const rateID of Object.keys(customUnit.rates)) { + if (rateIDs.includes(rateID)) { + const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); + optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; + successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; + failureRates[rateID] = { + ...currentRates[rateID], + pendingFields: {rate: null}, + errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, + }; + } + } + + const optimisticData: OnyxUpdate[] = [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + customUnits: { + [customUnit.customUnitID]: { + rates: optimisticRates, + }, + }, + }, + }, + ]; + + const successData: OnyxUpdate[] = [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + customUnits: { + [customUnit.customUnitID]: { + rates: successRates, + }, + }, + }, + }, + ]; + + const failureData: OnyxUpdate[] = [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + customUnits: { + [customUnit.customUnitID]: { + rates: failureRates, + }, + }, + }, + }, + ]; + + const params: UpdatePolicyDistanceRateValueParams = { + policyID, + customUnitID: customUnit.customUnitID, + customUnitRateArray: JSON.stringify(prepareCustomUnitRatesArray(customUnitRates)), + }; + + API.write(WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_RATE_VALUE, params, {optimisticData, successData, failureData}); +} + +function updateDistanceTaxRate(policyID: string, customUnit: CustomUnit, customUnitRates: Rate[]) { + const currentRates = customUnit.rates; + const optimisticRates: Record = {}; + const successRates: Record = {}; + const failureRates: Record = {}; + const rateIDs = customUnitRates.map((rate) => rate.customUnitRateID); + + for (const rateID of Object.keys(customUnit.rates)) { + if (rateIDs.includes(rateID)) { + const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); + optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; + successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; + failureRates[rateID] = { + ...currentRates[rateID], + pendingFields: {rate: null}, + errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, + }; + } + } + + const optimisticData: OnyxUpdate[] = [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + customUnits: { + [customUnit.customUnitID]: { + rates: optimisticRates, + }, + }, + }, + }, + ]; + + const successData: OnyxUpdate[] = [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + customUnits: { + [customUnit.customUnitID]: { + rates: successRates, + }, + }, + }, + }, + ]; + + const failureData: OnyxUpdate[] = [ + { + onyxMethod: Onyx.METHOD.MERGE, + key: `${ONYXKEYS.COLLECTION.POLICY}${policyID}`, + value: { + customUnits: { + [customUnit.customUnitID]: { + rates: failureRates, + }, + }, + }, + }, + ]; + + const params: UpdatePolicyDistanceRateValueParams = { + policyID, + customUnitID: customUnit.customUnitID, + customUnitRateArray: JSON.stringify(prepareCustomUnitRatesArray(customUnitRates)), + }; + + API.write(WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_RATE_VALUE, params, {optimisticData, successData, failureData}); +} + function setPolicyDistanceRatesEnabled(policyID: string, customUnit: CustomUnit, customUnitRates: Rate[]) { const currentRates = customUnit.rates; const optimisticRates: Record = {}; @@ -4833,6 +4975,8 @@ export { clearPolicyDistanceRatesErrorFields, clearPolicyDistanceRateErrorFields, updatePolicyDistanceRateValue, + updateDistanceTaxClaimableValue, + updateDistanceTaxRate, setPolicyDistanceRatesEnabled, deletePolicyDistanceRates, getPrimaryPolicy, diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 001af352681a..1a2b583f42de 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -99,7 +99,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail }; const onTaxRateChange = (newTaxRate: ListItemType) => { - Policy.updatePolicyDistanceRateValue(policyID, customUnit, [ + Policy.updateDistanceTaxRate(policyID, customUnit, [ { ...rate, attributes: { diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx index bafe4c15ba82..209c11db4815 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -44,7 +44,7 @@ function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDista const currency = rate.currency ?? CONST.CURRENCY.USD; const currentTaxReclaimableOnValue = rate.attributes?.taxClaimablePercentage && rate.rate ? (rate.attributes.taxClaimablePercentage * rate.rate) / 100 : ''; const submitTaxReclaimableOn = (values: FormOnyxValues) => { - Policy.updatePolicyDistanceRateValue(policyID, customUnit, [ + Policy.updateDistanceTaxClaimableValue(policyID, customUnit, [ { ...rate, attributes: { From 2273707f85202f3f7a1f666e5c43b78896b8e5a5 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Wed, 29 May 2024 22:49:16 +0700 Subject: [PATCH 10/37] update es.ts --- src/languages/es.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/languages/es.ts b/src/languages/es.ts index 069e324099fd..5fbbe76e753b 100644 --- a/src/languages/es.ts +++ b/src/languages/es.ts @@ -2269,7 +2269,7 @@ export default { deleteFailureMessage: 'Se ha producido un error al intentar eliminar la tasa de impuesto. Por favor, inténtalo más tarde.', updateFailureMessage: 'Se ha producido un error al intentar modificar la tasa de impuesto. Por favor, inténtalo más tarde.', createFailureMessage: 'Se ha producido un error al intentar crear la tasa de impuesto. Por favor, inténtalo más tarde.', - updateTaxClaimableFailureMessage: 'La porción reclamable debe ser menor que el monto de la tarifa a distancia.', + updateTaxClaimableFailureMessage: 'La porción recuperable debe ser menor al monto del importe por distancia.', }, deleteTaxConfirmation: '¿Estás seguro de que quieres eliminar este impuesto?', deleteMultipleTaxConfirmation: ({taxAmount}) => `¿Estás seguro de que quieres eliminar ${taxAmount} impuestos?`, From cd606713b5a4b7d3e6609fd371422fa462bb734e Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Thu, 30 May 2024 15:58:13 +0700 Subject: [PATCH 11/37] fix: minor change --- .../distanceRates/PolicyDistanceRateDetailsPage.tsx | 5 ++--- .../PolicyDistanceRateTaxRateSelectionModal.tsx | 4 ++-- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 1a2b583f42de..0d615d925751 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -80,7 +80,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const editRateValue = () => { Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_EDIT.getRoute(policyID, rateID)); }; - const editTaxReclaimableOnValue = () => { + const editTaxReclaimableValue = () => { Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT.getRoute(policyID, rateID)); }; @@ -184,7 +184,6 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail {isTrackTaxEnabled && ( )} diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx index e10f9461b466..d3f757f4c60c 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx @@ -30,7 +30,7 @@ type WorkspaceMemberDetailsPageProps = { onClose: () => void; }; -function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateChange, onClose}: WorkspaceMemberDetailsPageProps) { +function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateChange, onClose = () => {}}: WorkspaceMemberDetailsPageProps) { const {translate} = useLocalize(); const styles = useThemeStyles(); @@ -38,7 +38,7 @@ function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateCha onClose?.()} + onClose={onClose} onModalHide={onClose} hideModalContentWhileAnimating useNativeDriver From f5d98f286e814b9b8fcef68f9c614b61bc4b2852 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Thu, 30 May 2024 16:16:02 +0700 Subject: [PATCH 12/37] add new translation --- src/languages/en.ts | 3 +++ src/languages/es.ts | 3 +++ .../PolicyDistanceRateTaxReclaimableOnEditPage.tsx | 2 +- .../distanceRates/PolicyDistanceRatesSettingsPage.tsx | 8 ++++---- 4 files changed, 11 insertions(+), 5 deletions(-) diff --git a/src/languages/en.ts b/src/languages/en.ts index 52ef931e586b..8425949ff5d2 100755 --- a/src/languages/en.ts +++ b/src/languages/en.ts @@ -2192,6 +2192,7 @@ export default { delete: 'Delete field', deleteConfirmation: 'Are you sure that you want to delete this field?', }, + tags: { tagName: 'Tag name', requiresTag: 'Members must tag all expenses', @@ -2507,6 +2508,8 @@ export default { enableRate: 'Enable rate', status: 'Status', unit: 'Unit', + taxFeatureNotEnabledMessage: 'Taxes must be enabled on the workspace to use this feature. Head over to ', + changePromptMessage: ' to make that change.', defaultCategory: 'Default category', deleteDistanceRate: 'Delete distance rate', areYouSureDelete: ({count}: DistanceRateOperationsParams) => `Are you sure you want to delete ${Str.pluralize('this rate', 'these rates', count)}?`, diff --git a/src/languages/es.ts b/src/languages/es.ts index 14e93d7e2237..86401d551ab0 100644 --- a/src/languages/es.ts +++ b/src/languages/es.ts @@ -2228,6 +2228,7 @@ export default { delete: 'Eliminar campos', deleteConfirmation: '¿Estás seguro de que quieres eliminar esta campos?', }, + tags: { tagName: 'Nombre de etiqueta', requiresTag: 'Los miembros deben etiquetar todos los gastos', @@ -2544,6 +2545,8 @@ export default { enableRate: 'Activar tasa', status: 'Estado', unit: 'Unidad', + taxFeatureNotEnabledMessage: 'Los impuestos deben estar activados en el área de trabajo para poder utilizar esta función. Dirígete a ', + changePromptMessage: ' para hacer ese cambio.', defaultCategory: 'Categoría predeterminada', deleteDistanceRate: 'Eliminar tasa de distancia', areYouSureDelete: ({count}: DistanceRateOperationsParams) => `¿Estás seguro de que quieres eliminar ${Str.pluralize('esta tasa', 'estas tasas', count)}?`, diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx index 209c11db4815..96545e866cf3 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -16,7 +16,7 @@ import Navigation from '@libs/Navigation/Navigation'; import {validateTaxClaimableValue} from '@libs/PolicyDistanceRatesUtils'; import type {SettingsNavigatorParamList} from '@navigation/types'; import AccessOrNotFoundWrapper from '@pages/workspace/AccessOrNotFoundWrapper'; -import * as Policy from '@userActions/Policy'; +import * as Policy from '@userActions/Policy/Policy'; import CONST from '@src/CONST'; import ONYXKEYS from '@src/ONYXKEYS'; import type SCREENS from '@src/SCREENS'; diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index bfd9d8042e89..40a189a3e023 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -135,14 +135,14 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli style={styles.colorMuted} fontSize={14} > - Taxes must be enabled on the workspace to use this feature. Head over to{' '} + {translate('workspace.distanceRates.taxFeatureNotEnabledMessage')} Navigation.navigate(ROUTES.WORKSPACE_MORE_FEATURES.getRoute(policyID))} > - More features - {' '} - to make that change. + {translate('workspace.common.moreFeatures')} + + {translate('workspace.distanceRates.changePromptMessage')} )} From adf89938cceb3f7c06134783fd99fdd25b942bc5 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Thu, 30 May 2024 21:54:05 +0700 Subject: [PATCH 13/37] fix: add new translation and minor change --- src/languages/en.ts | 1 + src/languages/es.ts | 1 + .../PolicyDistanceRateDetailsPage.tsx | 42 +++++++++++-------- ...olicyDistanceRateTaxRateSelectionModal.tsx | 21 ++++------ .../PolicyDistanceRatesSettingsPage.tsx | 4 +- 5 files changed, 37 insertions(+), 32 deletions(-) diff --git a/src/languages/en.ts b/src/languages/en.ts index 8425949ff5d2..6d02618d52e7 100755 --- a/src/languages/en.ts +++ b/src/languages/en.ts @@ -2502,6 +2502,7 @@ export default { centrallyManage: 'Centrally manage rates, choose to track in miles or kilometers, and set a default category.', rate: 'Rate', addRate: 'Add rate', + trackTax: 'Track tax', deleteRates: ({count}: DistanceRateOperationsParams) => `Delete ${Str.pluralize('rate', 'rates', count)}`, enableRates: ({count}: DistanceRateOperationsParams) => `Enable ${Str.pluralize('rate', 'rates', count)}`, disableRates: ({count}: DistanceRateOperationsParams) => `Disable ${Str.pluralize('rate', 'rates', count)}`, diff --git a/src/languages/es.ts b/src/languages/es.ts index 86401d551ab0..b936186fcb4f 100644 --- a/src/languages/es.ts +++ b/src/languages/es.ts @@ -2539,6 +2539,7 @@ export default { centrallyManage: 'Gestiona centralizadamente las tasas, elige si contabilizar en millas o kilómetros, y define una categoría por defecto', rate: 'Tasa', addRate: 'Agregar tasa', + trackTax: 'Impuesto de seguimiento', deleteRates: ({count}: DistanceRateOperationsParams) => `Eliminar ${Str.pluralize('tasa', 'tasas', count)}`, enableRates: ({count}: DistanceRateOperationsParams) => `Activar ${Str.pluralize('tasa', 'tasas', count)}`, disableRates: ({count}: DistanceRateOperationsParams) => `Desactivar ${Str.pluralize('tasa', 'tasas', count)}`, diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 0d615d925751..59caca02498b 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -108,6 +108,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail }, }, ]); + setIsTaxRateSelectionModalVisible(false); Keyboard.dismiss(); }; @@ -182,27 +183,34 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail /> {isTrackTaxEnabled && ( - - setIsTaxRateSelectionModalVisible(true)} - /> - setIsTaxRateSelectionModalVisible(false)} - /> - + clearErrorFields('attributes')} + > + + setIsTaxRateSelectionModalVisible(true)} + /> + setIsTaxRateSelectionModalVisible(false)} + /> + + )} {isTrackTaxEnabled && ( clearErrorFields('rate')} + onClose={() => clearErrorFields('attributes')} > void; }; -function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateChange, onClose = () => {}}: WorkspaceMemberDetailsPageProps) { +function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateChange, onClose = () => {}}: PolicyDistanceRateTaxRateSelectionModalProps) { const {translate} = useLocalize(); - const styles = useThemeStyles(); return ( - - item.isSelected)?.keyForList} - /> - + item.isSelected)?.keyForList} + /> ); diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index 40a189a3e023..0332c73e274c 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -120,10 +120,10 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli - Track Tax + {translate('workspace.distanceRates.trackTax')} From 84eb62a4398d346135434b1777eb5eb8e9f8fe20 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Fri, 31 May 2024 14:20:20 +0700 Subject: [PATCH 14/37] fix: intergate API --- .../UpdatePolicyDistanceTaxRateValueParams.ts | 7 +++++++ .../parameters/UpdatePolicyTaxClaimableValueParams.ts | 7 +++++++ src/libs/API/parameters/index.ts | 2 ++ src/libs/API/types.ts | 4 ++++ src/libs/actions/Policy/Policy.ts | 10 ++++++---- 5 files changed, 26 insertions(+), 4 deletions(-) create mode 100644 src/libs/API/parameters/UpdatePolicyDistanceTaxRateValueParams.ts create mode 100644 src/libs/API/parameters/UpdatePolicyTaxClaimableValueParams.ts diff --git a/src/libs/API/parameters/UpdatePolicyDistanceTaxRateValueParams.ts b/src/libs/API/parameters/UpdatePolicyDistanceTaxRateValueParams.ts new file mode 100644 index 000000000000..d78738ee9750 --- /dev/null +++ b/src/libs/API/parameters/UpdatePolicyDistanceTaxRateValueParams.ts @@ -0,0 +1,7 @@ +type UpdatePolicyDistanceTaxRateValueParams = { + policyID: string; + customUnitID: string; + customUnitRateArray: string; +}; + +export default UpdatePolicyDistanceTaxRateValueParams; diff --git a/src/libs/API/parameters/UpdatePolicyTaxClaimableValueParams.ts b/src/libs/API/parameters/UpdatePolicyTaxClaimableValueParams.ts new file mode 100644 index 000000000000..8b227f94414a --- /dev/null +++ b/src/libs/API/parameters/UpdatePolicyTaxClaimableValueParams.ts @@ -0,0 +1,7 @@ +type UpdatePolicyTaxClaimableValueParams = { + policyID: string; + customUnitID: string; + customUnitRateArray: string; +}; + +export default UpdatePolicyTaxClaimableValueParams; diff --git a/src/libs/API/parameters/index.ts b/src/libs/API/parameters/index.ts index 52f130a28dd1..05a5d56e2c77 100644 --- a/src/libs/API/parameters/index.ts +++ b/src/libs/API/parameters/index.ts @@ -195,6 +195,8 @@ export type {default as CreatePolicyDistanceRateParams} from './CreatePolicyDist export type {default as SetPolicyDistanceRatesUnitParams} from './SetPolicyDistanceRatesUnitParams'; export type {default as SetPolicyDistanceRatesDefaultCategoryParams} from './SetPolicyDistanceRatesDefaultCategoryParams'; export type {default as UpdatePolicyDistanceRateValueParams} from './UpdatePolicyDistanceRateValueParams'; +export type {default as UpdatePolicyDistanceTaxRateValueParams} from './UpdatePolicyDistanceTaxRateValueParams'; +export type {default as UpdatePolicyTaxClaimableValueParams} from './UpdatePolicyTaxClaimableValueParams'; export type {default as SetPolicyDistanceRatesEnabledParams} from './SetPolicyDistanceRatesEnabledParams'; export type {default as DeletePolicyDistanceRatesParams} from './DeletePolicyDistanceRatesParams'; export type {default as CreatePolicyTagsParams} from './CreatePolicyTagsParams'; diff --git a/src/libs/API/types.ts b/src/libs/API/types.ts index 88eeaf7eeef0..f3b03bc60b4c 100644 --- a/src/libs/API/types.ts +++ b/src/libs/API/types.ts @@ -209,6 +209,8 @@ const WRITE_COMMANDS = { SET_POLICY_DISTANCE_RATES_DEFAULT_CATEGORY: 'SetPolicyDistanceRatesDefaultCategory', ENABLE_DISTANCE_REQUEST_TAX: 'EnableDistanceRequestTax', UPDATE_POLICY_DISTANCE_RATE_VALUE: 'UpdatePolicyDistanceRateValue', + UPDATE_POLICY_DISTANCE_TAX_RATE_VALUE: 'UpdateDistanceTaxRate', + UPDATE_DISTANCE_TAX_CLAIMABLE_VALUE: 'UpdateDistanceTaxClaimableValue', SET_POLICY_DISTANCE_RATES_ENABLED: 'SetPolicyDistanceRatesEnabled', DELETE_POLICY_DISTANCE_RATES: 'DeletePolicyDistanceRates', DISMISS_TRACK_EXPENSE_ACTIONABLE_WHISPER: 'DismissActionableWhisper', @@ -428,6 +430,8 @@ type WriteCommandParameters = { [WRITE_COMMANDS.UPDATE_MANY_POLICY_CONNECTION_CONFIGS]: Parameters.UpdateManyPolicyConnectionConfigurationsParams; [WRITE_COMMANDS.REMOVE_POLICY_CONNECTION]: Parameters.RemovePolicyConnectionParams; [WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_RATE_VALUE]: Parameters.UpdatePolicyDistanceRateValueParams; + [WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_TAX_RATE_VALUE]: Parameters.UpdatePolicyDistanceTaxRateValueParams; + [WRITE_COMMANDS.UPDATE_DISTANCE_TAX_CLAIMABLE_VALUE]: Parameters.UpdatePolicyTaxClaimableValueParams; [WRITE_COMMANDS.SET_POLICY_DISTANCE_RATES_ENABLED]: Parameters.SetPolicyDistanceRatesEnabledParams; [WRITE_COMMANDS.DELETE_POLICY_DISTANCE_RATES]: Parameters.DeletePolicyDistanceRatesParams; [WRITE_COMMANDS.DISMISS_TRACK_EXPENSE_ACTIONABLE_WHISPER]: Parameters.DismissTrackExpenseActionableWhisperParams; diff --git a/src/libs/actions/Policy/Policy.ts b/src/libs/actions/Policy/Policy.ts index 4857066ae4dc..792c3f27b47c 100644 --- a/src/libs/actions/Policy/Policy.ts +++ b/src/libs/actions/Policy/Policy.ts @@ -42,6 +42,8 @@ import type { SetWorkspacePayerParams, SetWorkspaceReimbursementParams, UpdatePolicyDistanceRateValueParams, + UpdatePolicyDistanceTaxRateValueParams, + UpdatePolicyTaxClaimableValueParams, UpdateWorkspaceAvatarParams, UpdateWorkspaceCustomUnitAndRateParams, UpdateWorkspaceDescriptionParams, @@ -3973,13 +3975,13 @@ function updateDistanceTaxClaimableValue(policyID: string, customUnit: CustomUni }, ]; - const params: UpdatePolicyDistanceRateValueParams = { + const params: UpdatePolicyTaxClaimableValueParams = { policyID, customUnitID: customUnit.customUnitID, customUnitRateArray: JSON.stringify(prepareCustomUnitRatesArray(customUnitRates)), }; - API.write(WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_RATE_VALUE, params, {optimisticData, successData, failureData}); + API.write(WRITE_COMMANDS.UPDATE_DISTANCE_TAX_CLAIMABLE_VALUE, params, {optimisticData, successData, failureData}); } function updateDistanceTaxRate(policyID: string, customUnit: CustomUnit, customUnitRates: Rate[]) { @@ -4044,13 +4046,13 @@ function updateDistanceTaxRate(policyID: string, customUnit: CustomUnit, customU }, ]; - const params: UpdatePolicyDistanceRateValueParams = { + const params: UpdatePolicyDistanceTaxRateValueParams = { policyID, customUnitID: customUnit.customUnitID, customUnitRateArray: JSON.stringify(prepareCustomUnitRatesArray(customUnitRates)), }; - API.write(WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_RATE_VALUE, params, {optimisticData, successData, failureData}); + API.write(WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_TAX_RATE_VALUE, params, {optimisticData, successData, failureData}); } function setPolicyDistanceRatesEnabled(policyID: string, customUnit: CustomUnit, customUnitRates: Rate[]) { From af79e580fa5536aed2a884bbb8b88e79ec1d7dc6 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Fri, 31 May 2024 15:33:31 +0700 Subject: [PATCH 15/37] fix: update tax rate edit page --- src/ROUTES.ts | 4 + src/SCREENS.ts | 1 + .../ModalStackNavigators/index.tsx | 1 + .../FULL_SCREEN_TO_RHP_MAPPING.ts | 1 + src/libs/Navigation/linkingConfig/config.ts | 3 + src/libs/Navigation/types.ts | 4 + .../PolicyDistanceRateDetailsPage.tsx | 44 +------- .../PolicyDistanceRateTaxRateEditPage.tsx | 104 ++++++++++++++++++ ...olicyDistanceRateTaxRateSelectionModal.tsx | 66 ----------- ...orkspaceTaxesSettingsWorkspaceCurrency.tsx | 1 - 10 files changed, 124 insertions(+), 105 deletions(-) create mode 100644 src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx delete mode 100644 src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx diff --git a/src/ROUTES.ts b/src/ROUTES.ts index 7c7f4e8610ea..45ad83d22f3a 100644 --- a/src/ROUTES.ts +++ b/src/ROUTES.ts @@ -781,6 +781,10 @@ const ROUTES = { route: 'settings/workspaces/:policyID/distance-rates/:rateID/tax-reclaimable/edit', getRoute: (policyID: string, rateID: string) => `settings/workspaces/${policyID}/distance-rates/${rateID}/tax-reclaimable/edit` as const, }, + WORKSPACE_DISTANCE_RATE_TAX_RATE_EDIT: { + route: 'settings/workspaces/:policyID/distance-rates/:rateID/tax-rate/edit', + getRoute: (policyID: string, rateID: string) => `settings/workspaces/${policyID}/distance-rates/${rateID}/tax-rate/edit` as const, + }, // Referral program promotion REFERRAL_DETAILS_MODAL: { route: 'referral/:contentType', diff --git a/src/SCREENS.ts b/src/SCREENS.ts index d3d62805a8a2..3ead52d64c64 100644 --- a/src/SCREENS.ts +++ b/src/SCREENS.ts @@ -313,6 +313,7 @@ const SCREENS = { DISTANCE_RATE_DETAILS: 'Distance_Rate_Details', DISTANCE_RATE_EDIT: 'Distance_Rate_Edit', DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT: 'Distance_Rate_Tax_Reclaimable_On_Edit', + DISTANCE_RATE_TAX_RATE_EDIT: 'Distance_Rate_Tax_Rate_Edit', }, EDIT_REQUEST: { diff --git a/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx b/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx index 40f550cc69b7..dfd387870ad6 100644 --- a/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx +++ b/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx @@ -241,6 +241,7 @@ const SettingsModalStackNavigator = createModalStackNavigator require('../../../../pages/workspace/distanceRates/PolicyDistanceRateEditPage').default as React.ComponentType, [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage').default as React.ComponentType, + [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RATE_EDIT]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAGS_SETTINGS]: () => require('../../../../pages/workspace/tags/WorkspaceTagsSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAG_SETTINGS]: () => require('../../../../pages/workspace/tags/TagSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAG_LIST_VIEW]: () => require('../../../../pages/workspace/tags/WorkspaceViewTagsPage').default as React.ComponentType, diff --git a/src/libs/Navigation/linkingConfig/FULL_SCREEN_TO_RHP_MAPPING.ts b/src/libs/Navigation/linkingConfig/FULL_SCREEN_TO_RHP_MAPPING.ts index 1fd6e9640233..3f1736d70a13 100755 --- a/src/libs/Navigation/linkingConfig/FULL_SCREEN_TO_RHP_MAPPING.ts +++ b/src/libs/Navigation/linkingConfig/FULL_SCREEN_TO_RHP_MAPPING.ts @@ -80,6 +80,7 @@ const FULL_SCREEN_TO_RHP_MAPPING: Partial> = { SCREENS.WORKSPACE.DISTANCE_RATES_SETTINGS, SCREENS.WORKSPACE.DISTANCE_RATE_EDIT, SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT, + SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RATE_EDIT, SCREENS.WORKSPACE.DISTANCE_RATE_DETAILS, ], }; diff --git a/src/libs/Navigation/linkingConfig/config.ts b/src/libs/Navigation/linkingConfig/config.ts index 9d82c041f8e8..9d27c6d17d71 100644 --- a/src/libs/Navigation/linkingConfig/config.ts +++ b/src/libs/Navigation/linkingConfig/config.ts @@ -416,6 +416,9 @@ const config: LinkingOptions['config'] = { [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT]: { path: ROUTES.WORKSPACE_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT.route, }, + [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RATE_EDIT]: { + path: ROUTES.WORKSPACE_DISTANCE_RATE_TAX_RATE_EDIT.route, + }, [SCREENS.WORKSPACE.TAGS_SETTINGS]: { path: ROUTES.WORKSPACE_TAGS_SETTINGS.route, }, diff --git a/src/libs/Navigation/types.ts b/src/libs/Navigation/types.ts index 1b82422691b2..6d2e7663f9c0 100644 --- a/src/libs/Navigation/types.ts +++ b/src/libs/Navigation/types.ts @@ -220,6 +220,10 @@ type SettingsNavigatorParamList = { policyID: string; rateID: string; }; + [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RATE_EDIT]: { + policyID: string; + rateID: string; + }; [SCREENS.WORKSPACE.TAGS_SETTINGS]: { policyID: string; }; diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 59caca02498b..e4b542d556c5 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -1,6 +1,6 @@ import type {StackScreenProps} from '@react-navigation/stack'; -import React, {useMemo, useState} from 'react'; -import {Keyboard, View} from 'react-native'; +import React, {useState} from 'react'; +import {View} from 'react-native'; import {withOnyx} from 'react-native-onyx'; import type {OnyxEntry} from 'react-native-onyx'; import ConfirmModal from '@components/ConfirmModal'; @@ -27,8 +27,6 @@ import ROUTES from '@src/ROUTES'; import type SCREENS from '@src/SCREENS'; import type * as OnyxTypes from '@src/types/onyx'; import type {Rate} from '@src/types/onyx/Policy'; -import type {ListItemType} from './PolicyDistanceRateTaxRateSelectionModal'; -import PolicyDistanceRateTaxRateSelectionModal from './PolicyDistanceRateTaxRateSelectionModal'; type PolicyDistanceRateDetailsPageOnyxProps = { /** Policy details */ @@ -43,8 +41,6 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const {windowWidth} = useWindowDimensions(); const [isWarningModalVisible, setIsWarningModalVisible] = useState(false); const [isDeleteModalVisible, setIsDeleteModalVisible] = useState(false); - const [isTaxRateSelectionModalVisible, setIsTaxRateSelectionModalVisible] = useState(false); - const policyID = route.params.policyID; const rateID = route.params.rateID; const customUnits = policy?.customUnits ?? {}; @@ -56,17 +52,6 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const isTrackTaxEnabled = customUnit.attributes.taxEnabled; const taxRate = taxRateExternalID ? `${policy?.taxRates?.taxes[taxRateExternalID].name} (${policy?.taxRates?.taxes[taxRateExternalID].value})` : ''; - const taxRateItems: ListItemType[] = useMemo(() => { - const taxes = policy?.taxRates?.taxes; - const result = Object.entries(taxes ?? {}).map(([key, value]) => ({ - value: key, - text: `${value.name} (${value.value})`, - isSelected: taxRateExternalID === key, - keyForList: key, - })); - return result; - }, [policy, taxRateExternalID]); - // Rates can be disabled or deleted as long as in the remaining rates there is always at least one enabled rate and there are no pending delete action const canDisableOrDeleteRate = Object.values(customUnit?.rates).some( (distanceRate: Rate) => distanceRate?.enabled && rateID !== distanceRate?.customUnitRateID && distanceRate?.pendingAction !== CONST.RED_BRICK_ROAD_PENDING_ACTION.DELETE, @@ -83,6 +68,9 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const editTaxReclaimableValue = () => { Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT.getRoute(policyID, rateID)); }; + const editTaxRateValue = () => { + Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_TAX_RATE_EDIT.getRoute(policyID, rateID)); + }; const toggleRate = () => { if (!rate?.enabled || canDisableOrDeleteRate) { @@ -98,20 +86,6 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail setIsDeleteModalVisible(false); }; - const onTaxRateChange = (newTaxRate: ListItemType) => { - Policy.updateDistanceTaxRate(policyID, customUnit, [ - { - ...rate, - attributes: { - ...rate.attributes, - taxRateExternalID: newTaxRate.value, - }, - }, - ]); - setIsTaxRateSelectionModalVisible(false); - Keyboard.dismiss(); - }; - const rateValueToDisplay = CurrencyUtils.convertAmountToDisplayString(rate?.rate, currency); const taxClaimableValueToDisplay = taxClaimablePercentage && rate.rate ? `${CurrencyUtils.getLocalizedCurrencySymbol(currency)}${((taxClaimablePercentage * rate.rate) / 100).toFixed(1)}` : ''; @@ -194,13 +168,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail title={taxRate} description={translate('workspace.taxes.taxRate')} shouldShowRightIcon - onPress={() => setIsTaxRateSelectionModalVisible(true)} - /> - setIsTaxRateSelectionModalVisible(false)} + onPress={editTaxRateValue} /> diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx new file mode 100644 index 000000000000..2fbd80bf7dbb --- /dev/null +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx @@ -0,0 +1,104 @@ +import type {StackScreenProps} from '@react-navigation/stack'; +import React, {useMemo} from 'react'; +import {Keyboard} from 'react-native'; +import {withOnyx} from 'react-native-onyx'; +import type {OnyxEntry} from 'react-native-onyx'; +import HeaderWithBackButton from '@components/HeaderWithBackButton'; +import ScreenWrapper from '@components/ScreenWrapper'; +import SelectionList from '@components/SelectionList'; +import RadioListItem from '@components/SelectionList/RadioListItem'; +import useLocalize from '@hooks/useLocalize'; +import useThemeStyles from '@hooks/useThemeStyles'; +import Navigation from '@libs/Navigation/Navigation'; +import type {SettingsNavigatorParamList} from '@navigation/types'; +import AccessOrNotFoundWrapper from '@pages/workspace/AccessOrNotFoundWrapper'; +import * as Policy from '@userActions/Policy/Policy'; +import CONST from '@src/CONST'; +import ONYXKEYS from '@src/ONYXKEYS'; +import ROUTES from '@src/ROUTES'; +import type SCREENS from '@src/SCREENS'; +import type * as OnyxTypes from '@src/types/onyx'; + +type ListItemType = { + value: string; + text: string; + isSelected: boolean; + keyForList: string; +}; + +type PolicyDistanceRateTaxRateEditPageOnyxProps = { + /** Policy details */ + policy: OnyxEntry; +}; + +type PolicyDistanceRateTaxRateEditPageProps = PolicyDistanceRateTaxRateEditPageOnyxProps & StackScreenProps; + +function PolicyDistanceRateTaxRateEditPage({policy, route}: PolicyDistanceRateTaxRateEditPageProps) { + const styles = useThemeStyles(); + const {translate} = useLocalize(); + const policyID = route.params.policyID; + const rateID = route.params.rateID; + const customUnits = policy?.customUnits ?? {}; + const customUnit = customUnits[Object.keys(customUnits)[0]]; + const rate = customUnit?.rates[rateID]; + const taxRateExternalID = rate.attributes?.taxRateExternalID; + const taxRateItems: ListItemType[] = useMemo(() => { + const taxes = policy?.taxRates?.taxes; + const result = Object.entries(taxes ?? {}).map(([key, value]) => ({ + value: key, + text: `${value.name} (${value.value})`, + isSelected: taxRateExternalID === key, + keyForList: key, + })); + return result; + }, [policy, taxRateExternalID]); + + const onTaxRateChange = (newTaxRate: ListItemType) => { + Policy.updateDistanceTaxRate(policyID, customUnit, [ + { + ...rate, + attributes: { + ...rate.attributes, + taxRateExternalID: newTaxRate.value, + }, + }, + ]); + Keyboard.dismiss(); + Navigation.navigate(ROUTES.WORKSPACE_DISTANCE_RATE_DETAILS.getRoute(policyID, rateID)); + }; + + return ( + + + Navigation.goBack()} + /> + item.isSelected)?.keyForList} + /> + + + ); +} + +PolicyDistanceRateTaxRateEditPage.displayName = 'PolicyDistanceRateTaxRateEditPage'; + +export default withOnyx({ + policy: { + key: ({route}) => `${ONYXKEYS.COLLECTION.POLICY}${route.params.policyID}`, + }, +})(PolicyDistanceRateTaxRateEditPage); diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx deleted file mode 100644 index 627ab6d1c6a7..000000000000 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateSelectionModal.tsx +++ /dev/null @@ -1,66 +0,0 @@ -import React from 'react'; -import HeaderWithBackButton from '@components/HeaderWithBackButton'; -import Modal from '@components/Modal'; -import ScreenWrapper from '@components/ScreenWrapper'; -import SelectionList from '@components/SelectionList'; -import RadioListItem from '@components/SelectionList/RadioListItem'; -import useLocalize from '@hooks/useLocalize'; -import CONST from '@src/CONST'; - -type ListItemType = { - value: string; - text: string; - isSelected: boolean; - keyForList: string; -}; - -type PolicyDistanceRateTaxRateSelectionModalProps = { - /** Whether the modal is visible */ - isVisible: boolean; - - /** The list of items to render */ - items: ListItemType[]; - - /** Function to call when the user selects a role */ - onTaxRateChange: ({value}: ListItemType) => void; - - /** Function to call when the user closes the role selection modal */ - onClose: () => void; -}; - -function PolicyDistanceRateTaxRateSelectionModal({isVisible, items, onTaxRateChange, onClose = () => {}}: PolicyDistanceRateTaxRateSelectionModalProps) { - const {translate} = useLocalize(); - - return ( - - - - item.isSelected)?.keyForList} - /> - - - ); -} - -PolicyDistanceRateTaxRateSelectionModal.displayName = 'PolicyDistanceRateTaxRateSelectionModal'; - -export type {ListItemType}; - -export default PolicyDistanceRateTaxRateSelectionModal; diff --git a/src/pages/workspace/taxes/WorkspaceTaxesSettingsWorkspaceCurrency.tsx b/src/pages/workspace/taxes/WorkspaceTaxesSettingsWorkspaceCurrency.tsx index ebb479bee4b7..b13c327bae4c 100644 --- a/src/pages/workspace/taxes/WorkspaceTaxesSettingsWorkspaceCurrency.tsx +++ b/src/pages/workspace/taxes/WorkspaceTaxesSettingsWorkspaceCurrency.tsx @@ -37,7 +37,6 @@ function WorkspaceTaxesSettingsWorkspaceCurrency({ setWorkspaceCurrencyDefault(policyID, taxes.code ?? ''); Navigation.goBack(ROUTES.WORKSPACE_TAXES_SETTINGS.getRoute(policyID)); }; - return ( Date: Fri, 31 May 2024 15:40:29 +0700 Subject: [PATCH 16/37] fix: navigate to more features --- .../distanceRates/PolicyDistanceRatesSettingsPage.tsx | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index 0332c73e274c..7e3ac82d815e 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -138,7 +138,10 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli {translate('workspace.distanceRates.taxFeatureNotEnabledMessage')} Navigation.navigate(ROUTES.WORKSPACE_MORE_FEATURES.getRoute(policyID))} + onPress={() => { + Navigation.dismissModal(); + Navigation.navigate(ROUTES.WORKSPACE_MORE_FEATURES.getRoute(policyID)); + }} > {translate('workspace.common.moreFeatures')} From 6a914198a5b76d35887eea2bdcf3a9ff3cf33f71 Mon Sep 17 00:00:00 2001 From: nkdengineer <161821005+nkdengineer@users.noreply.github.com> Date: Mon, 3 Jun 2024 10:13:52 +0700 Subject: [PATCH 17/37] Update src/languages/en.ts Co-authored-by: Eugene Voloshchak --- src/languages/en.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/src/languages/en.ts b/src/languages/en.ts index 6d02618d52e7..33c54f5471db 100755 --- a/src/languages/en.ts +++ b/src/languages/en.ts @@ -2192,7 +2192,6 @@ export default { delete: 'Delete field', deleteConfirmation: 'Are you sure that you want to delete this field?', }, - tags: { tagName: 'Tag name', requiresTag: 'Members must tag all expenses', From 6c84870ed00088cbda0e142f3d0d8194580e78e5 Mon Sep 17 00:00:00 2001 From: nkdengineer <161821005+nkdengineer@users.noreply.github.com> Date: Mon, 3 Jun 2024 10:14:17 +0700 Subject: [PATCH 18/37] Update src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx Co-authored-by: Eugene Voloshchak --- .../workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index 7e3ac82d815e..5662b4f29de3 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -46,7 +46,7 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli const customUnits = policy?.customUnits ?? {}; const customUnit = customUnits[Object.keys(customUnits)[0]]; const customUnitID = customUnit?.customUnitID ?? ''; - const isTrackTaxEnabled = customUnit.attributes.taxEnabled; + const isTrackTaxEnabled = customUnit?.attributes?.taxEnabled; const defaultCategory = customUnits[customUnitID]?.defaultCategory; const defaultUnit = customUnits[customUnitID]?.attributes.unit; From 624c4aacf581d043c606b079b3a60c288b4bbeeb Mon Sep 17 00:00:00 2001 From: nkdengineer <161821005+nkdengineer@users.noreply.github.com> Date: Mon, 3 Jun 2024 10:14:31 +0700 Subject: [PATCH 19/37] Update src/languages/es.ts Co-authored-by: Eugene Voloshchak --- src/languages/es.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/src/languages/es.ts b/src/languages/es.ts index b936186fcb4f..d1004d8d5888 100644 --- a/src/languages/es.ts +++ b/src/languages/es.ts @@ -2228,7 +2228,6 @@ export default { delete: 'Eliminar campos', deleteConfirmation: '¿Estás seguro de que quieres eliminar esta campos?', }, - tags: { tagName: 'Nombre de etiqueta', requiresTag: 'Los miembros deben etiquetar todos los gastos', From e8ae98b2d05373b2221d8b478f9eadd2c0f97213 Mon Sep 17 00:00:00 2001 From: nkdengineer <161821005+nkdengineer@users.noreply.github.com> Date: Mon, 3 Jun 2024 10:19:24 +0700 Subject: [PATCH 20/37] Update src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx Co-authored-by: Eugene Voloshchak --- .../distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx | 1 - 1 file changed, 1 deletion(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx index 96545e866cf3..0ce5268c0a2b 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -74,7 +74,6 @@ function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDista Navigation.goBack()} /> Date: Mon, 3 Jun 2024 10:19:48 +0700 Subject: [PATCH 21/37] Update src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx Co-authored-by: Eugene Voloshchak --- .../distanceRates/PolicyDistanceRateTaxRateEditPage.tsx | 1 - 1 file changed, 1 deletion(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx index 2fbd80bf7dbb..c1b503ade309 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx @@ -82,7 +82,6 @@ function PolicyDistanceRateTaxRateEditPage({policy, route}: PolicyDistanceRateTa Navigation.goBack()} /> Date: Mon, 3 Jun 2024 10:48:59 +0700 Subject: [PATCH 22/37] fix lint and remove useless files --- .../UpdatePolicyDistanceTaxRateValueParams.ts | 7 ------- .../UpdatePolicyTaxClaimableValueParams.ts | 7 ------- src/libs/API/parameters/index.ts | 2 -- src/libs/API/types.ts | 4 ++-- src/libs/actions/Policy/Policy.ts | 6 ++---- .../PolicyDistanceRateTaxRateEditPage.tsx | 19 ++++--------------- ...cyDistanceRateTaxReclaimableOnEditPage.tsx | 19 ++++--------------- ...orkspaceTaxesSettingsWorkspaceCurrency.tsx | 1 + 8 files changed, 13 insertions(+), 52 deletions(-) delete mode 100644 src/libs/API/parameters/UpdatePolicyDistanceTaxRateValueParams.ts delete mode 100644 src/libs/API/parameters/UpdatePolicyTaxClaimableValueParams.ts diff --git a/src/libs/API/parameters/UpdatePolicyDistanceTaxRateValueParams.ts b/src/libs/API/parameters/UpdatePolicyDistanceTaxRateValueParams.ts deleted file mode 100644 index d78738ee9750..000000000000 --- a/src/libs/API/parameters/UpdatePolicyDistanceTaxRateValueParams.ts +++ /dev/null @@ -1,7 +0,0 @@ -type UpdatePolicyDistanceTaxRateValueParams = { - policyID: string; - customUnitID: string; - customUnitRateArray: string; -}; - -export default UpdatePolicyDistanceTaxRateValueParams; diff --git a/src/libs/API/parameters/UpdatePolicyTaxClaimableValueParams.ts b/src/libs/API/parameters/UpdatePolicyTaxClaimableValueParams.ts deleted file mode 100644 index 8b227f94414a..000000000000 --- a/src/libs/API/parameters/UpdatePolicyTaxClaimableValueParams.ts +++ /dev/null @@ -1,7 +0,0 @@ -type UpdatePolicyTaxClaimableValueParams = { - policyID: string; - customUnitID: string; - customUnitRateArray: string; -}; - -export default UpdatePolicyTaxClaimableValueParams; diff --git a/src/libs/API/parameters/index.ts b/src/libs/API/parameters/index.ts index 05a5d56e2c77..52f130a28dd1 100644 --- a/src/libs/API/parameters/index.ts +++ b/src/libs/API/parameters/index.ts @@ -195,8 +195,6 @@ export type {default as CreatePolicyDistanceRateParams} from './CreatePolicyDist export type {default as SetPolicyDistanceRatesUnitParams} from './SetPolicyDistanceRatesUnitParams'; export type {default as SetPolicyDistanceRatesDefaultCategoryParams} from './SetPolicyDistanceRatesDefaultCategoryParams'; export type {default as UpdatePolicyDistanceRateValueParams} from './UpdatePolicyDistanceRateValueParams'; -export type {default as UpdatePolicyDistanceTaxRateValueParams} from './UpdatePolicyDistanceTaxRateValueParams'; -export type {default as UpdatePolicyTaxClaimableValueParams} from './UpdatePolicyTaxClaimableValueParams'; export type {default as SetPolicyDistanceRatesEnabledParams} from './SetPolicyDistanceRatesEnabledParams'; export type {default as DeletePolicyDistanceRatesParams} from './DeletePolicyDistanceRatesParams'; export type {default as CreatePolicyTagsParams} from './CreatePolicyTagsParams'; diff --git a/src/libs/API/types.ts b/src/libs/API/types.ts index f3b03bc60b4c..746daad3bbd5 100644 --- a/src/libs/API/types.ts +++ b/src/libs/API/types.ts @@ -430,8 +430,8 @@ type WriteCommandParameters = { [WRITE_COMMANDS.UPDATE_MANY_POLICY_CONNECTION_CONFIGS]: Parameters.UpdateManyPolicyConnectionConfigurationsParams; [WRITE_COMMANDS.REMOVE_POLICY_CONNECTION]: Parameters.RemovePolicyConnectionParams; [WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_RATE_VALUE]: Parameters.UpdatePolicyDistanceRateValueParams; - [WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_TAX_RATE_VALUE]: Parameters.UpdatePolicyDistanceTaxRateValueParams; - [WRITE_COMMANDS.UPDATE_DISTANCE_TAX_CLAIMABLE_VALUE]: Parameters.UpdatePolicyTaxClaimableValueParams; + [WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_TAX_RATE_VALUE]: Parameters.UpdatePolicyDistanceRateValueParams; + [WRITE_COMMANDS.UPDATE_DISTANCE_TAX_CLAIMABLE_VALUE]: Parameters.UpdatePolicyDistanceRateValueParams; [WRITE_COMMANDS.SET_POLICY_DISTANCE_RATES_ENABLED]: Parameters.SetPolicyDistanceRatesEnabledParams; [WRITE_COMMANDS.DELETE_POLICY_DISTANCE_RATES]: Parameters.DeletePolicyDistanceRatesParams; [WRITE_COMMANDS.DISMISS_TRACK_EXPENSE_ACTIONABLE_WHISPER]: Parameters.DismissTrackExpenseActionableWhisperParams; diff --git a/src/libs/actions/Policy/Policy.ts b/src/libs/actions/Policy/Policy.ts index 792c3f27b47c..ae1af7951fbf 100644 --- a/src/libs/actions/Policy/Policy.ts +++ b/src/libs/actions/Policy/Policy.ts @@ -42,8 +42,6 @@ import type { SetWorkspacePayerParams, SetWorkspaceReimbursementParams, UpdatePolicyDistanceRateValueParams, - UpdatePolicyDistanceTaxRateValueParams, - UpdatePolicyTaxClaimableValueParams, UpdateWorkspaceAvatarParams, UpdateWorkspaceCustomUnitAndRateParams, UpdateWorkspaceDescriptionParams, @@ -3975,7 +3973,7 @@ function updateDistanceTaxClaimableValue(policyID: string, customUnit: CustomUni }, ]; - const params: UpdatePolicyTaxClaimableValueParams = { + const params: UpdatePolicyDistanceRateValueParams = { policyID, customUnitID: customUnit.customUnitID, customUnitRateArray: JSON.stringify(prepareCustomUnitRatesArray(customUnitRates)), @@ -4046,7 +4044,7 @@ function updateDistanceTaxRate(policyID: string, customUnit: CustomUnit, customU }, ]; - const params: UpdatePolicyDistanceTaxRateValueParams = { + const params: UpdatePolicyDistanceRateValueParams = { policyID, customUnitID: customUnit.customUnitID, customUnitRateArray: JSON.stringify(prepareCustomUnitRatesArray(customUnitRates)), diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx index c1b503ade309..a779e762a224 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx @@ -1,8 +1,6 @@ import type {StackScreenProps} from '@react-navigation/stack'; import React, {useMemo} from 'react'; import {Keyboard} from 'react-native'; -import {withOnyx} from 'react-native-onyx'; -import type {OnyxEntry} from 'react-native-onyx'; import HeaderWithBackButton from '@components/HeaderWithBackButton'; import ScreenWrapper from '@components/ScreenWrapper'; import SelectionList from '@components/SelectionList'; @@ -12,12 +10,12 @@ import useThemeStyles from '@hooks/useThemeStyles'; import Navigation from '@libs/Navigation/Navigation'; import type {SettingsNavigatorParamList} from '@navigation/types'; import AccessOrNotFoundWrapper from '@pages/workspace/AccessOrNotFoundWrapper'; +import type {WithPolicyOnyxProps} from '@pages/workspace/withPolicy'; +import withPolicy from '@pages/workspace/withPolicy'; import * as Policy from '@userActions/Policy/Policy'; import CONST from '@src/CONST'; -import ONYXKEYS from '@src/ONYXKEYS'; import ROUTES from '@src/ROUTES'; import type SCREENS from '@src/SCREENS'; -import type * as OnyxTypes from '@src/types/onyx'; type ListItemType = { value: string; @@ -26,12 +24,7 @@ type ListItemType = { keyForList: string; }; -type PolicyDistanceRateTaxRateEditPageOnyxProps = { - /** Policy details */ - policy: OnyxEntry; -}; - -type PolicyDistanceRateTaxRateEditPageProps = PolicyDistanceRateTaxRateEditPageOnyxProps & StackScreenProps; +type PolicyDistanceRateTaxRateEditPageProps = WithPolicyOnyxProps & StackScreenProps; function PolicyDistanceRateTaxRateEditPage({policy, route}: PolicyDistanceRateTaxRateEditPageProps) { const styles = useThemeStyles(); @@ -96,8 +89,4 @@ function PolicyDistanceRateTaxRateEditPage({policy, route}: PolicyDistanceRateTa PolicyDistanceRateTaxRateEditPage.displayName = 'PolicyDistanceRateTaxRateEditPage'; -export default withOnyx({ - policy: { - key: ({route}) => `${ONYXKEYS.COLLECTION.POLICY}${route.params.policyID}`, - }, -})(PolicyDistanceRateTaxRateEditPage); +export default withPolicy(PolicyDistanceRateTaxRateEditPage); diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx index 0ce5268c0a2b..f76e068c5949 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -1,8 +1,6 @@ import type {StackScreenProps} from '@react-navigation/stack'; import React, {useCallback} from 'react'; import {Keyboard} from 'react-native'; -import {withOnyx} from 'react-native-onyx'; -import type {OnyxEntry} from 'react-native-onyx'; import AmountForm from '@components/AmountForm'; import FormProvider from '@components/Form/FormProvider'; import InputWrapperWithRef from '@components/Form/InputWrapper'; @@ -16,20 +14,15 @@ import Navigation from '@libs/Navigation/Navigation'; import {validateTaxClaimableValue} from '@libs/PolicyDistanceRatesUtils'; import type {SettingsNavigatorParamList} from '@navigation/types'; import AccessOrNotFoundWrapper from '@pages/workspace/AccessOrNotFoundWrapper'; +import type {WithPolicyOnyxProps} from '@pages/workspace/withPolicy'; +import withPolicy from '@pages/workspace/withPolicy'; import * as Policy from '@userActions/Policy/Policy'; import CONST from '@src/CONST'; import ONYXKEYS from '@src/ONYXKEYS'; import type SCREENS from '@src/SCREENS'; import INPUT_IDS from '@src/types/form/PolicyDistanceRateTaxReclaimableOnEditForm'; -import type * as OnyxTypes from '@src/types/onyx'; -type PolicyDistanceRateTaxReclaimableOnEditPageOnyxProps = { - /** Policy details */ - policy: OnyxEntry; -}; - -type PolicyDistanceRateTaxReclaimableOnEditPageProps = PolicyDistanceRateTaxReclaimableOnEditPageOnyxProps & - StackScreenProps; +type PolicyDistanceRateTaxReclaimableOnEditPageProps = WithPolicyOnyxProps & StackScreenProps; function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDistanceRateTaxReclaimableOnEditPageProps) { const styles = useThemeStyles(); @@ -104,8 +97,4 @@ function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDista PolicyDistanceRateTaxReclaimableOnEditPage.displayName = 'PolicyDistanceRateTaxReclaimableOnEditPage'; -export default withOnyx({ - policy: { - key: ({route}) => `${ONYXKEYS.COLLECTION.POLICY}${route.params.policyID}`, - }, -})(PolicyDistanceRateTaxReclaimableOnEditPage); +export default withPolicy(PolicyDistanceRateTaxReclaimableOnEditPage); diff --git a/src/pages/workspace/taxes/WorkspaceTaxesSettingsWorkspaceCurrency.tsx b/src/pages/workspace/taxes/WorkspaceTaxesSettingsWorkspaceCurrency.tsx index b13c327bae4c..ebb479bee4b7 100644 --- a/src/pages/workspace/taxes/WorkspaceTaxesSettingsWorkspaceCurrency.tsx +++ b/src/pages/workspace/taxes/WorkspaceTaxesSettingsWorkspaceCurrency.tsx @@ -37,6 +37,7 @@ function WorkspaceTaxesSettingsWorkspaceCurrency({ setWorkspaceCurrencyDefault(policyID, taxes.code ?? ''); Navigation.goBack(ROUTES.WORKSPACE_TAXES_SETTINGS.getRoute(policyID)); }; + return ( Date: Mon, 3 Jun 2024 11:09:13 +0700 Subject: [PATCH 23/37] fix typecheck --- .../distanceRates/PolicyDistanceRateTaxRateEditPage.tsx | 2 +- .../PolicyDistanceRateTaxReclaimableOnEditPage.tsx | 2 +- src/pages/workspace/withPolicy.tsx | 2 ++ 3 files changed, 4 insertions(+), 2 deletions(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx index a779e762a224..3b318c82b5d3 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage.tsx @@ -26,7 +26,7 @@ type ListItemType = { type PolicyDistanceRateTaxRateEditPageProps = WithPolicyOnyxProps & StackScreenProps; -function PolicyDistanceRateTaxRateEditPage({policy, route}: PolicyDistanceRateTaxRateEditPageProps) { +function PolicyDistanceRateTaxRateEditPage({route, policy}: PolicyDistanceRateTaxRateEditPageProps) { const styles = useThemeStyles(); const {translate} = useLocalize(); const policyID = route.params.policyID; diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx index f76e068c5949..0c61760d93ad 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx @@ -24,7 +24,7 @@ import INPUT_IDS from '@src/types/form/PolicyDistanceRateTaxReclaimableOnEditFor type PolicyDistanceRateTaxReclaimableOnEditPageProps = WithPolicyOnyxProps & StackScreenProps; -function PolicyDistanceRateTaxReclaimableOnEditPage({policy, route}: PolicyDistanceRateTaxReclaimableOnEditPageProps) { +function PolicyDistanceRateTaxReclaimableOnEditPage({route, policy}: PolicyDistanceRateTaxReclaimableOnEditPageProps) { const styles = useThemeStyles(); const {translate} = useLocalize(); const {inputCallbackRef} = useAutoFocusInput(); diff --git a/src/pages/workspace/withPolicy.tsx b/src/pages/workspace/withPolicy.tsx index 56ad756194a0..86d48facc386 100644 --- a/src/pages/workspace/withPolicy.tsx +++ b/src/pages/workspace/withPolicy.tsx @@ -39,6 +39,8 @@ type PolicyRoute = RouteProp< | typeof SCREENS.WORKSPACE.OWNER_CHANGE_CHECK | typeof SCREENS.WORKSPACE.TAX_EDIT | typeof SCREENS.WORKSPACE.ADDRESS + | typeof SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RATE_EDIT + | typeof SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT >; function getPolicyIDFromRoute(route: PolicyRoute): string { From a5f6d4914c42bdb4cd99cf575bc9bb37bc71a4d8 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 4 Jun 2024 13:54:46 +0700 Subject: [PATCH 24/37] rename variable and clean code --- src/libs/actions/Policy/Policy.ts | 76 ++++++++++--------- .../PolicyDistanceRateDetailsPage.tsx | 6 +- .../PolicyDistanceRatesSettingsPage.tsx | 9 ++- 3 files changed, 48 insertions(+), 43 deletions(-) diff --git a/src/libs/actions/Policy/Policy.ts b/src/libs/actions/Policy/Policy.ts index ae1af7951fbf..9c8d1469bfdf 100644 --- a/src/libs/actions/Policy/Policy.ts +++ b/src/libs/actions/Policy/Policy.ts @@ -3848,16 +3848,17 @@ function updatePolicyDistanceRateValue(policyID: string, customUnit: CustomUnit, const rateIDs = customUnitRates.map((rate) => rate.customUnitRateID); for (const rateID of Object.keys(customUnit.rates)) { - if (rateIDs.includes(rateID)) { - const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); - optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; - successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; - failureRates[rateID] = { - ...currentRates[rateID], - pendingFields: {rate: null}, - errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, - }; + if (!rateIDs.includes(rateID)) { + return; } + const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); + optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; + successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; + failureRates[rateID] = { + ...currentRates[rateID], + pendingFields: {rate: null}, + errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, + }; } const optimisticData: OnyxUpdate[] = [ @@ -3919,16 +3920,17 @@ function updateDistanceTaxClaimableValue(policyID: string, customUnit: CustomUni const rateIDs = customUnitRates.map((rate) => rate.customUnitRateID); for (const rateID of Object.keys(customUnit.rates)) { - if (rateIDs.includes(rateID)) { - const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); - optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; - successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; - failureRates[rateID] = { - ...currentRates[rateID], - pendingFields: {rate: null}, - errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, - }; + if (!rateIDs.includes(rateID)) { + return; } + const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); + optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; + successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; + failureRates[rateID] = { + ...currentRates[rateID], + pendingFields: {rate: null}, + errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, + }; } const optimisticData: OnyxUpdate[] = [ @@ -3990,16 +3992,17 @@ function updateDistanceTaxRate(policyID: string, customUnit: CustomUnit, customU const rateIDs = customUnitRates.map((rate) => rate.customUnitRateID); for (const rateID of Object.keys(customUnit.rates)) { - if (rateIDs.includes(rateID)) { - const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); - optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; - successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; - failureRates[rateID] = { - ...currentRates[rateID], - pendingFields: {rate: null}, - errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, - }; + if (!rateIDs.includes(rateID)) { + return; } + const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); + optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; + successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; + failureRates[rateID] = { + ...currentRates[rateID], + pendingFields: {rate: null}, + errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, + }; } const optimisticData: OnyxUpdate[] = [ @@ -4061,16 +4064,17 @@ function setPolicyDistanceRatesEnabled(policyID: string, customUnit: CustomUnit, const rateIDs = customUnitRates.map((rate) => rate.customUnitRateID); for (const rateID of Object.keys(currentRates)) { - if (rateIDs.includes(rateID)) { - const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); - optimisticRates[rateID] = {...foundRate, pendingFields: {enabled: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; - successRates[rateID] = {...foundRate, pendingFields: {enabled: null}}; - failureRates[rateID] = { - ...currentRates[rateID], - pendingFields: {enabled: null}, - errorFields: {enabled: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, - }; + if (!rateIDs.includes(rateID)) { + return; } + const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); + optimisticRates[rateID] = {...foundRate, pendingFields: {enabled: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; + successRates[rateID] = {...foundRate, pendingFields: {enabled: null}}; + failureRates[rateID] = { + ...currentRates[rateID], + pendingFields: {enabled: null}, + errorFields: {enabled: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, + }; } const optimisticData: OnyxUpdate[] = [ diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index e4b542d556c5..ccf97b267436 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -50,7 +50,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const taxClaimablePercentage = rate.attributes?.taxClaimablePercentage; const taxRateExternalID = rate.attributes?.taxRateExternalID; - const isTrackTaxEnabled = customUnit.attributes.taxEnabled; + const isDistanceTrackTaxEnabled = customUnit?.attributes?.taxEnabled; const taxRate = taxRateExternalID ? `${policy?.taxRates?.taxes[taxRateExternalID].name} (${policy?.taxRates?.taxes[taxRateExternalID].value})` : ''; // Rates can be disabled or deleted as long as in the remaining rates there is always at least one enabled rate and there are no pending delete action const canDisableOrDeleteRate = Object.values(customUnit?.rates).some( @@ -156,7 +156,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail onPress={editRateValue} /> - {isTrackTaxEnabled && ( + {isDistanceTrackTaxEnabled && ( )} - {isTrackTaxEnabled && ( + {isDistanceTrackTaxEnabled && ( {translate('workspace.distanceRates.trackTax')} - {!policy?.tax?.trackingEnabled && ( + {!isPolicyTrackTaxEnabled && ( Date: Tue, 4 Jun 2024 14:00:19 +0700 Subject: [PATCH 25/37] fix chore --- .../workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index 4660a17b96e4..24365ddce225 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -47,7 +47,7 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli const customUnit = customUnits[Object.keys(customUnits)[0]]; const customUnitID = customUnit?.customUnitID ?? ''; const isDistanceTrackTaxEnabled = customUnit?.attributes?.taxEnabled; - const isPolicyTrackTaxEnabled = !policy?.tax?.trackingEnabled; + const isPolicyTrackTaxEnabled = policy?.tax?.trackingEnabled; const defaultCategory = customUnits[customUnitID]?.defaultCategory; const defaultUnit = customUnits[customUnitID]?.attributes.unit; From 860252ce8735c32abd7777a622cbe87444703fd0 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 4 Jun 2024 14:09:54 +0700 Subject: [PATCH 26/37] fix bug distance rates detail page isn't scrollable --- .../PolicyDistanceRateDetailsPage.tsx | 151 +++++++++--------- .../PolicyDistanceRatesSettingsPage.tsx | 113 ++++++------- 2 files changed, 135 insertions(+), 129 deletions(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index ccf97b267436..fd1d65159cef 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -9,6 +9,7 @@ import * as Expensicons from '@components/Icon/Expensicons'; import MenuItemWithTopDescription from '@components/MenuItemWithTopDescription'; import OfflineWithFeedback from '@components/OfflineWithFeedback'; import ScreenWrapper from '@components/ScreenWrapper'; +import ScrollView from '@components/ScrollView'; import Switch from '@components/Switch'; import Text from '@components/Text'; import useLocalize from '@hooks/useLocalize'; @@ -120,94 +121,96 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail includeSafeAreaPaddingBottom={false} style={[styles.defaultModalContainer]} > - - - clearErrorFields('enabled')} - > - - {translate('workspace.distanceRates.enableRate')} - - - - clearErrorFields('rate')} - > - - - {isDistanceTrackTaxEnabled && ( + + + clearErrorFields('attributes')} + onClose={() => clearErrorFields('enabled')} > - - + {translate('workspace.distanceRates.enableRate')} + - )} - {isDistanceTrackTaxEnabled && ( clearErrorFields('attributes')} + onClose={() => clearErrorFields('rate')} > - )} - setIsWarningModalVisible(false)} - isVisible={isWarningModalVisible} - title={translate('workspace.distanceRates.oopsNotSoFast')} - prompt={translate('workspace.distanceRates.workspaceNeeds')} - confirmText={translate('common.buttonConfirm')} - shouldShowCancelButton={false} - /> - setIsDeleteModalVisible(false)} - prompt={translate('workspace.distanceRates.areYouSureDelete', {count: 1})} - confirmText={translate('common.delete')} - cancelText={translate('common.cancel')} - danger - /> - + {isDistanceTrackTaxEnabled && ( + clearErrorFields('attributes')} + > + + + + + )} + {isDistanceTrackTaxEnabled && ( + clearErrorFields('attributes')} + > + + + )} + setIsWarningModalVisible(false)} + isVisible={isWarningModalVisible} + title={translate('workspace.distanceRates.oopsNotSoFast')} + prompt={translate('workspace.distanceRates.workspaceNeeds')} + confirmText={translate('common.buttonConfirm')} + shouldShowCancelButton={false} + /> + setIsDeleteModalVisible(false)} + prompt={translate('workspace.distanceRates.areYouSureDelete', {count: 1})} + confirmText={translate('common.delete')} + cancelText={translate('common.cancel')} + danger + /> + + ); diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index 24365ddce225..b8d36cafe71c 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -6,6 +6,7 @@ import {withOnyx} from 'react-native-onyx'; import HeaderWithBackButton from '@components/HeaderWithBackButton'; import OfflineWithFeedback from '@components/OfflineWithFeedback'; import ScreenWrapper from '@components/ScreenWrapper'; +import ScrollView from '@components/ScrollView'; import type {ListItem} from '@components/SelectionList/types'; import Switch from '@components/Switch'; import Text from '@components/Text'; @@ -87,71 +88,73 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli style={[styles.defaultModalContainer]} testID={PolicyDistanceRatesSettingsPage.displayName} > - - - clearErrorFields('attributes')} - > - - - {policy?.areCategoriesEnabled && OptionsListUtils.hasEnabledOptions(policyCategories ?? {}) && ( + + + clearErrorFields('defaultCategory')} + onClose={() => clearErrorFields('attributes')} > - - )} - - - - {translate('workspace.distanceRates.trackTax')} - clearErrorFields('defaultCategory')} + > + + + )} + + + + {translate('workspace.distanceRates.trackTax')} + + - - {!isPolicyTrackTaxEnabled && ( - - - {translate('workspace.distanceRates.taxFeatureNotEnabledMessage')} - + { - Navigation.dismissModal(); - Navigation.navigate(ROUTES.WORKSPACE_MORE_FEATURES.getRoute(policyID)); - }} > - {translate('workspace.common.moreFeatures')} - - {translate('workspace.distanceRates.changePromptMessage')} - - - )} - - + {translate('workspace.distanceRates.taxFeatureNotEnabledMessage')} + { + Navigation.dismissModal(); + Navigation.navigate(ROUTES.WORKSPACE_MORE_FEATURES.getRoute(policyID)); + }} + > + {translate('workspace.common.moreFeatures')} + + {translate('workspace.distanceRates.changePromptMessage')} + + + )} + + + ); From 903f9f53b302e34f277ad4bb9f57e2f5e4186b53 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 4 Jun 2024 16:11:22 +0700 Subject: [PATCH 27/37] fix ts error --- src/libs/actions/Policy/Policy.ts | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/libs/actions/Policy/Policy.ts b/src/libs/actions/Policy/Policy.ts index ec507234339c..cbdd8f2ef683 100644 --- a/src/libs/actions/Policy/Policy.ts +++ b/src/libs/actions/Policy/Policy.ts @@ -1403,7 +1403,9 @@ function addMembersToWorkspace(invitedEmailsToAccountIDs: InvitedEmailsToAccount // Convert to object with each key containing the error. We don’t // need to remove the members since that is handled by onClose of OfflineWithFeedback. - value: failureMembersState, + value: { + employeeList: failureMembersState, + }, }, ...membersChats.onyxFailureData, ...announceRoomMembers.onyxFailureData, From 6491b8f8f54312c0f78549b044e31ade1ab9b1bb Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 4 Jun 2024 17:49:48 +0700 Subject: [PATCH 28/37] fixed header message and clean code --- .../PolicyDistanceRateDetailsPage.tsx | 14 +++++++------- .../PolicyDistanceRatesSettingsPage.tsx | 8 ++++---- 2 files changed, 11 insertions(+), 11 deletions(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 5d96d249c4ee..7469bdf0cca9 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -51,7 +51,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const taxClaimablePercentage = rate.attributes?.taxClaimablePercentage; const taxRateExternalID = rate.attributes?.taxRateExternalID; - const isDistanceTrackTaxEnabled = customUnit?.attributes?.taxEnabled; + const isDistanceTrackTaxEnabled = Boolean(customUnit?.attributes?.taxEnabled); const taxRate = taxRateExternalID ? `${policy?.taxRates?.taxes[taxRateExternalID].name} (${policy?.taxRates?.taxes[taxRateExternalID].value})` : ''; // Rates can be disabled or deleted as long as in the remaining rates there is always at least one enabled rate and there are no pending delete action const canDisableOrDeleteRate = Object.values(customUnit?.rates ?? {}).some( @@ -121,13 +121,13 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail includeSafeAreaPaddingBottom={false} style={[styles.defaultModalContainer]} > + - + - {translate('workspace.distanceRates.trackTax')} Date: Tue, 4 Jun 2024 18:01:24 +0700 Subject: [PATCH 29/37] remove Boolean --- .../distanceRates/PolicyDistanceRateDetailsPage.tsx | 2 +- .../distanceRates/PolicyDistanceRatesSettingsPage.tsx | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 7469bdf0cca9..0187b15bc79c 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -51,7 +51,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail const taxClaimablePercentage = rate.attributes?.taxClaimablePercentage; const taxRateExternalID = rate.attributes?.taxRateExternalID; - const isDistanceTrackTaxEnabled = Boolean(customUnit?.attributes?.taxEnabled); + const isDistanceTrackTaxEnabled = !!customUnit?.attributes?.taxEnabled; const taxRate = taxRateExternalID ? `${policy?.taxRates?.taxes[taxRateExternalID].name} (${policy?.taxRates?.taxes[taxRateExternalID].value})` : ''; // Rates can be disabled or deleted as long as in the remaining rates there is always at least one enabled rate and there are no pending delete action const canDisableOrDeleteRate = Object.values(customUnit?.rates ?? {}).some( diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index b8adca547663..b478d4ea4b26 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -47,8 +47,8 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli const customUnits = policy?.customUnits ?? {}; const customUnit = customUnits[Object.keys(customUnits)[0]]; const customUnitID = customUnit?.customUnitID ?? ''; - const isDistanceTrackTaxEnabled = Boolean(customUnit?.attributes?.taxEnabled); - const isPolicyTrackTaxEnabled = Boolean(policy?.tax?.trackingEnabled); + const isDistanceTrackTaxEnabled = !!customUnit?.attributes?.taxEnabled; + const isPolicyTrackTaxEnabled = !!policy?.tax?.trackingEnabled; const defaultCategory = customUnits[customUnitID]?.defaultCategory; const defaultUnit = customUnits[customUnitID]?.attributes.unit; @@ -73,7 +73,7 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli Policy.clearPolicyDistanceRatesErrorFields(policyID, customUnitID, {...errorFields, [fieldName]: null}); }; - const onToggleTrackTax = (isOn: boolean) => { + const onToggleTrackTax = (isOn: !! => { const attributes = {...customUnits[customUnitID].attributes, taxEnabled: isOn}; Policy.enableDistanceRequestTax(policyID, customUnit.name, customUnitID, attributes); }; From 5de43769ab77911c8c67c8d78f8a64785326a3ef Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Tue, 4 Jun 2024 18:04:40 +0700 Subject: [PATCH 30/37] fix typecheck --- .../workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx index b478d4ea4b26..052660805def 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx @@ -73,7 +73,7 @@ function PolicyDistanceRatesSettingsPage({policy, policyCategories, route}: Poli Policy.clearPolicyDistanceRatesErrorFields(policyID, customUnitID, {...errorFields, [fieldName]: null}); }; - const onToggleTrackTax = (isOn: !! => { + const onToggleTrackTax = (isOn: boolean) => { const attributes = {...customUnits[customUnitID].attributes, taxEnabled: isOn}; Policy.enableDistanceRequestTax(policyID, customUnit.name, customUnitID, attributes); }; From 3555f5e80a63c0c18d31711b813b48d2f66081b9 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Wed, 5 Jun 2024 00:36:00 +0700 Subject: [PATCH 31/37] clean code --- .../workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx | 2 +- .../distanceRates/PolicyDistanceRateTaxRateEditPage.tsx | 2 -- .../PolicyDistanceRateTaxReclaimableOnEditPage.tsx | 2 -- .../workspace/distanceRates/PolicyDistanceRatesSettingsPage.tsx | 2 +- 4 files changed, 2 insertions(+), 6 deletions(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 0187b15bc79c..65521ee4408f 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -128,7 +128,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail threeDotsAnchorPosition={styles.threeDotsPopoverOffset(windowWidth)} /> - + - + Date: Wed, 5 Jun 2024 14:50:52 +0700 Subject: [PATCH 32/37] fix typecheck --- src/libs/actions/IOU.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/libs/actions/IOU.ts b/src/libs/actions/IOU.ts index 014ed5da3d48..1d9b3e6ecf2c 100644 --- a/src/libs/actions/IOU.ts +++ b/src/libs/actions/IOU.ts @@ -2253,9 +2253,9 @@ function getTrackExpenseInformation( createdReportActionIDForThread: optimisticCreatedActionForTransactionThread.reportActionID, actionableWhisperReportActionIDParam: actionableTrackExpenseWhisper?.reportActionID ?? '', onyxData: { - optimisticData: [...optimisticData, ...trackExpenseOnyxData[0]], - successData: [...successData, ...trackExpenseOnyxData[1]], - failureData: [...failureData, ...trackExpenseOnyxData[2]], + optimisticData: optimisticData.concat(trackExpenseOnyxData[0]), + successData: successData.concat(trackExpenseOnyxData[1]), + failureData: failureData.concat(trackExpenseOnyxData[2]), }, }; } From 6b08a2257f69299bd8ba5563ba106ee7769aa032 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Wed, 5 Jun 2024 20:27:00 +0700 Subject: [PATCH 33/37] fix related bug --- src/libs/actions/Policy/DistanceRate.ts | 40 +++++++++---------- .../PolicyDistanceRateDetailsPage.tsx | 3 +- 2 files changed, 21 insertions(+), 22 deletions(-) diff --git a/src/libs/actions/Policy/DistanceRate.ts b/src/libs/actions/Policy/DistanceRate.ts index d5961c8f8c82..dacd5a7de811 100644 --- a/src/libs/actions/Policy/DistanceRate.ts +++ b/src/libs/actions/Policy/DistanceRate.ts @@ -528,17 +528,16 @@ function updateDistanceTaxClaimableValue(policyID: string, customUnit: CustomUni const rateIDs = customUnitRates.map((rate) => rate.customUnitRateID); for (const rateID of Object.keys(customUnit.rates)) { - if (!rateIDs.includes(rateID)) { - return; + if (rateIDs.includes(rateID)) { + const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); + optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; + successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; + failureRates[rateID] = { + ...currentRates[rateID], + pendingFields: {rate: null}, + errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, + }; } - const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); - optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; - successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; - failureRates[rateID] = { - ...currentRates[rateID], - pendingFields: {rate: null}, - errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, - }; } const optimisticData: OnyxUpdate[] = [ @@ -600,17 +599,16 @@ function updateDistanceTaxRate(policyID: string, customUnit: CustomUnit, customU const rateIDs = customUnitRates.map((rate) => rate.customUnitRateID); for (const rateID of Object.keys(customUnit.rates)) { - if (!rateIDs.includes(rateID)) { - return; + if (rateIDs.includes(rateID)) { + const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); + optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; + successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; + failureRates[rateID] = { + ...currentRates[rateID], + pendingFields: {rate: null}, + errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, + }; } - const foundRate = customUnitRates.find((rate) => rate.customUnitRateID === rateID); - optimisticRates[rateID] = {...foundRate, pendingFields: {rate: CONST.RED_BRICK_ROAD_PENDING_ACTION.UPDATE}}; - successRates[rateID] = {...foundRate, pendingFields: {rate: null}}; - failureRates[rateID] = { - ...currentRates[rateID], - pendingFields: {rate: null}, - errorFields: {rate: ErrorUtils.getMicroSecondOnyxError('common.genericErrorMessage')}, - }; } const optimisticData: OnyxUpdate[] = [ @@ -661,6 +659,8 @@ function updateDistanceTaxRate(policyID: string, customUnit: CustomUnit, customU customUnitRateArray: JSON.stringify(prepareCustomUnitRatesArray(customUnitRates)), }; + console.log(optimisticData); + API.write(WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_TAX_RATE_VALUE, params, {optimisticData, successData, failureData}); } diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index 97835d39f638..f96877583791 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -88,8 +88,7 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail }; const rateValueToDisplay = CurrencyUtils.convertAmountToDisplayString(rate?.rate, currency); - const taxClaimableValueToDisplay = - taxClaimablePercentage && rate.rate ? `${CurrencyUtils.getLocalizedCurrencySymbol(currency)}${((taxClaimablePercentage * rate.rate) / 100).toFixed(1)}` : ''; + const taxClaimableValueToDisplay = taxClaimablePercentage && rate.rate ? CurrencyUtils.convertAmountToDisplayString(taxClaimablePercentage * rate.rate, currency) : ''; const unitToDisplay = translate(`common.${customUnit?.attributes?.unit ?? CONST.CUSTOM_UNITS.DISTANCE_UNIT_MILES}`); const threeDotsMenuItems = [ From 088382bb2c54b8ebb4aeb73a69e1d6dc798e1729 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Wed, 5 Jun 2024 20:28:20 +0700 Subject: [PATCH 34/37] remove log --- src/libs/actions/Policy/DistanceRate.ts | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/libs/actions/Policy/DistanceRate.ts b/src/libs/actions/Policy/DistanceRate.ts index dacd5a7de811..6b0a9c5c3ee0 100644 --- a/src/libs/actions/Policy/DistanceRate.ts +++ b/src/libs/actions/Policy/DistanceRate.ts @@ -659,8 +659,6 @@ function updateDistanceTaxRate(policyID: string, customUnit: CustomUnit, customU customUnitRateArray: JSON.stringify(prepareCustomUnitRatesArray(customUnitRates)), }; - console.log(optimisticData); - API.write(WRITE_COMMANDS.UPDATE_POLICY_DISTANCE_TAX_RATE_VALUE, params, {optimisticData, successData, failureData}); } From c80c78a24563230b332fd1971e7d5d004b8a9a99 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Wed, 5 Jun 2024 20:35:22 +0700 Subject: [PATCH 35/37] refactor code --- .../AppNavigator/ModalStackNavigators/index.tsx | 2 +- src/libs/PolicyDistanceRatesUtils.ts | 6 ++---- ...sx => PolicyDistanceRateTaxReclaimableEditPage.tsx} | 10 +++++----- 3 files changed, 8 insertions(+), 10 deletions(-) rename src/pages/workspace/distanceRates/{PolicyDistanceRateTaxReclaimableOnEditPage.tsx => PolicyDistanceRateTaxReclaimableEditPage.tsx} (88%) diff --git a/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx b/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx index 02004551dc0b..531d53b0f3fe 100644 --- a/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx +++ b/src/libs/Navigation/AppNavigator/ModalStackNavigators/index.tsx @@ -248,7 +248,7 @@ const SettingsModalStackNavigator = createModalStackNavigator require('../../../../pages/workspace/distanceRates/PolicyDistanceRateDetailsPage').default as React.ComponentType, [SCREENS.WORKSPACE.DISTANCE_RATE_EDIT]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateEditPage').default as React.ComponentType, [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RECLAIMABLE_ON_EDIT]: () => - require('../../../../pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage').default as React.ComponentType, + require('../../../../pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableEditPage').default as React.ComponentType, [SCREENS.WORKSPACE.DISTANCE_RATE_TAX_RATE_EDIT]: () => require('../../../../pages/workspace/distanceRates/PolicyDistanceRateTaxRateEditPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAGS_SETTINGS]: () => require('../../../../pages/workspace/tags/WorkspaceTagsSettingsPage').default as React.ComponentType, [SCREENS.WORKSPACE.TAG_SETTINGS]: () => require('../../../../pages/workspace/tags/TagSettingsPage').default as React.ComponentType, diff --git a/src/libs/PolicyDistanceRatesUtils.ts b/src/libs/PolicyDistanceRatesUtils.ts index b61f9d684a2f..084356df7449 100644 --- a/src/libs/PolicyDistanceRatesUtils.ts +++ b/src/libs/PolicyDistanceRatesUtils.ts @@ -28,10 +28,8 @@ function validateRateValue(values: FormOnyxValues, currency: stri function validateTaxClaimableValue(values: FormOnyxValues, rate: Rate): FormInputErrors { const errors: FormInputErrors = {}; - if (!rate.rate) { - return errors; - } - if (Number(values.taxClaimableValue) > rate.rate / 100) { + + if (rate.rate && Number(values.taxClaimableValue) > rate.rate / 100) { errors.taxClaimableValue = 'workspace.taxes.error.updateTaxClaimableFailureMessage'; } return errors; diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableEditPage.tsx similarity index 88% rename from src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx rename to src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableEditPage.tsx index 450dc9768cf4..1503341ee96d 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableOnEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableEditPage.tsx @@ -21,9 +21,9 @@ import ONYXKEYS from '@src/ONYXKEYS'; import type SCREENS from '@src/SCREENS'; import INPUT_IDS from '@src/types/form/PolicyDistanceRateTaxReclaimableOnEditForm'; -type PolicyDistanceRateTaxReclaimableOnEditPageProps = WithPolicyOnyxProps & StackScreenProps; +type PolicyDistanceRateTaxReclaimableEditPageProps = WithPolicyOnyxProps & StackScreenProps; -function PolicyDistanceRateTaxReclaimableOnEditPage({route, policy}: PolicyDistanceRateTaxReclaimableOnEditPageProps) { +function PolicyDistanceRateTaxReclaimableEditPage({route, policy}: PolicyDistanceRateTaxReclaimableEditPageProps) { const styles = useThemeStyles(); const {translate} = useLocalize(); const {inputCallbackRef} = useAutoFocusInput(); @@ -59,7 +59,7 @@ function PolicyDistanceRateTaxReclaimableOnEditPage({route, policy}: PolicyDista Date: Wed, 5 Jun 2024 23:01:49 +0700 Subject: [PATCH 36/37] remove unnecessary View --- .../PolicyDistanceRateDetailsPage.tsx | 134 +++++++++--------- 1 file changed, 66 insertions(+), 68 deletions(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx index f96877583791..7f604efd20ee 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateDetailsPage.tsx @@ -127,88 +127,86 @@ function PolicyDistanceRateDetailsPage({policy, route}: PolicyDistanceRateDetail threeDotsAnchorPosition={styles.threeDotsPopoverOffset(windowWidth)} /> - + clearErrorFields('enabled')} + > + + {translate('workspace.distanceRates.enableRate')} + + + + clearErrorFields('rate')} + > + + + {isDistanceTrackTaxEnabled && ( clearErrorFields('enabled')} + onClose={() => clearErrorFields('attributes')} > - - {translate('workspace.distanceRates.enableRate')} - + + )} + {isDistanceTrackTaxEnabled && ( clearErrorFields('rate')} + onClose={() => clearErrorFields('attributes')} > - {isDistanceTrackTaxEnabled && ( - clearErrorFields('attributes')} - > - - - - - )} - {isDistanceTrackTaxEnabled && ( - clearErrorFields('attributes')} - > - - - )} - setIsWarningModalVisible(false)} - isVisible={isWarningModalVisible} - title={translate('workspace.distanceRates.oopsNotSoFast')} - prompt={translate('workspace.distanceRates.workspaceNeeds')} - confirmText={translate('common.buttonConfirm')} - shouldShowCancelButton={false} - /> - setIsDeleteModalVisible(false)} - prompt={translate('workspace.distanceRates.areYouSureDelete', {count: 1})} - confirmText={translate('common.delete')} - cancelText={translate('common.cancel')} - danger - /> - + )} + setIsWarningModalVisible(false)} + isVisible={isWarningModalVisible} + title={translate('workspace.distanceRates.oopsNotSoFast')} + prompt={translate('workspace.distanceRates.workspaceNeeds')} + confirmText={translate('common.buttonConfirm')} + shouldShowCancelButton={false} + /> + setIsDeleteModalVisible(false)} + prompt={translate('workspace.distanceRates.areYouSureDelete', {count: 1})} + confirmText={translate('common.delete')} + cancelText={translate('common.cancel')} + danger + /> From c0bd795b529b196d922a1d92e2c0f341c377e6a8 Mon Sep 17 00:00:00 2001 From: nkdengineer Date: Wed, 5 Jun 2024 23:50:24 +0700 Subject: [PATCH 37/37] fix bug display amount --- .../PolicyDistanceRateTaxReclaimableEditPage.tsx | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableEditPage.tsx b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableEditPage.tsx index 1503341ee96d..7be33360de27 100644 --- a/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableEditPage.tsx +++ b/src/pages/workspace/distanceRates/PolicyDistanceRateTaxReclaimableEditPage.tsx @@ -9,6 +9,7 @@ import ScreenWrapper from '@components/ScreenWrapper'; import useAutoFocusInput from '@hooks/useAutoFocusInput'; import useLocalize from '@hooks/useLocalize'; import useThemeStyles from '@hooks/useThemeStyles'; +import * as CurrencyUtils from '@libs/CurrencyUtils'; import Navigation from '@libs/Navigation/Navigation'; import {validateTaxClaimableValue} from '@libs/PolicyDistanceRatesUtils'; import type {SettingsNavigatorParamList} from '@navigation/types'; @@ -34,7 +35,10 @@ function PolicyDistanceRateTaxReclaimableEditPage({route, policy}: PolicyDistanc const customUnit = customUnits[Object.keys(customUnits)[0]]; const rate = customUnit.rates[rateID]; const currency = rate.currency ?? CONST.CURRENCY.USD; - const currentTaxReclaimableOnValue = rate.attributes?.taxClaimablePercentage && rate.rate ? (rate.attributes.taxClaimablePercentage * rate.rate) / 100 : ''; + const extraDecimals = 1; + const decimals = CurrencyUtils.getCurrencyDecimals(currency) + extraDecimals; + const currentTaxReclaimableOnValue = rate.attributes?.taxClaimablePercentage && rate.rate ? ((rate.attributes.taxClaimablePercentage * rate.rate) / 100).toFixed(decimals) : ''; + const submitTaxReclaimableOn = (values: FormOnyxValues) => { DistanceRate.updateDistanceTaxClaimableValue(policyID, customUnit, [ { @@ -81,7 +85,7 @@ function PolicyDistanceRateTaxReclaimableEditPage({route, policy}: PolicyDistanc