From e955a762bc2fb6480e9c14bab7aadfc811d81544 Mon Sep 17 00:00:00 2001 From: Alex Beaman Date: Tue, 14 May 2024 21:34:59 +0300 Subject: [PATCH] Merge pull request #42128 from Expensify/monil-fixOfflineCurrencyTaxUpdate [CP Staging] Fix tax rate being updated when currency is updated in offline mode (cherry picked from commit 0d424d20c9c5c3513d705c0e2a899a6b33f7055d) --- src/libs/ReportUtils.ts | 18 +++++++++------ src/libs/actions/IOU.ts | 3 +++ .../iou/request/step/IOURequestStepAmount.tsx | 22 ++++++++----------- 3 files changed, 23 insertions(+), 20 deletions(-) diff --git a/src/libs/ReportUtils.ts b/src/libs/ReportUtils.ts index 8f9328ef0c69..30a7d5ac0c2d 100644 --- a/src/libs/ReportUtils.ts +++ b/src/libs/ReportUtils.ts @@ -2969,7 +2969,8 @@ function getModifiedExpenseOriginalMessage( // The amount is always a combination of the currency and the number value so when one changes we need to store both // to match how we handle the modified expense action in oldDot - if ('amount' in transactionChanges || 'currency' in transactionChanges) { + const didAmountOrCurrencyChange = 'amount' in transactionChanges || 'currency' in transactionChanges; + if (didAmountOrCurrencyChange) { originalMessage.oldAmount = TransactionUtils.getAmount(oldTransaction, isFromExpenseReport); originalMessage.amount = transactionChanges?.amount ?? transactionChanges.oldAmount; originalMessage.oldCurrency = TransactionUtils.getCurrency(oldTransaction); @@ -2986,19 +2987,22 @@ function getModifiedExpenseOriginalMessage( originalMessage.tag = transactionChanges?.tag; } + // We only want to display a tax rate update system message when tax rate is updated by user. + // Tax rate can change as a result of currency update. In such cases, we want to skip displaying a system message, as discussed. + const didTaxCodeChange = 'taxCode' in transactionChanges; + if (didTaxCodeChange && !didAmountOrCurrencyChange) { + originalMessage.oldTaxRate = policy?.taxRates?.taxes[TransactionUtils.getTaxCode(oldTransaction)]?.value; + originalMessage.taxRate = transactionChanges?.taxCode && policy?.taxRates?.taxes[transactionChanges?.taxCode].value; + } + // We only want to display a tax amount update system message when tax amount is updated by user. // Tax amount can change as a result of amount, currency or tax rate update. In such cases, we want to skip displaying a system message, as discussed. - if ('taxAmount' in transactionChanges && !('amount' in transactionChanges || 'currency' in transactionChanges || 'taxCode' in transactionChanges)) { + if ('taxAmount' in transactionChanges && !(didAmountOrCurrencyChange || didTaxCodeChange)) { originalMessage.oldTaxAmount = TransactionUtils.getTaxAmount(oldTransaction, isFromExpenseReport); originalMessage.taxAmount = transactionChanges?.taxAmount; originalMessage.currency = TransactionUtils.getCurrency(oldTransaction); } - if ('taxCode' in transactionChanges) { - originalMessage.oldTaxRate = policy?.taxRates?.taxes[TransactionUtils.getTaxCode(oldTransaction)]?.value; - originalMessage.taxRate = transactionChanges?.taxCode && policy?.taxRates?.taxes[transactionChanges?.taxCode].value; - } - if ('billable' in transactionChanges) { const oldBillable = TransactionUtils.getBillable(oldTransaction); originalMessage.oldBillable = oldBillable ? Localize.translateLocal('common.billable').toLowerCase() : Localize.translateLocal('common.nonBillable').toLowerCase(); diff --git a/src/libs/actions/IOU.ts b/src/libs/actions/IOU.ts index f600be80933f..92c8fd9cca08 100644 --- a/src/libs/actions/IOU.ts +++ b/src/libs/actions/IOU.ts @@ -5052,6 +5052,7 @@ type UpdateMoneyRequestAmountAndCurrencyParams = { policy?: OnyxEntry; policyTagList?: OnyxEntry; policyCategories?: OnyxEntry; + taxCode: string; }; /** Updates the amount and currency fields of an expense */ @@ -5064,10 +5065,12 @@ function updateMoneyRequestAmountAndCurrency({ policy, policyTagList, policyCategories, + taxCode, }: UpdateMoneyRequestAmountAndCurrencyParams) { const transactionChanges = { amount, currency, + taxCode, taxAmount, }; const transactionThreadReport = allReports?.[`${ONYXKEYS.COLLECTION.REPORT}${transactionThreadReportID}`] ?? null; diff --git a/src/pages/iou/request/step/IOURequestStepAmount.tsx b/src/pages/iou/request/step/IOURequestStepAmount.tsx index b8a8c11d3d80..cdc5c9979519 100644 --- a/src/pages/iou/request/step/IOURequestStepAmount.tsx +++ b/src/pages/iou/request/step/IOURequestStepAmount.tsx @@ -56,16 +56,6 @@ type IOURequestStepAmountProps = IOURequestStepAmountOnyxProps & transaction: OnyxEntry; }; -function getTaxAmount(transaction: OnyxEntry, policy: OnyxEntry, newAmount: number) { - if (!transaction?.amount) { - return 0; - } - const transactionTaxCode = transaction?.taxCode ?? ''; - const defaultTaxCode = TransactionUtils.getDefaultTaxCode(policy, transaction) ?? ''; - const taxPercentage = TransactionUtils.getTaxValue(policy, transaction, transactionTaxCode ?? defaultTaxCode) ?? ''; - return CurrencyUtils.convertToBackendAmount(TransactionUtils.calculateTaxAmount(taxPercentage, newAmount)); -} - function IOURequestStepAmount({ report, route: { @@ -279,7 +269,8 @@ function IOURequestStepAmount({ } // If the value hasn't changed, don't request to save changes on the server and just close the modal - if (newAmount === TransactionUtils.getAmount(transaction) && currency === TransactionUtils.getCurrency(transaction)) { + const transactionCurrency = TransactionUtils.getCurrency(transaction); + if (newAmount === TransactionUtils.getAmount(transaction) && currency === transactionCurrency) { Navigation.dismissModal(); return; } @@ -290,9 +281,14 @@ function IOURequestStepAmount({ return; } - const taxAmount = getTaxAmount(transaction, policy, newAmount); + // If currency has changed, then we get the default tax rate based on currency, otherwise we use the current tax rate selected in transaction, if we have it. + const transactionTaxCode = transaction?.taxCode ?? ''; + const defaultTaxCode = TransactionUtils.getDefaultTaxCode(policy, transaction, currency) ?? ''; + const taxCode = (currency !== transactionCurrency ? defaultTaxCode : transactionTaxCode) ?? defaultTaxCode; + const taxPercentage = TransactionUtils.getTaxValue(policy, transaction, taxCode) ?? ''; + const taxAmount = CurrencyUtils.convertToBackendAmount(TransactionUtils.calculateTaxAmount(taxPercentage, newAmount)); - IOU.updateMoneyRequestAmountAndCurrency({transactionID, transactionThreadReportID: reportID, currency, amount: newAmount, taxAmount}); + IOU.updateMoneyRequestAmountAndCurrency({transactionID, transactionThreadReportID: reportID, currency, amount: newAmount, taxAmount, policy, taxCode}); Navigation.dismissModal(); };