From 3ae754853b9a2c6f4ba4f7ad3f7aef83475b6727 Mon Sep 17 00:00:00 2001 From: "Daniel Gale-Rosen (via MelvinBot)" Date: Wed, 8 Apr 2026 18:21:49 +0000 Subject: [PATCH 1/5] Add itemized receipt changelog support, update manual approval threshold format, fix bug - Add UPDATE_MAX_EXPENSE_AMOUNT_NO_ITEMIZED_RECEIPT action type to CONST - Add original message fields for itemized receipt amounts - Add getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage function - Add dispatch in PureReportActionItem and SidebarUtils - Add English and Spanish translations for itemized receipt changelogs - Fix bug in getUpdatedManualApprovalThresholdMessage that checked oldLimit twice instead of checking newLimit on the second clause Co-authored-by: Daniel Gale-Rosen --- src/CONST/index.ts | 1 + src/languages/en.ts | 3 +++ src/languages/es.ts | 3 +++ src/libs/ReportActionsUtils.ts | 27 ++++++++++++++++++- src/libs/SidebarUtils.ts | 3 +++ .../inbox/report/PureReportActionItem.tsx | 3 +++ src/types/onyx/OriginalMessage.ts | 6 +++++ 7 files changed, 45 insertions(+), 1 deletion(-) diff --git a/src/CONST/index.ts b/src/CONST/index.ts index e57a1b1f9cf8e..77d44ad0b2be6 100644 --- a/src/CONST/index.ts +++ b/src/CONST/index.ts @@ -1558,6 +1558,7 @@ const CONST = { UPDATE_MANUAL_APPROVAL_THRESHOLD: 'POLICYCHANGELOG_UPDATE_MANUAL_APPROVAL_THRESHOLD', UPDATE_MAX_EXPENSE_AMOUNT: 'POLICYCHANGELOG_UPDATE_MAX_EXPENSE_AMOUNT', UPDATE_MAX_EXPENSE_AMOUNT_NO_RECEIPT: 'POLICYCHANGELOG_UPDATE_MAX_EXPENSE_AMOUNT_NO_RECEIPT', + UPDATE_MAX_EXPENSE_AMOUNT_NO_ITEMIZED_RECEIPT: 'POLICYCHANGELOG_UPDATE_MAX_EXPENSE_AMOUNT_NO_ITEMIZED_RECEIPT', UPDATE_MAX_EXPENSE_AGE: 'POLICYCHANGELOG_UPDATE_MAX_EXPENSE_AGE', UPDATE_MULTIPLE_TAGS_APPROVER_RULES: 'POLICYCHANGELOG_UPDATE_MULTIPLE_TAGS_APPROVER_RULES', UPDATE_NAME: 'POLICYCHANGELOG_UPDATE_NAME', diff --git a/src/languages/en.ts b/src/languages/en.ts index 17dbf0ea29ee5..dd5d4560c9ed2 100644 --- a/src/languages/en.ts +++ b/src/languages/en.ts @@ -7378,6 +7378,9 @@ const translations = { setReceiptRequiredAmount: (newValue: string) => `set receipt required amount to "${newValue}"`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `changed receipt required amount to "${newValue}" (previously "${oldValue}")`, removedReceiptRequiredAmount: (oldValue: string) => `removed receipt required amount (previously "${oldValue}")`, + setItemizedReceiptRequiredAmount: (newValue: string) => `set itemized receipt required amount to "${newValue}"`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => `changed itemized receipt required amount to "${newValue}" (previously "${oldValue}")`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `removed itemized receipt required amount (previously "${oldValue}")`, setMaxExpenseAmount: (newValue: string) => `set max expense amount to "${newValue}"`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `changed max expense amount to "${newValue}" (previously "${oldValue}")`, removedMaxExpenseAmount: (oldValue: string) => `removed max expense amount (previously "${oldValue}")`, diff --git a/src/languages/es.ts b/src/languages/es.ts index 6a30c8c202d8a..6d0fdedf60891 100644 --- a/src/languages/es.ts +++ b/src/languages/es.ts @@ -6943,6 +6943,9 @@ ${amount} para ${merchant} - ${date}`, setReceiptRequiredAmount: (newValue) => `estableció el importe requerido del recibo en "${newValue}"`, changedReceiptRequiredAmount: (oldValue, newValue) => `cambió el importe requerido del recibo a "${newValue}" (antes "${oldValue}")`, removedReceiptRequiredAmount: (oldValue) => `eliminó el importe requerido del recibo (antes "${oldValue}")`, + setItemizedReceiptRequiredAmount: (newValue) => `estableció el importe requerido del recibo detallado en "${newValue}"`, + changedItemizedReceiptRequiredAmount: (oldValue, newValue) => `cambió el importe requerido del recibo detallado a "${newValue}" (antes "${oldValue}")`, + removedItemizedReceiptRequiredAmount: (oldValue) => `eliminó el importe requerido del recibo detallado (antes "${oldValue}")`, setMaxExpenseAmount: (newValue) => `estableció el importe máximo del gasto en "${newValue}"`, changedMaxExpenseAmount: (oldValue, newValue) => `cambió el importe máximo del gasto a "${newValue}" (antes "${oldValue}")`, diff --git a/src/libs/ReportActionsUtils.ts b/src/libs/ReportActionsUtils.ts index 1c31711ce7a7a..a8299c4f6ef9f 100644 --- a/src/libs/ReportActionsUtils.ts +++ b/src/libs/ReportActionsUtils.ts @@ -3612,6 +3612,30 @@ function getPolicyChangeLogMaxExpenseAmountNoReceiptMessage(translate: Localized return getReportActionText(action); } +function getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage(translate: LocalizedTranslate, action: ReportAction): string { + const {oldMaxExpenseAmountNoItemizedReceipt, newMaxExpenseAmountNoItemizedReceipt, currency} = + getOriginalMessage(action as ReportAction) ?? {}; + + if (typeof oldMaxExpenseAmountNoItemizedReceipt === 'number' && typeof newMaxExpenseAmountNoItemizedReceipt === 'number') { + const oldIsDisabled = oldMaxExpenseAmountNoItemizedReceipt === CONST.DISABLED_MAX_EXPENSE_VALUE; + const newIsDisabled = newMaxExpenseAmountNoItemizedReceipt === CONST.DISABLED_MAX_EXPENSE_VALUE; + const oldValue = oldIsDisabled ? '' : convertToDisplayString(oldMaxExpenseAmountNoItemizedReceipt, currency); + const newValue = newIsDisabled ? '' : convertToDisplayString(newMaxExpenseAmountNoItemizedReceipt, currency); + + if (oldIsDisabled && !newIsDisabled) { + return translate('workspaceActions.setItemizedReceiptRequiredAmount', newValue); + } + + if (!oldIsDisabled && newIsDisabled) { + return translate('workspaceActions.removedItemizedReceiptRequiredAmount', oldValue); + } + + return translate('workspaceActions.changedItemizedReceiptRequiredAmount', oldValue, newValue); + } + + return getReportActionText(action); +} + function getPolicyChangeLogMaxExpenseAmountMessage(translate: LocalizedTranslate, action: ReportAction): string { const {oldMaxExpenseAmount, newMaxExpenseAmount, currency} = getOriginalMessage(action as ReportAction) ?? {}; @@ -3927,7 +3951,7 @@ function getUpdatedManualApprovalThresholdMessage(translate: LocalizedTranslate, currency = CONST.CURRENCY.USD, } = getOriginalMessage(reportAction as ReportAction) ?? {}; - if (typeof oldLimit !== 'number' || typeof oldLimit !== 'number') { + if (typeof oldLimit !== 'number' || typeof newLimit !== 'number') { return getReportActionText(reportAction); } return translate('workspaceActions.updatedManualApprovalThreshold', {oldLimit: convertToDisplayString(oldLimit, currency), newLimit: convertToDisplayString(newLimit, currency)}); @@ -4684,6 +4708,7 @@ export { getForeignCurrencyDefaultTaxUpdateMessage, getWorkspaceFrequencyUpdateMessage, getPolicyChangeLogMaxExpenseAmountNoReceiptMessage, + getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage, getPolicyChangeLogMaxExpenseAmountMessage, getPolicyChangeLogMaxExpenseAgeMessage, getPolicyChangeLogDefaultBillableMessage, diff --git a/src/libs/SidebarUtils.ts b/src/libs/SidebarUtils.ts index fe3de00aec9a3..2f24c4e9e5acd 100644 --- a/src/libs/SidebarUtils.ts +++ b/src/libs/SidebarUtils.ts @@ -73,6 +73,7 @@ import { getPolicyChangeLogMaxExpenseAgeMessage, getPolicyChangeLogMaxExpenseAmountMessage, getPolicyChangeLogMaxExpenseAmountNoReceiptMessage, + getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage, getPolicyChangeLogUpdateEmployee, getReimburserUpdateMessage, getRemovedCardFeedMessage, @@ -1036,6 +1037,8 @@ function getOptionData({ result.alternateText = getCompanyAddressUpdateMessage(translate, lastAction); } else if (lastAction?.actionName === CONST.REPORT.ACTIONS.TYPE.POLICY_CHANGE_LOG.UPDATE_MAX_EXPENSE_AMOUNT_NO_RECEIPT) { result.alternateText = getPolicyChangeLogMaxExpenseAmountNoReceiptMessage(translate, lastAction); + } else if (lastAction?.actionName === CONST.REPORT.ACTIONS.TYPE.POLICY_CHANGE_LOG.UPDATE_MAX_EXPENSE_AMOUNT_NO_ITEMIZED_RECEIPT) { + result.alternateText = getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage(translate, lastAction); } else if (lastAction?.actionName === CONST.REPORT.ACTIONS.TYPE.POLICY_CHANGE_LOG.UPDATE_MAX_EXPENSE_AMOUNT) { result.alternateText = getPolicyChangeLogMaxExpenseAmountMessage(translate, lastAction); } else if (lastAction?.actionName === CONST.REPORT.ACTIONS.TYPE.POLICY_CHANGE_LOG.UPDATE_MAX_EXPENSE_AGE) { diff --git a/src/pages/inbox/report/PureReportActionItem.tsx b/src/pages/inbox/report/PureReportActionItem.tsx index ca19344d56b79..32597980f4c87 100644 --- a/src/pages/inbox/report/PureReportActionItem.tsx +++ b/src/pages/inbox/report/PureReportActionItem.tsx @@ -119,6 +119,7 @@ import { getPolicyChangeLogMaxExpenseAgeMessage, getPolicyChangeLogMaxExpenseAmountMessage, getPolicyChangeLogMaxExpenseAmountNoReceiptMessage, + getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage, getPolicyChangeLogUpdateEmployee, getReimburserUpdateMessage, getRemovedCardFeedMessage, @@ -1626,6 +1627,8 @@ function PureReportActionItem({ children = ; } else if (isActionOfType(action, CONST.REPORT.ACTIONS.TYPE.POLICY_CHANGE_LOG.UPDATE_MAX_EXPENSE_AMOUNT_NO_RECEIPT)) { children = ; + } else if (isActionOfType(action, CONST.REPORT.ACTIONS.TYPE.POLICY_CHANGE_LOG.UPDATE_MAX_EXPENSE_AMOUNT_NO_ITEMIZED_RECEIPT)) { + children = ; } else if (isActionOfType(action, CONST.REPORT.ACTIONS.TYPE.POLICY_CHANGE_LOG.UPDATE_MAX_EXPENSE_AMOUNT)) { children = ; } else if (isActionOfType(action, CONST.REPORT.ACTIONS.TYPE.POLICY_CHANGE_LOG.UPDATE_MAX_EXPENSE_AGE)) { diff --git a/src/types/onyx/OriginalMessage.ts b/src/types/onyx/OriginalMessage.ts index 41b63bc218006..7fc49006c20b0 100644 --- a/src/types/onyx/OriginalMessage.ts +++ b/src/types/onyx/OriginalMessage.ts @@ -475,6 +475,12 @@ type OriginalMessagePolicyChangeLog = { /** New value for max expense amount with no receipt */ newMaxExpenseAmountNoReceipt?: number; + /** Old value for max expense amount with no itemized receipt */ + oldMaxExpenseAmountNoItemizedReceipt?: number; + + /** New value for max expense amount with no itemized receipt */ + newMaxExpenseAmountNoItemizedReceipt?: number; + /** Currency of the policy */ currency?: string; From 1edd819c3976f9242d206a278fde99614895b818 Mon Sep 17 00:00:00 2001 From: "Daniel Gale-Rosen (via MelvinBot)" Date: Wed, 8 Apr 2026 18:27:12 +0000 Subject: [PATCH 2/5] Fix prettier formatting for import order Co-authored-by: Daniel Gale-Rosen --- src/libs/SidebarUtils.ts | 2 +- src/pages/inbox/report/PureReportActionItem.tsx | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/libs/SidebarUtils.ts b/src/libs/SidebarUtils.ts index 2f24c4e9e5acd..85362be9e161b 100644 --- a/src/libs/SidebarUtils.ts +++ b/src/libs/SidebarUtils.ts @@ -72,8 +72,8 @@ import { getPolicyChangeLogEmployeeLeftMessage, getPolicyChangeLogMaxExpenseAgeMessage, getPolicyChangeLogMaxExpenseAmountMessage, - getPolicyChangeLogMaxExpenseAmountNoReceiptMessage, getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage, + getPolicyChangeLogMaxExpenseAmountNoReceiptMessage, getPolicyChangeLogUpdateEmployee, getReimburserUpdateMessage, getRemovedCardFeedMessage, diff --git a/src/pages/inbox/report/PureReportActionItem.tsx b/src/pages/inbox/report/PureReportActionItem.tsx index 32597980f4c87..153ec506951e8 100644 --- a/src/pages/inbox/report/PureReportActionItem.tsx +++ b/src/pages/inbox/report/PureReportActionItem.tsx @@ -118,8 +118,8 @@ import { getPolicyChangeLogDeleteMemberMessage, getPolicyChangeLogMaxExpenseAgeMessage, getPolicyChangeLogMaxExpenseAmountMessage, - getPolicyChangeLogMaxExpenseAmountNoReceiptMessage, getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage, + getPolicyChangeLogMaxExpenseAmountNoReceiptMessage, getPolicyChangeLogUpdateEmployee, getReimburserUpdateMessage, getRemovedCardFeedMessage, From 0af89cf28dc9d53be8b0e9b59effd1d209ae37af Mon Sep 17 00:00:00 2001 From: "Daniel Gale-Rosen (via MelvinBot)" Date: Wed, 8 Apr 2026 18:34:39 +0000 Subject: [PATCH 3/5] Add missing itemized receipt translations for all languages Co-authored-by: Daniel Gale-Rosen --- src/languages/de.ts | 5 ++++- src/languages/fr.ts | 3 +++ src/languages/it.ts | 4 ++++ src/languages/ja.ts | 3 +++ src/languages/nl.ts | 4 ++++ src/languages/pl.ts | 3 +++ src/languages/pt-BR.ts | 3 +++ src/languages/zh-hans.ts | 5 ++++- 8 files changed, 28 insertions(+), 2 deletions(-) diff --git a/src/languages/de.ts b/src/languages/de.ts index e650ed7ef72cb..c540c5c58f1d6 100644 --- a/src/languages/de.ts +++ b/src/languages/de.ts @@ -7272,7 +7272,10 @@ Fügen Sie weitere Ausgabelimits hinzu, um den Cashflow Ihres Unternehmens zu sc }, setReceiptRequiredAmount: (newValue: string) => `Belegpflichtigen Betrag auf „${newValue}“ festlegen`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `Belegpflichtbetrag auf „${newValue}“ geändert (zuvor „${oldValue}“)`, - removedReceiptRequiredAmount: (oldValue: string) => `Belegpflichtigen Betrag entfernt (zuvor „${oldValue}“)`, + removedReceiptRequiredAmount: (oldValue: string) => `Belegpflichtigen Betrag entfernt (zuvor „${oldValue}”)`, + setItemizedReceiptRequiredAmount: (newValue: string) => `Pflichtbetrag für aufgeschlüsselten Beleg auf „${newValue}” festgelegt`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => `Pflichtbetrag für aufgeschlüsselten Beleg auf „${newValue}” geändert (zuvor „${oldValue}”)`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `Pflichtbetrag für aufgeschlüsselten Beleg entfernt (zuvor „${oldValue}”)`, setMaxExpenseAmount: (newValue: string) => `maximalen Ausgabenbetrag auf „${newValue}“ festlegen`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `hat den maximalen Ausgabenbetrag auf „${newValue}“ geändert (zuvor „${oldValue}“)`, removedMaxExpenseAmount: (oldValue: string) => `maximale Ausgabenhöhe entfernt (zuvor „${oldValue}“)`, diff --git a/src/languages/fr.ts b/src/languages/fr.ts index 2d13b29a885f9..20a88d3f97aaf 100644 --- a/src/languages/fr.ts +++ b/src/languages/fr.ts @@ -7295,6 +7295,9 @@ Ajoutez davantage de règles de dépenses pour protéger la trésorerie de l’e setReceiptRequiredAmount: (newValue: string) => `définir le montant de reçu obligatoire sur « ${newValue} »`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `a modifié le montant requis pour le reçu à « ${newValue} » (auparavant « ${oldValue} »)`, removedReceiptRequiredAmount: (oldValue: string) => `a supprimé le montant requis pour le reçu (précédemment « ${oldValue} »)`, + setItemizedReceiptRequiredAmount: (newValue: string) => `a défini le montant requis pour le reçu détaillé sur « ${newValue} »`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => `a modifié le montant requis pour le reçu détaillé à « ${newValue} » (auparavant « ${oldValue} »)`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `a supprimé le montant requis pour le reçu détaillé (précédemment « ${oldValue} »)`, setMaxExpenseAmount: (newValue: string) => `définir le montant maximal de dépense sur « ${newValue} »`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `montant maximal de dépense modifié en « ${newValue} » (précédemment « ${oldValue} »)`, removedMaxExpenseAmount: (oldValue: string) => `montant de dépense maximal supprimé (précédemment « ${oldValue} »)`, diff --git a/src/languages/it.ts b/src/languages/it.ts index 7cde855b8932c..11e36b0a80ba1 100644 --- a/src/languages/it.ts +++ b/src/languages/it.ts @@ -7260,6 +7260,10 @@ Aggiungi altre regole di spesa per proteggere il flusso di cassa aziendale.`, setReceiptRequiredAmount: (newValue: string) => `imposta l’importo richiesto per la ricevuta su "${newValue}"`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `ha modificato l’importo richiesto per la ricevuta in "${newValue}" (in precedenza "${oldValue}")`, removedReceiptRequiredAmount: (oldValue: string) => `ha rimosso l’importo richiesto per la ricevuta (in precedenza «${oldValue}»)`, + setItemizedReceiptRequiredAmount: (newValue: string) => `ha impostato l’importo richiesto per la ricevuta dettagliata su "${newValue}"`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => + `ha modificato l’importo richiesto per la ricevuta dettagliata in "${newValue}" (in precedenza "${oldValue}")`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `ha rimosso l’importo richiesto per la ricevuta dettagliata (in precedenza "${oldValue}")`, setMaxExpenseAmount: (newValue: string) => `imposta l’importo massimo della spesa su "${newValue}"`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `ha modificato l'importo massimo della spesa a "${newValue}" (precedentemente "${oldValue}")`, removedMaxExpenseAmount: (oldValue: string) => `importo massimo spesa rimosso (precedentemente "${oldValue}")`, diff --git a/src/languages/ja.ts b/src/languages/ja.ts index f0a6dc81d8df1..30f78c3697e2a 100644 --- a/src/languages/ja.ts +++ b/src/languages/ja.ts @@ -7174,6 +7174,9 @@ ${reportName} setReceiptRequiredAmount: (newValue: string) => `必要な領収書金額を「${newValue}」に設定`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `領収書必須金額を「${newValue}」(以前は「${oldValue}」)に変更しました`, removedReceiptRequiredAmount: (oldValue: string) => `必須領収書金額を削除しました(以前の値:「${oldValue}」)`, + setItemizedReceiptRequiredAmount: (newValue: string) => `明細付き領収書の必須金額を「${newValue}」に設定しました`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => `明細付き領収書の必須金額を「${newValue}」に変更しました(以前は「${oldValue}」)`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `明細付き領収書の必須金額を削除しました(以前の値:「${oldValue}」)`, setMaxExpenseAmount: (newValue: string) => `最大経費金額を「${newValue}」に設定`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `上限経費額を「${newValue}」に変更しました(以前は「${oldValue}」)`, removedMaxExpenseAmount: (oldValue: string) => `最大経費金額を削除しました(以前の値: 「${oldValue}」)`, diff --git a/src/languages/nl.ts b/src/languages/nl.ts index ff18cdf3b591a..b962e37c91eb2 100644 --- a/src/languages/nl.ts +++ b/src/languages/nl.ts @@ -7239,6 +7239,10 @@ Voeg meer bestedingsregels toe om de kasstroom van het bedrijf te beschermen.`, setReceiptRequiredAmount: (newValue: string) => `stel het vereiste bonbedrag in op "${newValue}"`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `heeft het vereiste bonbedrag gewijzigd naar "${newValue}" (voorheen "${oldValue}")`, removedReceiptRequiredAmount: (oldValue: string) => `vereiste bedrag op verwijderde bon (voorheen “${oldValue}”)`, + setItemizedReceiptRequiredAmount: (newValue: string) => `vereist bedrag voor gespecificeerde bon ingesteld op “${newValue}”`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => + `heeft het vereiste bedrag voor gespecificeerde bon gewijzigd naar “${newValue}” (voorheen “${oldValue}”)`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `vereist bedrag voor gespecificeerde bon verwijderd (voorheen “${oldValue}”)`, setMaxExpenseAmount: (newValue: string) => `maximumbedrag voor uitgave instellen op "${newValue}"`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `maximale onkostensom gewijzigd naar "${newValue}" (voorheen "${oldValue}")`, removedMaxExpenseAmount: (oldValue: string) => `maximaal bedrag voor uitgave verwijderd (voorheen "${oldValue}")`, diff --git a/src/languages/pl.ts b/src/languages/pl.ts index 9de7099eee653..3a6f6b250edae 100644 --- a/src/languages/pl.ts +++ b/src/languages/pl.ts @@ -7228,6 +7228,9 @@ Dodaj więcej zasad wydatków, żeby chronić płynność finansową firmy.`, setReceiptRequiredAmount: (newValue: string) => `ustaw wymaganą kwotę paragonu na „${newValue}”`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `zmienił(a) wymaganą kwotę paragonu na „${newValue}” (wcześniej „${oldValue}”)`, removedReceiptRequiredAmount: (oldValue: string) => `usunięto wymagany limit paragonu (wcześniej „${oldValue}”)`, + setItemizedReceiptRequiredAmount: (newValue: string) => `ustawiono wymaganą kwotę szczegółowego paragonu na „${newValue}”`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => `zmieniono wymaganą kwotę szczegółowego paragonu na „${newValue}” (wcześniej „${oldValue}”)`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `usunięto wymaganą kwotę szczegółowego paragonu (wcześniej „${oldValue}”)`, setMaxExpenseAmount: (newValue: string) => `ustaw maksymalną kwotę wydatku na „${newValue}”`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `zmieniono maksymalną kwotę wydatku na „${newValue}” (wcześniej „${oldValue}”)`, removedMaxExpenseAmount: (oldValue: string) => `usunięto maksymalną kwotę wydatku (wcześniej „${oldValue}”)`, diff --git a/src/languages/pt-BR.ts b/src/languages/pt-BR.ts index fbddaffffeeb7..7d107ee5c4123 100644 --- a/src/languages/pt-BR.ts +++ b/src/languages/pt-BR.ts @@ -7231,6 +7231,9 @@ Adicione mais regras de gasto para proteger o fluxo de caixa da empresa.`, setReceiptRequiredAmount: (newValue: string) => `definir valor exigido do recibo como "${newValue}"`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `alterou o valor obrigatório do recibo para "${newValue}" (antes "${oldValue}")`, removedReceiptRequiredAmount: (oldValue: string) => `removeu o valor obrigatório do recibo (antes era "${oldValue}")`, + setItemizedReceiptRequiredAmount: (newValue: string) => `definiu o valor obrigatório do recibo detalhado como "${newValue}"`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => `alterou o valor obrigatório do recibo detalhado para "${newValue}" (antes "${oldValue}")`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `removeu o valor obrigatório do recibo detalhado (antes era "${oldValue}")`, setMaxExpenseAmount: (newValue: string) => `definir valor máximo da despesa como "${newValue}"`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `alterou o valor máximo da despesa para "${newValue}" (antes "${oldValue}")`, removedMaxExpenseAmount: (oldValue: string) => `removeu o valor máximo de despesa (anteriormente "${oldValue}")`, diff --git a/src/languages/zh-hans.ts b/src/languages/zh-hans.ts index 3de0ae015fdff..e2a391f481a1b 100644 --- a/src/languages/zh-hans.ts +++ b/src/languages/zh-hans.ts @@ -7043,7 +7043,10 @@ ${reportName} }, setReceiptRequiredAmount: (newValue: string) => `将需要收据的金额设置为“${newValue}”`, changedReceiptRequiredAmount: (oldValue: string, newValue: string) => `已将所需收据金额更改为“${newValue}”(之前为“${oldValue}”)`, - removedReceiptRequiredAmount: (oldValue: string) => `已移除所需收据金额(先前为“${oldValue}”)`, + removedReceiptRequiredAmount: (oldValue: string) => `已移除所需收据金额(先前为”${oldValue}”)`, + setItemizedReceiptRequiredAmount: (newValue: string) => `将逐项收据所需金额设置为”${newValue}”`, + changedItemizedReceiptRequiredAmount: (oldValue: string, newValue: string) => `已将逐项收据所需金额更改为”${newValue}”(之前为”${oldValue}”)`, + removedItemizedReceiptRequiredAmount: (oldValue: string) => `已移除逐项收据所需金额(先前为”${oldValue}”)`, setMaxExpenseAmount: (newValue: string) => `将最高报销金额设置为“${newValue}”`, changedMaxExpenseAmount: (oldValue: string, newValue: string) => `将最高报销金额更改为 “${newValue}”(之前为 “${oldValue}”)`, removedMaxExpenseAmount: (oldValue: string) => `已移除最⾼报销金额(原为“${oldValue}”)`, From d5c0815d7beef49cab50c044b1bd42c3b75348cc Mon Sep 17 00:00:00 2001 From: "Daniel Gale-Rosen (via MelvinBot)" Date: Wed, 8 Apr 2026 20:46:56 +0000 Subject: [PATCH 4/5] Rename oldIsDisabled/newIsDisabled to isOldLimitDisabled/isNewLimitDisabled Co-authored-by: Daniel Gale-Rosen --- src/libs/ReportActionsUtils.ts | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/libs/ReportActionsUtils.ts b/src/libs/ReportActionsUtils.ts index a8299c4f6ef9f..10ea68413baa6 100644 --- a/src/libs/ReportActionsUtils.ts +++ b/src/libs/ReportActionsUtils.ts @@ -3617,16 +3617,16 @@ function getPolicyChangeLogMaxExpenseAmountNoItemizedReceiptMessage(translate: L getOriginalMessage(action as ReportAction) ?? {}; if (typeof oldMaxExpenseAmountNoItemizedReceipt === 'number' && typeof newMaxExpenseAmountNoItemizedReceipt === 'number') { - const oldIsDisabled = oldMaxExpenseAmountNoItemizedReceipt === CONST.DISABLED_MAX_EXPENSE_VALUE; - const newIsDisabled = newMaxExpenseAmountNoItemizedReceipt === CONST.DISABLED_MAX_EXPENSE_VALUE; - const oldValue = oldIsDisabled ? '' : convertToDisplayString(oldMaxExpenseAmountNoItemizedReceipt, currency); - const newValue = newIsDisabled ? '' : convertToDisplayString(newMaxExpenseAmountNoItemizedReceipt, currency); + const isOldLimitDisabled = oldMaxExpenseAmountNoItemizedReceipt === CONST.DISABLED_MAX_EXPENSE_VALUE; + const isNewLimitDisabled = newMaxExpenseAmountNoItemizedReceipt === CONST.DISABLED_MAX_EXPENSE_VALUE; + const oldValue = isOldLimitDisabled ? '' : convertToDisplayString(oldMaxExpenseAmountNoItemizedReceipt, currency); + const newValue = isNewLimitDisabled ? '' : convertToDisplayString(newMaxExpenseAmountNoItemizedReceipt, currency); - if (oldIsDisabled && !newIsDisabled) { + if (isOldLimitDisabled && !isNewLimitDisabled) { return translate('workspaceActions.setItemizedReceiptRequiredAmount', newValue); } - if (!oldIsDisabled && newIsDisabled) { + if (!isOldLimitDisabled && isNewLimitDisabled) { return translate('workspaceActions.removedItemizedReceiptRequiredAmount', oldValue); } From b6991d7d056bb3c9b6846e7a4fa27eda3d5286ea Mon Sep 17 00:00:00 2001 From: "Daniel Gale-Rosen (via MelvinBot)" Date: Wed, 8 Apr 2026 20:56:52 +0000 Subject: [PATCH 5/5] Fix: update AddNewCardPage to match main and remove stale isModalVisible reference The file on main was refactored from useState/isModalVisible to useConfirmModal but a reference to isModalVisible was left on line 85 (SelectCountryStep's disableAutoFocus prop). This caused TS2304 when CI merges main into the branch. Co-authored-by: Daniel Gale-Rosen --- .../Wallet/PersonalCards/AddNewCardPage.tsx | 47 ++++++++++--------- 1 file changed, 24 insertions(+), 23 deletions(-) diff --git a/src/pages/settings/Wallet/PersonalCards/AddNewCardPage.tsx b/src/pages/settings/Wallet/PersonalCards/AddNewCardPage.tsx index d9f3d7b39cbac..9e139591a2ab2 100644 --- a/src/pages/settings/Wallet/PersonalCards/AddNewCardPage.tsx +++ b/src/pages/settings/Wallet/PersonalCards/AddNewCardPage.tsx @@ -1,7 +1,8 @@ -import React, {useEffect, useState} from 'react'; +import React, {useEffect} from 'react'; import {View} from 'react-native'; -import ConfirmModal from '@components/ConfirmModal'; import FullScreenLoadingIndicator from '@components/FullscreenLoadingIndicator'; +import {ModalActions} from '@components/Modal/Global/ModalContext'; +import useConfirmModal from '@hooks/useConfirmModal'; import useCurrentUserPersonalDetails from '@hooks/useCurrentUserPersonalDetails'; import useLocalize from '@hooks/useLocalize'; import useOnyx from '@hooks/useOnyx'; @@ -25,7 +26,7 @@ function AddPersonalNewCardPage() { const [introSelected] = useOnyx(ONYXKEYS.NVP_INTRO_SELECTED); const [betas] = useOnyx(ONYXKEYS.BETAS); const {currentStep} = addNewPersonalCardFeed ?? {}; - const [isModalVisible, setIsModalVisible] = useState(false); + const {showConfirmModal} = useConfirmModal(); const {translate} = useLocalize(); const {accountID: currentUserAccountID} = useCurrentUserPersonalDetails(); const isAddCardFeedLoading = isLoadingOnyxValue(addNewPersonalCardFeedMetadata); @@ -61,31 +62,31 @@ function AddPersonalNewCardPage() { CurrentStep = ; break; case CONST.PERSONAL_CARDS.STEP.PLAID_CONNECTION: - CurrentStep = setIsModalVisible(true)} />; + CurrentStep = ( + { + showConfirmModal({ + title: translate('workspace.companyCards.addNewCard.exitModal.title'), + success: true, + confirmText: translate('workspace.companyCards.addNewCard.exitModal.confirmText'), + cancelText: translate('workspace.companyCards.addNewCard.exitModal.cancelText'), + prompt: translate('workspace.companyCards.addNewCard.exitModal.prompt'), + }).then((result) => { + if (result.action !== ModalActions.CONFIRM) { + return; + } + navigateToConciergeChat(conciergeReportID, introSelected, currentUserAccountID, false, betas); + }); + }} + /> + ); break; default: - CurrentStep = ; + CurrentStep = ; break; } - return ( - <> - {CurrentStep} - setIsModalVisible(false)} - onConfirm={() => { - setIsModalVisible(false); - navigateToConciergeChat(conciergeReportID, introSelected, currentUserAccountID, false, betas); - }} - /> - - ); + return {CurrentStep}; } export default AddPersonalNewCardPage;