Skip to content

Commit e854f7f

Browse files
committed
feat: Ensure all the USD displays have prefix and USD suffix
1 parent 22e733c commit e854f7f

File tree

6 files changed

+330
-77
lines changed

6 files changed

+330
-77
lines changed

src/containers/Vault/VaultHeader/index.tsx

Lines changed: 35 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -270,7 +270,7 @@ export const VaultHeader = ({ data, vaultId, displayCurrency }: Props) => {
270270
const convertedAmount = convertToDisplayCurrency(assetsTotal)
271271
if (
272272
convertedAmount === undefined &&
273-
displayCurrency === 'usd'
273+
displayCurrency === 'USD'
274274
) {
275275
return '--'
276276
}
@@ -284,15 +284,23 @@ export const VaultHeader = ({ data, vaultId, displayCurrency }: Props) => {
284284
return '--'
285285
// Note: As per the NumberFormat policy, prices in the range of [10_000, 1M] do not display decimal values
286286
// Very large prices (greater than 1M must have two decimal places)
287+
const displayedCurrency: string = getDisplayCurrencyLabel()
287288
if (Number(amount) < 1000000 && Number(amount) >= 10000) {
288-
if (isCurrencyExoticSymbol(asset?.currency))
289-
return `${getDisplayCurrencyLabel()} ${parseAmount(amount, 0)}`
290-
return `${parseAmount(amount, 0)} ${getDisplayCurrencyLabel()}`
289+
if (
290+
isCurrencyExoticSymbol(asset?.currency) &&
291+
displayedCurrency !== 'USD'
292+
)
293+
return `${getCurrencySymbol(asset?.currency)} ${parseAmount(amount, 0)}`
294+
// All USD denominated amounts are prefixed by `$` symbol
295+
return `${displayedCurrency === 'USD' ? '$' : ''}${parseAmount(amount, 0)} ${displayedCurrency}`
291296
}
292297

293-
if (isCurrencyExoticSymbol(asset?.currency))
294-
return `${getDisplayCurrencyLabel()} ${parseAmount(amount, 2)}`
295-
return `${parseAmount(amount, 2)} ${getDisplayCurrencyLabel()}`
298+
if (
299+
isCurrencyExoticSymbol(asset?.currency) &&
300+
displayedCurrency !== 'USD'
301+
)
302+
return `${getCurrencySymbol(asset?.currency)} ${parseAmount(amount, 2)}`
303+
return `${displayedCurrency === 'USD' ? '$' : ''}${parseAmount(amount, 2)} ${displayedCurrency}`
296304
})()}
297305
/>
298306
<TokenTableRow
@@ -303,9 +311,13 @@ export const VaultHeader = ({ data, vaultId, displayCurrency }: Props) => {
303311
const parsedAmt = parseAmount(assetsMaximum, 2)
304312
if (['0', '0.00', '0.0000'].includes(parsedAmt)) return '--'
305313

306-
if (isCurrencyExoticSymbol(asset?.currency))
314+
const displayedCurrency: string = getDisplayCurrencyLabel()
315+
if (
316+
isCurrencyExoticSymbol(asset?.currency) &&
317+
displayedCurrency !== 'USD'
318+
)
307319
return `${getCurrencySymbol(asset?.currency)} ${parsedAmt}`
308-
return `${parsedAmt} ${getCurrencySymbol(asset?.currency ?? asset?.mpt_issuance_id)}`
320+
return `${displayedCurrency === 'USD' ? '$' : ''}${parsedAmt} ${displayedCurrency}`
309321
})()}
310322
/>
311323
<TokenTableRow
@@ -317,19 +329,29 @@ export const VaultHeader = ({ data, vaultId, displayCurrency }: Props) => {
317329
value={(() => {
318330
const parsedAmt = parseAmount(assetsAvailable ?? '0', 2)
319331
if (['0', '0.00', '0.0000'].includes(parsedAmt)) return '--'
320-
if (isCurrencyExoticSymbol(asset?.currency))
332+
333+
const displayedCurrency: string = getDisplayCurrencyLabel()
334+
if (
335+
isCurrencyExoticSymbol(asset?.currency) &&
336+
displayedCurrency !== 'USD'
337+
)
321338
return `${getCurrencySymbol(asset?.currency)} ${parsedAmt}`
322-
return `${parsedAmt} ${getCurrencySymbol(asset?.currency ?? asset?.mpt_issuance_id)}`
339+
return `${displayedCurrency === 'USD' ? '$' : ''}${parsedAmt} ${displayedCurrency}`
323340
})()}
324341
/>
325342
<TokenTableRow
326343
label={t('unrealized_loss')}
327344
value={(() => {
328345
const parsedAmt = parseAmount(lossUnrealized ?? '0', 2)
329346
if (['0', '0.00', '0.0000'].includes(parsedAmt)) return '--'
330-
if (isCurrencyExoticSymbol(asset?.currency))
347+
348+
const displayedCurrency: string = getDisplayCurrencyLabel()
349+
if (
350+
isCurrencyExoticSymbol(asset?.currency) &&
351+
displayedCurrency !== 'USD'
352+
)
331353
return `${getCurrencySymbol(asset?.currency)} ${parsedAmt}`
332-
return `${parsedAmt} ${getCurrencySymbol(asset?.currency ?? asset?.mpt_issuance_id)}`
354+
return `${displayedCurrency === 'USD' ? '$' : ''}${parsedAmt} ${displayedCurrency}`
333355
})()}
334356
/>
335357
</tbody>

src/containers/Vault/VaultHeader/test/VaultHeader.test.tsx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1142,7 +1142,7 @@ describe('VaultHeader Component', () => {
11421142

11431143
// 1,000,000 XRP * 2.5 = 2,500,000 USD = "2.50M USD"
11441144
// formatAmount joins [prefix, formattedNum, currency] with spaces
1145-
expect(screen.getByText('USD 2.50M')).toBeInTheDocument()
1145+
expect(screen.getByText('$2.50M USD')).toBeInTheDocument()
11461146
})
11471147

11481148
it('displays RLUSD TVL as USD with 1:1 conversion when displayCurrency is "usd"', () => {
@@ -1164,7 +1164,7 @@ describe('VaultHeader Component', () => {
11641164

11651165
// RLUSD is a stablecoin pegged 1:1 to USD
11661166
// 5,000,000 RLUSD = "5.00M USD"
1167-
expect(screen.getByText('5.00M USD')).toBeInTheDocument()
1167+
expect(screen.getByText('$5.00M USD')).toBeInTheDocument()
11681168
})
11691169

11701170
it('convert native currency EUR into USD displayed currency', () => {
@@ -1190,7 +1190,7 @@ describe('VaultHeader Component', () => {
11901190
)
11911191

11921192
const tvlRow = screen.getByText('Total Value Locked (TVL)').closest('tr')
1193-
expect(tvlRow).toHaveTextContent('Total Value Locked (TVL)2.00M USD')
1193+
expect(tvlRow).toHaveTextContent('Total Value Locked (TVL)$2.00M USD')
11941194
})
11951195
})
11961196
})

src/containers/Vault/VaultLoans/BrokerDetails.tsx

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,12 +68,15 @@ export const BrokerDetails = ({
6868
inputAsset: AssetInfo | undefined,
6969
): string => {
7070
const convertedAmount = convertToDisplayCurrency(amount)
71-
if (convertedAmount === undefined && displayCurrency === 'usd') {
71+
if (convertedAmount === undefined && displayCurrency === 'USD') {
7272
return '--'
7373
}
7474

7575
const finalDisplayAmount = convertedAmount ?? amount
7676
if (finalDisplayAmount !== undefined) {
77+
if (displayCurrency === 'USD') {
78+
return `$${parseAmount(finalDisplayAmount, 2)} USD`
79+
}
7780
if (
7881
inputAsset?.currency &&
7982
isCurrencyExoticSymbol(inputAsset?.currency)

src/containers/Vault/VaultLoans/LoanRow.tsx

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -81,9 +81,9 @@ export const LoanRow = ({
8181
}
8282

8383
const prefix = displayCurrency === 'USD' ? '$' : ''
84-
if (isCurrencySpecialSymbol)
85-
return `${getCurrencySymbol(currency)} ${prefix}${parseAmount(displayNum, 1, language)}`
86-
return `${prefix}${parseAmount(displayNum, 1, language)} ${currency}`
84+
if (isCurrencySpecialSymbol && displayCurrency !== 'USD')
85+
return `${getCurrencySymbol(currency)} ${parseAmount(displayNum, 1, language)}`
86+
return `${prefix}${parseAmount(displayNum, 1, language)} ${displayCurrency}`
8787
}
8888

8989
const formatFee = (fee: string | number): string => {
@@ -103,8 +103,8 @@ export const LoanRow = ({
103103

104104
const prefix = displayCurrency === 'USD' ? '$' : ''
105105
if (isCurrencySpecialSymbol)
106-
return `${getCurrencySymbol(currency)} ${prefix}${parseAmount(displayNum, 1, language)}`
107-
return `${prefix}${parseAmount(displayNum, 1, language)} ${currency}`
106+
return `${getCurrencySymbol(currency)} ${parseAmount(displayNum, 1, language)}`
107+
return `${prefix}${parseAmount(displayNum, 1, language)} ${displayCurrency}`
108108
}
109109

110110
const formatGracePeriod = (seconds: number): string => {

src/containers/Vault/VaultLoans/test/BrokerLoansTable.test.tsx

Lines changed: 86 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -906,45 +906,59 @@ describe('BrokerLoansTable Component', () => {
906906
* =========================================
907907
* Verify currency is passed through to LoanRow.
908908
*/
909-
describe('Currency Prop', () => {
910-
it('passes currency to loan rows', () => {
911-
const loans = [createMockLoan({ TotalValueOutstanding: '1000' })]
909+
describe('Currency Prop tests', () => {
910+
it('renders correctly with non-XRP/non-USD currency', () => {
911+
// Test with EUR - an arbitrary IOU currency that is neither XRP nor RLUSD
912+
// This ensures the component handles any currency type correctly
913+
const loans = [
914+
createMockLoan({
915+
index: 'LOAN_EUR_1',
916+
PrincipalOutstanding: '5000',
917+
TotalValueOutstanding: '5250',
918+
}),
919+
]
912920

913-
render(
921+
const { container } = render(
914922
<TestWrapper>
915923
<BrokerLoansTable
916924
loans={loans}
917-
currency="RLUSD"
918-
displayCurrency={defaultDisplayCurrency}
919-
asset={{ currency: 'RLUSD', issuer: 'rTestIssuer' }}
925+
currency="EUR"
926+
displayCurrency="EUR"
927+
asset={{ currency: 'EUR', issuer: 'rTestIssuer' }}
920928
/>
921929
</TestWrapper>,
922930
)
923931

924-
// The amount cells should include the currency (amount-requested and outstanding-balance)
925-
// Using getAllByText since currency appears in multiple columns
926-
const elementsWithCurrency = screen.getAllByText(/RLUSD/)
927-
expect(elementsWithCurrency.length).toBeGreaterThan(0)
932+
// Table should render with loan row
933+
expect(container.querySelector('.loan-row')).toBeInTheDocument()
934+
935+
// Verify the amount-requested and outstanding-balance cells display EUR values
936+
const loanRow = container.querySelector('.loan-row')!
937+
const amountRequested = loanRow.querySelector('.amount-requested')
938+
const outstandingBalance = loanRow.querySelector('.outstanding-balance')
939+
expect(amountRequested).toHaveTextContent('5,250.00 EUR')
940+
expect(outstandingBalance).toHaveTextContent('5,250.00 EUR')
928941
})
929942

930-
it('renders correctly with non-XRP/non-RLUSD currency', () => {
931-
// Test with EUR - an arbitrary IOU currency that is neither XRP nor RLUSD
932-
// This ensures the component handles any currency type correctly
943+
it(`Render the BrokerLoans table with BTC exotic currency`, () => {
933944
const loans = [
934945
createMockLoan({
935-
index: 'LOAN_EUR_1',
946+
index: 'LOAN_BTC_1',
936947
PrincipalOutstanding: '5000',
937948
TotalValueOutstanding: '5250',
938949
}),
939950
]
940951

952+
const btcAsset = { currency: 'BTC', issuer: 'rTestIssuer' }
953+
941954
const { container } = render(
942955
<TestWrapper>
943956
<BrokerLoansTable
944957
loans={loans}
945-
currency="EUR"
946-
displayCurrency={defaultDisplayCurrency}
947-
asset={{ currency: 'EUR', issuer: 'rTestIssuer' }}
958+
currency={btcAsset.currency}
959+
displayCurrency={btcAsset.currency}
960+
asset={btcAsset}
961+
isCurrencySpecialSymbol={isCurrencyExoticSymbol(btcAsset.currency)}
948962
/>
949963
</TestWrapper>,
950964
)
@@ -953,15 +967,15 @@ describe('BrokerLoansTable Component', () => {
953967
expect(container.querySelector('.loan-row')).toBeInTheDocument()
954968

955969
// Currency should appear in the amount columns
956-
const elementsWithCurrency = screen.getAllByText(/EUR/)
970+
const elementsWithCurrency = screen.getAllByText(/\u20BF 5,250.00/)
957971
expect(elementsWithCurrency.length).toBeGreaterThan(0)
958972

959973
// Verify XRP and USD do not appear - ensures EUR is used throughout
960974
expect(screen.queryByText(/XRP/)).not.toBeInTheDocument()
961975
expect(screen.queryByText(/USD/)).not.toBeInTheDocument()
962976
})
963977

964-
it(`Render the BrokerLoans table with BTC exotic currency`, () => {
978+
it(`display a BTC-denominated Loan in USD currency`, () => {
965979
const loans = [
966980
createMockLoan({
967981
index: 'LOAN_BTC_1',
@@ -977,7 +991,7 @@ describe('BrokerLoansTable Component', () => {
977991
<BrokerLoansTable
978992
loans={loans}
979993
currency={btcAsset.currency}
980-
displayCurrency={btcAsset.currency}
994+
displayCurrency="USD"
981995
asset={btcAsset}
982996
isCurrencySpecialSymbol={isCurrencyExoticSymbol(btcAsset.currency)}
983997
/>
@@ -986,31 +1000,63 @@ describe('BrokerLoansTable Component', () => {
9861000

9871001
// Table should render with loan row
9881002
expect(container.querySelector('.loan-row')).toBeInTheDocument()
1003+
const loanRow = container.querySelector('.loan-row')!
1004+
const amountRequested = loanRow.querySelector('.amount-requested')
1005+
const outstandingBalance = loanRow.querySelector('.outstanding-balance')
1006+
expect(amountRequested).toHaveTextContent('$7,875.00 USD')
1007+
expect(outstandingBalance).toHaveTextContent('$7,875.00 USD')
1008+
})
9891009

990-
// Currency should appear in the amount columns
991-
const elementsWithCurrency = screen.getAllByText(/\u20BF 5,250.00/)
992-
expect(elementsWithCurrency.length).toBeGreaterThan(0)
1010+
it('display a XRP-denominated Loan in XRP currency', () => {
1011+
const loans = [createMockLoan()]
9931012

994-
// Verify XRP and USD do not appear - ensures EUR is used throughout
995-
expect(screen.queryByText(/XRP/)).not.toBeInTheDocument()
996-
expect(screen.queryByText(/USD/)).not.toBeInTheDocument()
1013+
// This should not throw - currency defaults to XRP because XRP is the asset of the Vault.
1014+
const { container } = render(
1015+
<TestWrapper>
1016+
<BrokerLoansTable
1017+
loans={loans}
1018+
currency={defaultAsset.currency}
1019+
displayCurrency={defaultDisplayCurrency}
1020+
asset={defaultAsset}
1021+
isCurrencySpecialSymbol={isCurrencyExoticSymbol(
1022+
defaultAsset.currency,
1023+
)}
1024+
/>
1025+
</TestWrapper>,
1026+
)
1027+
1028+
// Verify the amount-requested and outstanding-balance cells display EUR values
1029+
const loanRow = container.querySelector('.loan-row')!
1030+
const amountRequested = loanRow.querySelector('.amount-requested')
1031+
const outstandingBalance = loanRow.querySelector('.outstanding-balance')
1032+
expect(amountRequested).toHaveTextContent('\uE900 10.5K')
1033+
expect(outstandingBalance).toHaveTextContent('\uE900 10.5K')
9971034
})
9981035

999-
it('defaults to empty string when currency not provided', () => {
1036+
it(`display a XRP-denominated Loan in USD currency`, () => {
10001037
const loans = [createMockLoan()]
10011038

1002-
// This should not throw - currency defaults to ''
1003-
expect(() =>
1004-
render(
1005-
<TestWrapper>
1006-
<BrokerLoansTable
1007-
loans={loans}
1008-
displayCurrency={defaultDisplayCurrency}
1009-
asset={defaultAsset}
1010-
/>
1011-
</TestWrapper>,
1012-
),
1013-
).not.toThrow()
1039+
// This should not throw - currency defaults to XRP because XRP is the asset of the Vault.
1040+
const { container } = render(
1041+
<TestWrapper>
1042+
<BrokerLoansTable
1043+
loans={loans}
1044+
currency={defaultAsset.currency}
1045+
displayCurrency="USD"
1046+
asset={defaultAsset}
1047+
isCurrencySpecialSymbol={isCurrencyExoticSymbol(
1048+
defaultAsset.currency,
1049+
)}
1050+
/>
1051+
</TestWrapper>,
1052+
)
1053+
1054+
// Verify the amount-requested and outstanding-balance cells display EUR values
1055+
const loanRow = container.querySelector('.loan-row')!
1056+
const amountRequested = loanRow.querySelector('.amount-requested')
1057+
const outstandingBalance = loanRow.querySelector('.outstanding-balance')
1058+
expect(amountRequested).toHaveTextContent('$15.8K USD')
1059+
expect(outstandingBalance).toHaveTextContent('$15.8K USD')
10141060
})
10151061
})
10161062
})

0 commit comments

Comments
 (0)