Skip to content

fix: re-parse required tokens when token rates load after transaction added#8714

Draft
matthewwalsh0 wants to merge 4 commits intomainfrom
fix/pay-recompute-required-tokens-on-rates
Draft

fix: re-parse required tokens when token rates load after transaction added#8714
matthewwalsh0 wants to merge 4 commits intomainfrom
fix/pay-recompute-required-tokens-on-rates

Conversation

@matthewwalsh0
Copy link
Copy Markdown
Member

Explanation

TransactionPayController.parseRequiredTokens returns an empty array when token fiat rates are unavailable (getTokenFiatRate returns undefined). The result is stored in transactionData[id].tokens and surfaced to clients via the controller's state.

Currently, the only retry trigger is a txParams.data change (handled by the existing pollTransactionChanges subscription). Clients that gate data edits on having a resolved required token are therefore stuck: the rates never get re-checked because the data never changes, and the data never changes because the client refuses to encode an edit without a known target token's decimals. The required-token state remains empty for the lifetime of the confirmation, even after marketData and currencyRates populate.

This change adds a second subscription that re-runs parseRequiredTokens when the rate sources update, but only for entries whose tokens array is currently empty and whose underlying transaction is not finalized.

Implementation

  • New pollRateChanges helper in utils/transaction.ts, sibling to the existing pollTransactionChanges.
  • Subscribes to the same rate sources getTokenFiatRate reads from, gated on the assetsUnifyState feature flag:
    • Flag enabled: AssetsController:stateChange.
    • Flag disabled (default): TokenRatesController:stateChange and CurrencyRateController:stateChange.
  • Handler iterates transactionData from controller state, skipping entries that already have non-empty tokens and transactions whose status is in FINALIZED_STATUSES. Remaining candidates are re-parsed via the existing onTransactionChange path.
  • TransactionPayController constructor wires pollRateChanges next to the existing pollTransactionChanges call, passing a () => this.state getter.
  • Added required event types to AllowedEvents: AssetsControllerStateChangeEvent, CurrencyRateStateChange, TokenRatesControllerStateChangeEvent.

Out of scope

  • Stale rates after a successful parse. The handler only retries entries with tokens.length === 0; entries that previously parsed successfully are not invalidated when rates change. Clients increasingly read aggregated totals?.targetAmount.usd rather than per-token amounts, so this hasn't been a problem in practice — but it remains a latent staleness exposure that this PR does not address.

References

N/A.

Changelog

Checklist

  • I've updated the test suite for new or updated code as appropriate
  • I've updated documentation (JSDoc, Markdown, etc.) for new or updated code as appropriate
  • I've highlighted breaking changes using the "BREAKING" category above as appropriate
  • I've prepared draft pull requests for clients and consumer packages to resolve any breaking changes

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant