Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use error prop for violations for consistent styling #34303

Merged
merged 41 commits into from
Feb 13, 2024
Merged
Show file tree
Hide file tree
Changes from 31 commits
Commits
Show all changes
41 commits
Select commit Hold shift + click to select a range
a4844ce
feat(Violations): create useMoneyRequestViewErrors and move violation…
trevor-coleman Jan 10, 2024
67b0987
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Jan 10, 2024
6dc9f5c
feat(Violations): move hasViolations into useMoneyRequestViewErrors, …
trevor-coleman Jan 10, 2024
36b7dbf
feat(Violations): add comment
trevor-coleman Jan 10, 2024
02fe40d
feat(Violations): add comment
trevor-coleman Jan 11, 2024
d3fecfc
feat(Violations): move getErrorForField into MoneyRequestView
trevor-coleman Jan 11, 2024
c19d1a8
Merge branch 'cdanwards/violations/transaction-thread-violations' int…
trevor-coleman Jan 15, 2024
e12dc9f
feat(Violations): fix import
trevor-coleman Jan 15, 2024
32efefc
feat(Violations): update translation params to match violation data o…
trevor-coleman Jan 15, 2024
70e45a8
feat(Violations): change param names to match violation data prop
trevor-coleman Jan 15, 2024
df51b44
feat(Violations): change param names to match violation data prop
trevor-coleman Jan 15, 2024
394caca
feat(Violations): fixes
trevor-coleman Jan 15, 2024
b8b7b18
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Jan 18, 2024
2a624f9
feat(Violations): filter violations by type
trevor-coleman Jan 22, 2024
b80bcdd
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Jan 22, 2024
e37a63a
feat(Violations): fix dependency array
trevor-coleman Jan 22, 2024
ef959ef
feat(Violations): handle default case for missing tag
trevor-coleman Jan 22, 2024
cd807d6
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Jan 23, 2024
8be0e64
feat(Violations): simplify
trevor-coleman Jan 24, 2024
0adddd0
feat(Violations): fix fields
trevor-coleman Jan 24, 2024
a336be8
feat(Violations): reword comment
trevor-coleman Jan 24, 2024
01c552c
feat(Violations): remove redundant check
trevor-coleman Jan 24, 2024
498634a
feat(Violations): add space
trevor-coleman Jan 24, 2024
015764e
feat(Violations): change empty string to single quotes
trevor-coleman Jan 24, 2024
b2ba0b6
feat(Violations): make translations consistent
trevor-coleman Jan 24, 2024
3a75337
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Jan 24, 2024
581f8b0
feat(Violations): rename vars
trevor-coleman Jan 24, 2024
c92ee98
feat(Violations): return empty string if variables are missing
trevor-coleman Jan 24, 2024
a556d5f
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Jan 30, 2024
c9e75c4
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Feb 1, 2024
9cdf6ea
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Feb 2, 2024
a828529
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Feb 3, 2024
abf3255
feat(Violations): restore type
trevor-coleman Feb 3, 2024
5498c82
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Feb 5, 2024
e90cf9f
Merge remote-tracking branch 'origin/main' into 32594-update-style-fo…
trevor-coleman Feb 6, 2024
011a08a
feat(Violations): add deps to array
trevor-coleman Feb 6, 2024
519897a
feat(Violations): replace tag field
trevor-coleman Feb 6, 2024
2327c7c
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Feb 6, 2024
df76a09
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Feb 9, 2024
7eb9560
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Feb 12, 2024
766ccf3
Merge remote-tracking branch 'upstream/main' into 32594-update-style-…
trevor-coleman Feb 12, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
79 changes: 57 additions & 22 deletions src/components/ReportActionItem/MoneyRequestView.js
Original file line number Diff line number Diff line change
Expand Up @@ -26,13 +26,14 @@ import useWindowDimensions from '@hooks/useWindowDimensions';
import * as CardUtils from '@libs/CardUtils';
import compose from '@libs/compose';
import * as CurrencyUtils from '@libs/CurrencyUtils';
import Navigation from '@libs/Navigation/Navigation';
import * as OptionsListUtils from '@libs/OptionsListUtils';
import * as PolicyUtils from '@libs/PolicyUtils';
import * as ReceiptUtils from '@libs/ReceiptUtils';
import * as ReportActionsUtils from '@libs/ReportActionsUtils';
import * as ReportUtils from '@libs/ReportUtils';
import * as TransactionUtils from '@libs/TransactionUtils';
import ViolationsUtils from '@libs/Violations/ViolationsUtils';
import Navigation from '@navigation/Navigation';
import AnimatedEmptyStateBackground from '@pages/home/report/AnimatedEmptyStateBackground';
import reportActionPropTypes from '@pages/home/report/reportActionPropTypes';
import iouReportPropTypes from '@pages/iouReportPropTypes';
Expand Down Expand Up @@ -229,6 +230,43 @@ function MoneyRequestView({report, parentReport, parentReportActions, policyCate
const pendingAction = lodashGet(transaction, 'pendingAction');
const getPendingFieldAction = (fieldPath) => lodashGet(transaction, fieldPath) || pendingAction;

const getErrorForField = useCallback(
(field) => {
// Checks applied when creating a new money request
// NOTE: receipt field can return multiple violations, so we need to handle it separately
const fieldChecks = {
amount: {
isError: transactionAmount === 0,
translationPath: 'common.error.enterAmount',
},
merchant: {
isError: isPolicyExpenseChat && isEmptyMerchant,
translationPath: 'common.error.enterMerchant',
},
date: {
isError: transactionDate === '',
translationPath: 'common.error.enterDate',
},
};

const {isError, translationPath} = fieldChecks[field] || {};

// Return form errors if there are any
if (hasErrors && isError && translationPath) {
return translate(translationPath);
}

// Return violations if there are any
if (canUseViolations && hasViolations(field)) {
const violations = getViolationsForField(field);
return ViolationsUtils.getViolationTranslation(violations[0], translate);
}

return '';
trevor-coleman marked this conversation as resolved.
Show resolved Hide resolved
},
[transactionAmount, isPolicyExpenseChat, isEmptyMerchant, transactionDate, hasErrors, canUseViolations, hasViolations, translate, getViolationsForField],
);

return (
<View style={[StyleUtils.getReportWelcomeContainerStyle(isSmallScreenWidth)]}>
<AnimatedEmptyStateBackground />
Expand Down Expand Up @@ -282,10 +320,9 @@ function MoneyRequestView({report, parentReport, parentReportActions, policyCate
interactive={canEditAmount}
shouldShowRightIcon={canEditAmount}
onPress={() => Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(report.reportID, CONST.EDIT_REQUEST_FIELD.AMOUNT))}
brickRoadIndicator={hasViolations('amount') || (hasErrors && transactionAmount === 0) ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={hasErrors && transactionAmount === 0 ? translate('common.error.enterAmount') : ''}
brickRoadIndicator={getErrorForField('amount') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={getErrorForField('amount')}
/>
{canUseViolations && <ViolationMessages violations={getViolationsForField('amount')} />}
</OfflineWithFeedback>
<OfflineWithFeedback pendingAction={getPendingFieldAction('pendingFields.comment')}>
<MenuItemWithTopDescription
Expand All @@ -297,10 +334,10 @@ function MoneyRequestView({report, parentReport, parentReportActions, policyCate
titleStyle={styles.flex1}
onPress={() => Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(report.reportID, CONST.EDIT_REQUEST_FIELD.DESCRIPTION))}
wrapperStyle={[styles.pv2, styles.taskDescriptionMenuItem]}
brickRoadIndicator={hasViolations('comment') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
brickRoadIndicator={getErrorForField('comment') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={getErrorForField('comment')}
numberOfLinesTitle={0}
/>
{canUseViolations && <ViolationMessages violations={getViolationsForField('comment')} />}
</OfflineWithFeedback>
{isDistanceRequest ? (
<OfflineWithFeedback pendingAction={lodashGet(transaction, 'pendingFields.waypoints') || lodashGet(transaction, 'pendingAction')}>
Expand All @@ -322,10 +359,9 @@ function MoneyRequestView({report, parentReport, parentReportActions, policyCate
shouldShowRightIcon={canEditMerchant}
titleStyle={styles.flex1}
onPress={() => Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(report.reportID, CONST.EDIT_REQUEST_FIELD.MERCHANT))}
brickRoadIndicator={hasViolations('merchant') || (hasErrors && isEmptyMerchant && isPolicyExpenseChat) ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={hasErrors && isPolicyExpenseChat && isEmptyMerchant ? translate('common.error.enterMerchant') : ''}
brickRoadIndicator={getErrorForField('merchant') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={getErrorForField('merchant')}
/>
{canUseViolations && <ViolationMessages violations={getViolationsForField('merchant')} />}
</OfflineWithFeedback>
)}
<OfflineWithFeedback pendingAction={getPendingFieldAction('pendingFields.created')}>
Expand All @@ -336,10 +372,9 @@ function MoneyRequestView({report, parentReport, parentReportActions, policyCate
shouldShowRightIcon={canEditDate}
titleStyle={styles.flex1}
onPress={() => Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(report.reportID, CONST.EDIT_REQUEST_FIELD.DATE))}
brickRoadIndicator={hasViolations('date') || (hasErrors && transactionDate === '') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={hasErrors && transactionDate === '' ? translate('common.error.enterDate') : ''}
brickRoadIndicator={getErrorForField('date') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={getErrorForField('date')}
/>
{canUseViolations && <ViolationMessages violations={getViolationsForField('date')} />}
</OfflineWithFeedback>
{shouldShowCategory && (
<OfflineWithFeedback pendingAction={lodashGet(transaction, 'pendingFields.category') || lodashGet(transaction, 'pendingAction')}>
Expand All @@ -350,9 +385,9 @@ function MoneyRequestView({report, parentReport, parentReportActions, policyCate
shouldShowRightIcon={canEdit}
titleStyle={styles.flex1}
onPress={() => Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(report.reportID, CONST.EDIT_REQUEST_FIELD.CATEGORY))}
brickRoadIndicator={hasViolations('category') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
brickRoadIndicator={getErrorForField('category') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={getErrorForField('category')}
/>
{canUseViolations && <ViolationMessages violations={getViolationsForField('category')} />}
</OfflineWithFeedback>
)}
{shouldShowTag && (
Expand All @@ -364,9 +399,9 @@ function MoneyRequestView({report, parentReport, parentReportActions, policyCate
shouldShowRightIcon={canEdit}
titleStyle={styles.flex1}
onPress={() => Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(report.reportID, CONST.EDIT_REQUEST_FIELD.TAG))}
brickRoadIndicator={hasViolations('tag') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
brickRoadIndicator={getErrorForField('tag') ? CONST.BRICK_ROAD_INDICATOR_STATUS.ERROR : ''}
error={getErrorForField('tag')}
/>
{canUseViolations && <ViolationMessages violations={getViolationsForField('tag')} />}
</OfflineWithFeedback>
)}
{isCardTransaction && (
Expand All @@ -388,13 +423,13 @@ function MoneyRequestView({report, parentReport, parentReportActions, policyCate
isOn={transactionBillable}
onToggle={saveBillable}
/>
{getErrorForField('billable') && (
<ViolationMessages
violations={getViolationsForField('billable')}
isLast
/>
)}
</View>
{hasViolations('billable') && (
<ViolationMessages
violations={getViolationsForField('billable')}
isLast
/>
)}
</>
)}
</View>
Expand Down
5 changes: 2 additions & 3 deletions src/hooks/useViolations.ts
Original file line number Diff line number Diff line change
Expand Up @@ -49,14 +49,13 @@ type ViolationsMap = Map<ViolationField, TransactionViolation[]>;

function useViolations(violations: TransactionViolation[]) {
const violationsByField = useMemo((): ViolationsMap => {
const filteredViolations = violations.filter((violation) => violation.type === 'violation');
const violationGroups = new Map<ViolationField, TransactionViolation[]>();

for (const violation of violations) {
for (const violation of filteredViolations) {
const field = violationFields[violation.name];
const existingViolations = violationGroups.get(field) ?? [];
violationGroups.set(field, [...existingViolations, violation]);
}

return violationGroups ?? new Map();
}, [violations]);

Expand Down
18 changes: 9 additions & 9 deletions src/languages/en.ts
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,6 @@ import type {
ViolationsInvoiceMarkupParams,
ViolationsMaxAgeParams,
ViolationsMissingTagParams,
ViolationsOverAutoApprovalLimitParams,
ViolationsOverCategoryLimitParams,
ViolationsOverLimitParams,
ViolationsPerDayLimitParams,
Expand Down Expand Up @@ -2113,7 +2112,7 @@ export default {
allTagLevelsRequired: 'All tags required',
autoReportedRejectedExpense: ({rejectReason, rejectedBy}: ViolationsAutoReportedRejectedExpenseParams) => `${rejectedBy} rejected this expense with the comment "${rejectReason}"`,
billableExpense: 'Billable no longer valid',
cashExpenseWithNoReceipt: ({amount}: ViolationsCashExpenseWithNoReceiptParams) => `Receipt required over ${amount}`,
cashExpenseWithNoReceipt: ({formattedLimit}: ViolationsCashExpenseWithNoReceiptParams) => `Receipt required${formattedLimit ? ` over ${formattedLimit}` : ''}`,
categoryOutOfPolicy: 'Category no longer valid',
conversionSurcharge: ({surcharge}: ViolationsConversionSurchargeParams) => `Applied ${surcharge}% conversion surcharge`,
customUnitOutOfPolicy: 'Unit no longer valid',
Expand All @@ -2124,17 +2123,18 @@ export default {
maxAge: ({maxAge}: ViolationsMaxAgeParams) => `Date older than ${maxAge} days`,
missingCategory: 'Missing category',
missingComment: 'Description required for selected category',
missingTag: ({tagName}: ViolationsMissingTagParams) => `Missing ${tagName ?? 'tag'}`,
missingTag: ({tagName}: ViolationsMissingTagParams = {}) => `Missing ${tagName ?? 'tag'}`,
trevor-coleman marked this conversation as resolved.
Show resolved Hide resolved
modifiedAmount: 'Amount greater than scanned receipt',
modifiedDate: 'Date differs from scanned receipt',
nonExpensiworksExpense: 'Non-Expensiworks expense',
overAutoApprovalLimit: ({formattedLimitAmount}: ViolationsOverAutoApprovalLimitParams) => `Expense exceeds auto approval limit of ${formattedLimitAmount}`,
overCategoryLimit: ({categoryLimit}: ViolationsOverCategoryLimitParams) => `Amount over ${categoryLimit}/person category limit`,
overLimit: ({amount}: ViolationsOverLimitParams) => `Amount over ${amount}/person limit`,
overLimitAttendee: ({amount}: ViolationsOverLimitParams) => `Amount over ${amount}/person limit`,
perDayLimit: ({limit}: ViolationsPerDayLimitParams) => `Amount over daily ${limit}/person category limit`,
overAutoApprovalLimit: ({formattedLimit}: ViolationsOverLimitParams) => `Expense exceeds auto approval limit of ${formattedLimit}`,
trevor-coleman marked this conversation as resolved.
Show resolved Hide resolved
overCategoryLimit: ({formattedLimit}: ViolationsOverCategoryLimitParams) => `Amount over ${formattedLimit}/person category limit`,
overLimit: ({formattedLimit}: ViolationsOverLimitParams) => `Amount over ${formattedLimit}/person limit`,
overLimitAttendee: ({formattedLimit}: ViolationsOverLimitParams) => `Amount over ${formattedLimit}/person limit`,
perDayLimit: ({formattedLimit}: ViolationsPerDayLimitParams) => `Amount over daily ${formattedLimit}/person category limit`,
receiptNotSmartScanned: 'Receipt not verified. Please confirm accuracy.',
receiptRequired: ({amount, category}: ViolationsReceiptRequiredParams) => `Receipt required over ${amount} ${category ? ' category limit' : ''}`,
receiptRequired: ({formattedLimit, category}: ViolationsReceiptRequiredParams = {}) =>
`Receipt required${formattedLimit ? ` over ${formattedLimit}${category ? ' category limit' : ''}` : ''}`,
rter: ({brokenBankConnection, email, isAdmin, isTransactionOlderThan7Days, member}: ViolationsRterParams) => {
if (brokenBankConnection) {
return isAdmin
Expand Down
20 changes: 11 additions & 9 deletions src/languages/es.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2600,9 +2600,9 @@ export default {
allTagLevelsRequired: 'Todas las etiquetas son obligatorias',
autoReportedRejectedExpense: ({rejectedBy, rejectReason}: ViolationsAutoReportedRejectedExpenseParams) => `${rejectedBy} rechazó la solicitud y comentó "${rejectReason}"`,
billableExpense: 'La opción facturable ya no es válida',
cashExpenseWithNoReceipt: ({amount}: ViolationsCashExpenseWithNoReceiptParams) => `Recibo obligatorio para cantidades mayores de ${amount}`,
cashExpenseWithNoReceipt: ({formattedLimit}: ViolationsCashExpenseWithNoReceiptParams) => `Recibo obligatorio para cantidades mayores de ${formattedLimit}`,
categoryOutOfPolicy: 'La categoría ya no es válida',
conversionSurcharge: ({surcharge}: ViolationsConversionSurchargeParams) => `${surcharge}% de recargo aplicado`,
conversionSurcharge: ({surcharge}: ViolationsConversionSurchargeParams = {}) => `${surcharge}% de recargo aplicado`,
customUnitOutOfPolicy: 'La unidad ya no es válida',
duplicatedTransaction: 'Posible duplicado',
fieldRequired: 'Los campos del informe son obligatorios',
Expand All @@ -2611,17 +2611,19 @@ export default {
maxAge: ({maxAge}: ViolationsMaxAgeParams) => `Fecha de más de ${maxAge} días`,
missingCategory: 'Falta categoría',
missingComment: 'Descripción obligatoria para la categoría seleccionada',
missingTag: ({tagName}: ViolationsMissingTagParams) => `Falta ${tagName}`,
missingTag: ({tagName}: ViolationsMissingTagParams = {}) => `Falta ${tagName ?? 'etiqueta'}`,
modifiedAmount: 'Importe superior al del recibo escaneado',
modifiedDate: 'Fecha difiere del recibo escaneado',
nonExpensiworksExpense: 'Gasto no proviene de Expensiworks',
overAutoApprovalLimit: ({formattedLimitAmount}: ViolationsOverAutoApprovalLimitParams) => `Importe supera el límite de aprobación automática de ${formattedLimitAmount}`,
overCategoryLimit: ({categoryLimit}: ViolationsOverCategoryLimitParams) => `Importe supera el límite para la categoría de ${categoryLimit}/persona`,
overLimit: ({amount}: ViolationsOverLimitParams) => `Importe supera el límite de ${amount}/persona`,
overLimitAttendee: ({amount}: ViolationsOverLimitParams) => `Importe supera el límite de ${amount}/persona`,
perDayLimit: ({limit}: ViolationsPerDayLimitParams) => `Importe supera el límite diario de la categoría de ${limit}/persona`,
overAutoApprovalLimit: ({formattedLimit}: ViolationsOverAutoApprovalLimitParams) =>
`Importe supera el límite de aprobación automática${formattedLimit ? ` de ${formattedLimit}` : ''}`,
overCategoryLimit: ({formattedLimit}: ViolationsOverCategoryLimitParams) => `Importe supera el límite para la categoría${formattedLimit ? ` de ${formattedLimit}/persona` : ''}`,
overLimit: ({formattedLimit}: ViolationsOverLimitParams) => `Importe supera el límite${formattedLimit ? ` de ${formattedLimit}/persona` : ''}`,
overLimitAttendee: ({formattedLimit}: ViolationsOverLimitParams) => `Importe supera el límite${formattedLimit ? ` de ${formattedLimit}/persona` : ''}`,
perDayLimit: ({formattedLimit}: ViolationsPerDayLimitParams) => `Importe supera el límite diario de la categoría${formattedLimit ? ` de ${formattedLimit}/persona` : ''}`,
receiptNotSmartScanned: 'Recibo no verificado. Por favor, confirma su exactitud',
receiptRequired: ({amount, category}: ViolationsReceiptRequiredParams) => `Recibo obligatorio para importes sobre ${category ? 'el limite de la categoría de ' : ''}${amount}`,
receiptRequired: ({formattedLimit, category}: ViolationsReceiptRequiredParams = {}) =>
`Recibo obligatorio${formattedLimit ? ` para importes sobre ${category ? 'el limite de la categoría de ' : ''}${formattedLimit}` : ''}`,
Comment on lines +2647 to +2655
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Are all the translations final and approved?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes.

rter: ({brokenBankConnection, isAdmin, email, isTransactionOlderThan7Days, member}: ViolationsRterParams) => {
if (brokenBankConnection) {
return isAdmin
Expand Down
12 changes: 6 additions & 6 deletions src/languages/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -215,7 +215,7 @@ type WalletProgramParams = {walletProgram: string};

type ViolationsAutoReportedRejectedExpenseParams = {rejectedBy: string; rejectReason: string};

type ViolationsCashExpenseWithNoReceiptParams = {amount: string};
type ViolationsCashExpenseWithNoReceiptParams = {formattedLimit?: string};

type ViolationsConversionSurchargeParams = {surcharge?: number};

Expand All @@ -225,15 +225,15 @@ type ViolationsMaxAgeParams = {maxAge: number};

type ViolationsMissingTagParams = {tagName?: string};

type ViolationsOverAutoApprovalLimitParams = {formattedLimitAmount: string};
type ViolationsOverAutoApprovalLimitParams = {formattedLimit?: string};

type ViolationsOverCategoryLimitParams = {categoryLimit: string};
type ViolationsOverCategoryLimitParams = {formattedLimit?: string};

type ViolationsOverLimitParams = {amount: string};
type ViolationsOverLimitParams = {formattedLimit?: string};

type ViolationsPerDayLimitParams = {limit: string};
type ViolationsPerDayLimitParams = {formattedLimit?: string};

type ViolationsReceiptRequiredParams = {amount: string; category?: string};
type ViolationsReceiptRequiredParams = {formattedLimit?: string; category?: string};

type ViolationsRterParams = {
brokenBankConnection: boolean;
Expand Down
Loading
Loading