diff --git a/cashtab/src/components/Alias/Alias.js b/cashtab/src/components/Alias/Alias.js --- a/cashtab/src/components/Alias/Alias.js +++ b/cashtab/src/components/Alias/Alias.js @@ -85,6 +85,8 @@ aliasServerError, aliasPrices, setAliasPrices, + aliasPriceError, + setAliasPriceError, } = ContextValue; const walletState = getWalletState(wallet); const { balances } = walletState; @@ -119,7 +121,7 @@ try { setAliasPrices(await queryAliasServer('prices')); } catch (err) { - setAliasValidationError( + setAliasPriceError( `Failed to fetch alias price information from server. Alias registration disabled. Refresh page to try again.`, ); passLoadingStatus(false); @@ -500,12 +502,21 @@ + {aliasValidationError + ? aliasValidationError + : ''} + + ) } inputProps={{ addonAfter: ' . xec', @@ -532,11 +543,10 @@ aliasPrices.prices .length !== 1 ) { - setAliasValidationError( - `Alias registration is temporarily unavailable, please check again later.`, + setAliasPriceError( + `Alias pricing error, registration is temporarily unavailable. Please check again later.`, ); setIsValidAliasInput(false); - return; } // TODO Once chronik-client has been upgraded for in-node chronik, update // this price parsing logic to use the new ws for blockheight comparisons. @@ -602,7 +612,8 @@ !isValidAliasAddressInput || aliasValidationError !== false || - aliasServerError !== false + aliasServerError !== false || + aliasPriceError !== false } onClick={() => preparePreviewModal() @@ -660,9 +671,12 @@ )} - {aliasServerError && - aliasValidationError === false && - aliasServerError} + {aliasPriceError + ? aliasPriceError + : aliasValidationError + ? aliasValidationError + : aliasServerError && + aliasServerError} - {aliasServerError && - aliasValidationError === false && - aliasServerError} + {aliasPriceError + ? aliasPriceError + : aliasValidationError + ? aliasValidationError + : aliasServerError && + aliasServerError} diff --git a/cashtab/src/components/Alias/__tests__/Alias.test.js b/cashtab/src/components/Alias/__tests__/Alias.test.js --- a/cashtab/src/components/Alias/__tests__/Alias.test.js +++ b/cashtab/src/components/Alias/__tests__/Alias.test.js @@ -44,7 +44,7 @@ // Activate alias features aliasSettings.aliasEnabled = true; - +/* eslint testing-library/no-container: 0 */ describe('', () => { afterEach(async () => { jest.clearAllMocks(); @@ -183,13 +183,13 @@ ).toHaveTextContent('chicken444.xec'); }); }); - it('Registered and Pending lists still renders when aliasValidationError is populated and aliasServerError is false', async () => { + it('Registered and Pending lists still renders upon alias pricing response error and aliasServerError is false', async () => { const mockedChronik = await initializeCashtabStateForTests( walletWithXecAndTokens, localforage, ); - // Note: Not mocking the '/prices' API call here in order to populate aliasValidationError + // Note: Not mocking the '/prices' API call here in order to populate aliasPriceError // Mock the refreshAliases() call to alias-server's '/address' endpoint upon component load const addressFetchUrl = `${aliasSettings.aliasServerBaseUrl}/address/${walletWithXecAndTokens.Path1899.cashAddress}`; @@ -201,7 +201,22 @@ Promise.resolve(aliasAddressTwoRegisteredOnePending), }); - render(); + const { container } = render( + , + ); + + // Ensure the alias pricing error exists and the Register Alias button is disabled + // Note: the pricing error in is wrapped within an AntdFormWrapper, hence + // getByTestId is not possible. getByText is also problematic in that it returns multiple + // instances and attempts to reference the [0] index results in not found response. + // As a final mitigation, using the querySelector here because the output from findByText + // shows the pricing error message residing within the [class="ant-form-item-explain-error"] tag. + expect( + container.querySelector('[class="ant-form-item-explain-error"]'), + ).toBeInTheDocument(); + expect( + screen.getByRole('button', { name: /Register Alias/ }), + ).toHaveProperty('disabled', true); // Registered and Pending Alias dropdowns are rendered expect( diff --git a/cashtab/src/hooks/useWallet.js b/cashtab/src/hooks/useWallet.js --- a/cashtab/src/hooks/useWallet.js +++ b/cashtab/src/hooks/useWallet.js @@ -74,6 +74,7 @@ }); const [aliasPrices, setAliasPrices] = useState(null); const [aliasServerError, setAliasServerError] = useState(false); + const [aliasPriceError, setAliasPriceError] = useState(false); const [aliasIntervalId, setAliasIntervalId] = useState(null); const [chaintipBlockheight, setChaintipBlockheight] = useState(0); const { balances, tokens } = isValidStoredWallet(wallet) @@ -1550,6 +1551,8 @@ setAliases, aliasServerError, setAliasServerError, + aliasPriceError, + setAliasPriceError, aliasPrices, setAliasPrices, getActiveWalletFromLocalForage,