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

feat: speedup pending transactions #3425

Merged
merged 4 commits into from
Apr 8, 2024
Merged

feat: speedup pending transactions #3425

merged 4 commits into from
Apr 8, 2024

Conversation

schmanu
Copy link
Member

@schmanu schmanu commented Mar 12, 2024

What it solves

Stuck transactions due to moving gas prices disappear after a 1 minute timeout.

Resolves #3107

How this PR fixes it

  • Shows pending transactions and offers a Speedup button after the timeout instead of showing an error and removing them
  • Sped up transactions use the current gasPrice but speed it up by
    • Multiplying the maxPriorityFeePerGasby two
    • Adjust the maxFeePerGas accordingly

How to test it

  • Submit a transaction and overwrite the baseFee in MetaMask to a very low value (e.g. 1)
  • Click the speedup button and resubmit the tx

Screenshots

Checklist

  • I've tested the branch on mobile 📱
  • I've documented how it affects the analytics (if at all) 📊
  • I've written a unit/e2e test for it (if applicable) 🧑‍💻

@schmanu schmanu requested a review from compojoom March 12, 2024 13:46
Copy link

github-actions bot commented Mar 12, 2024

Copy link

ESLint Summary View Full Report

Annotations are provided inline on the Files Changed tab. You can also see all annotations that were generated on the annotations page.

Type Occurrences Fixable
Errors 0 0
Warnings 0 0
Ignored 0 N/A
  • Result: ✅ success
  • Annotations: 0 total

Report generated by eslint-plus-action

Copy link

github-actions bot commented Mar 12, 2024

📦 Next.js Bundle Analysis for safe-wallet-web

This analysis was generated by the Next.js Bundle Analysis action. 🤖

⚠️ Global Bundle Size Increased

Page Size (compressed)
global 997.54 KB (🟡 +433 B)
Details

The global bundle is the javascript bundle that loads alongside every page. It is in its own category because its impact is much higher - an increase to its size means that every page on your website loads slower, and a decrease means every page loads faster.

Any third party scripts you have added directly to your app using the <script> tag are not accounted for in this analysis

If you want further insight into what is behind the changes, give @next/bundle-analyzer a try!

Eight Pages Changed Size

The following pages changed size from the code in this PR compared to its base branch:

Page Size (compressed) First Load
/apps/open 78.52 KB (🟡 +11.72 KB) 1.05 MB
/balances 29.91 KB (🟡 +2 B) 1 MB
/home 57.38 KB (🟡 +1 B) 1.03 MB
/transactions 103.71 KB (🟡 +11.72 KB) 1.08 MB
/transactions/history 103.67 KB (🟡 +11.72 KB) 1.08 MB
/transactions/messages 63.38 KB (🟡 +11.72 KB) 1.04 MB
/transactions/queue 58.98 KB (🟡 +11.72 KB) 1.03 MB
/transactions/tx 48.33 KB (🔴 +11.72 KB) 1.02 MB
Details

Only the gzipped size is provided here based on an expert tip.

First Load is the size of the global bundle plus the bundle for the individual page. If a user were to show up to your website and land on a given page, the first load size represents the amount of javascript that user would need to download. If next/link is used, subsequent page loads would only need to download that page's bundle (the number in the "Size" column), since the global bundle has already been downloaded.

Any third party scripts you have added directly to your app using the <script> tag are not accounted for in this analysis

Next to the size is how much the size has increased or decreased compared with the base branch of this PR. If this percentage has increased by 20% or more, there will be a red status indicator applied, indicating that special attention should be given to this.

Copy link

github-actions bot commented Mar 12, 2024

Coverage report

St.
Category Percentage Covered / Total
🟡 Statements
79.01% (-0.35% 🔻)
11178/14147
🔴 Branches
58.23% (-0.19% 🔻)
2639/4532
🟡 Functions
65.95% (+0.01% 🔼)
1799/2728
🟢 Lines
80.29% (-0.38% 🔻)
10073/12545
Show new covered files 🐣
St.
File Statements Branches Functions Lines
🟢
... / SimpleTxWatcher.ts
100% 100% 100% 100%
🔴
... / SpeedUpMonitor.tsx
37.93% 0% 0% 40.74%
🔴
... / SpeedUpModal.tsx
38.33% 0% 0% 38.98%
🔴
... / useCounter.ts
16.67% 0% 0% 20%
🟢
... / IsSpeedableTx.tsx
100% 100% 100% 100%
Show files with reduced coverage 🔻
St.
File Statements Branches Functions Lines
🟢
... / txHistorySlice.ts
85.71% (+1.1% 🔼)
57.14% (-2.86% 🔻)
50%
91.67% (+0.76% 🔼)
🔴
... / dispatch.ts
40.22% (-7.21% 🔻)
43.48% (+0.14% 🔼)
30% (+0.37% 🔼)
39.52% (-7.05% 🔻)
🟢
... / ethers-utils.ts
76.47% (-11.76% 🔻)
33.33%
66.67% (-16.67% 🔻)
83.33% (-8.33% 🔻)
🟢
... / useGasPrice.ts
95% (-0.89% 🔻)
80.95% (-1.4% 🔻)
100%
94.81% (-0.91% 🔻)
🟢
... / index.tsx
100%
91.67% (-1.19% 🔻)
100% 100%
🟢
... / useTransactionStatus.ts
91.3% (-4.15% 🔻)
66.67% 100% 95%

Test suite run success

1408 tests passing in 196 suites.

Report generated by 🧪jest coverage report action from e10be15

Copy link

github-actions bot commented Mar 15, 2024

ESLint Summary View Full Report

Annotations are provided inline on the Files Changed tab. You can also see all annotations that were generated on the annotations page.

Type Occurrences Fixable
Errors 0 0
Warnings 0 0
Ignored 0 N/A
  • Result: ✅ success
  • Annotations: 0 total

Report generated by eslint-plus-action

@compojoom compojoom marked this pull request as ready for review March 19, 2024 13:48
Copy link

github-actions bot commented Mar 20, 2024

ESLint Summary View Full Report

Annotations are provided inline on the Files Changed tab. You can also see all annotations that were generated on the annotations page.

Type Occurrences Fixable
Errors 0 0
Warnings 2 0
Ignored 0 N/A
  • Result: ✅ success

  • Annotations: 2 total


[warning] react-hooks/exhaustive-deps

verifies the list of dependencies for Hooks like useEffect and similar


Report generated by eslint-plus-action

Copy link
Member

@usame-algan usame-algan left a comment

Choose a reason for hiding this comment

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

Works really nice already! As discussed with @compojoom we need to find a way to clean up pending transactions if they were sped-up from outside the UI. Our idea is to check the txHistory whenever it updates and compare the newest nonce with the pending tx nonce. If its the same we can remove the pending tx.

I also noticed that the notifications in Figma have a linear progress bar. Did we decide not to implement that?

Screenshot 2024-03-20 at 16 22 01

public/images/common/ic-rocket-speedup.svg Outdated Show resolved Hide resolved
src/components/transactions/TxSummary/PendingActions.tsx Outdated Show resolved Hide resolved
src/components/transactions/TxSummary/PendingActions.tsx Outdated Show resolved Hide resolved
src/components/transactions/TxSummary/PendingActions.tsx Outdated Show resolved Hide resolved
src/components/transactions/TxSummary/PendingActions.tsx Outdated Show resolved Hide resolved
src/features/speedup/components/SpeedUpMonitor.tsx Outdated Show resolved Hide resolved
src/features/speedup/components/SpeedUpMonitor.tsx Outdated Show resolved Hide resolved
Comment on lines 43 to 64
<Alert
severity="warning"
icon={<SvgIcon component={Rocket} />}
action={<Button onClick={() => setOpenSpeedUpModal(true)}>{`Speed up >`}</Button>}
>
Copy link
Member

Choose a reason for hiding this comment

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

The Alert box in Figma looks sligthly different i.e. no border, no title and the action is centered vertically

Screenshot 2024-03-20 at 16 10 21

src/hooks/useGasPrice.ts Outdated Show resolved Hide resolved
src/store/pendingTxsSlice.ts Outdated Show resolved Hide resolved
@schmanu
Copy link
Member Author

schmanu commented Mar 21, 2024

Works really nice already! As discussed with @compojoom we need to find a way to clean up pending transactions if they were sped-up from outside the UI. Our idea is to check the txHistory whenever it updates and compare the newest nonce with the pending tx nonce. If its the same we can remove the pending tx.

I also noticed that the notifications in Figma have a linear progress bar. Did we decide not to implement that?
Screenshot 2024-03-20 at 16 22 01

We decided to not go with sticky notifications yet as we have too many popups / overlays already. Focusing on the new logic by just adding speed up buttons to all components currently showing pending txs.

src/components/transactions/TxSummary/QueueActions.tsx Outdated Show resolved Hide resolved
Comment on lines +53 to +63
switch (status) {
case PendingStatus.PROCESSING:
case PendingStatus.RELAYING:
StatusComponent = <ProcessingStatus txId={txId} pendingTx={pendingTx} />
break
case PendingStatus.INDEXING:
StatusComponent = <IndexingStatus />
break
default:
StatusComponent = <DefaultStatus error={error} />
Copy link
Member

Choose a reason for hiding this comment

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

The StatusMessage component has the same switch cases. Is there a reason we are not using it anymore? All three of these components seem to have the same DOM structure.

Copy link
Collaborator

Choose a reason for hiding this comment

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

the statusMessage component was packing everything in a blue container (the message: "this tx was confirmed and is now ..."), which according to @TanyaEfremova was not correct. I couldn't figure out a way how to refactor it to accomodate this, so I went for writing as is now in the successScreen.
grafik

The StatusMessage component is actually no longer used anywhere. If you have ideas how to make it work with the new requirements let me know, otherwise I would actually remove it.

Copy link
Collaborator

Choose a reason for hiding this comment

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

I see that you use a similar StatusMessage component in safe creation. The main difference is in the steps and a bit in the UI. The problem here is that if we are in the processing state we need the pendingTx to display the speed up. So it is no longer possible to just pass a status and be done with it. If you have some ideas how to abstract this let me know.

Copy link
Member

Choose a reason for hiding this comment

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

We could render the pendingTx part as a child i.e.

<StatusMessage status={status} error={error}>
    {pendingTx && <SpeedUpMonitor txId={txId} pendingTx={pendingTx} modalTrigger={'alertBox'} />}
</StatusMessage>

That way we could reuse all the other elements and their styles.

Copy link
Collaborator

Choose a reason for hiding this comment

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

I thought about this, but then the speedUp is only shown if you we are processing. With this change we are passing it as if it was a generic child, so someone can pass something else and would think that it's a child component that renders below the StatusMessage. The speedup is tightly coupled to the processing state and generalizing the component like this feels awkward. At least to me. I understand the need for a general MessageStatus component, but can't think of a pattern that I like.

Copy link
Member

Choose a reason for hiding this comment

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

How about having it inside StatusMessage and only rendering it if status == PROCESSING then?

src/features/speedup/components/SpeedUpMonitor.tsx Outdated Show resolved Hide resolved
src/services/tx/tx-sender/__tests__/ts-sender.test.ts Outdated Show resolved Hide resolved
src/services/tx/tx-sender/dispatch.ts Outdated Show resolved Hide resolved
src/components/common/Notifications/index.tsx Outdated Show resolved Hide resolved
src/utils/SimpleTxWatcher.ts Outdated Show resolved Hide resolved
Copy link

github-actions bot commented Mar 21, 2024

ESLint Summary View Full Report

Annotations are provided inline on the Files Changed tab. You can also see all annotations that were generated on the annotations page.

Type Occurrences Fixable
Errors 0 0
Warnings 0 0
Ignored 0 N/A
  • Result: ✅ success
  • Annotations: 0 total

Report generated by eslint-plus-action

src/components/transactions/TxSummary/index.tsx Outdated Show resolved Hide resolved
src/features/speedup/components/SpeedUpMonitor.tsx Outdated Show resolved Hide resolved
src/features/speedup/components/SpeedUpMonitor.tsx Outdated Show resolved Hide resolved
src/features/speedup/components/SpeedUpMonitor.tsx Outdated Show resolved Hide resolved
src/features/speedup/components/SpeedUpModal.tsx Outdated Show resolved Hide resolved
Comment on lines +66 to +75
if (results.filter((item) => isTransactionListItem(item)).length === 0) {
results.splice(0, 1)
}
}

if (results[1] && isConflictHeaderListItem(results[1])) {
// Check if we both conflicting txs are still pending
if (results.filter((item) => isTransactionListItem(item)).length <= 1) {
results.splice(1, 1)
}
Copy link
Member

Choose a reason for hiding this comment

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

Not sure I understand these two conditions. If the first element is a label and there is nothing else we remove the label. Why not check for results.length === 1 in that case?

For the second condition I don't see how it is connected to pending transactions. If we filter all of them out anyway does it matter if one or two are pending?

Copy link
Member Author

Choose a reason for hiding this comment

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

You could execute the same tx twice. Once with i.e. metamask and once with e.g. ledger. So there is in theory the possibility to have conflicting pending txs. But if only one of the untrusted queue txs is pending we have to remove the conflicting tx label.

src/store/txHistorySlice.ts Outdated Show resolved Hide resolved
Copy link

ESLint Summary View Full Report

Annotations are provided inline on the Files Changed tab. You can also see all annotations that were generated on the annotations page.

Type Occurrences Fixable
Errors 0 0
Warnings 0 0
Ignored 0 N/A
  • Result: ✅ success
  • Annotations: 0 total

Report generated by eslint-plus-action

@francovenica
Copy link
Contributor

francovenica commented Apr 1, 2024

The execute button looks broken in this PR. It doesn't look like that in current dev:
image

EDIT:
To add another visual issue that is not in dev, so I assume it was caused here.
The amount of signatures is almost overlapping the text "Needs your confirmation"
image

@francovenica
Copy link
Contributor

Question. If the tx is sped up in the wallet itself (like MM extension or MM mobile), should the safe app catch that and show the updated tx hash?
Is not happening, but since is in the test plan in Notion, I wonder if it is even possible to do
image

@compojoom
Copy link
Collaborator

Question. If the tx is sped up in the wallet itself (like MM extension or MM mobile), should the safe app catch that and show the updated tx hash? Is not happening, but since is in the test plan in Notion, I wonder if it is even possible to do image

Unfortunately this is not possible. If the user speeds up in MM we don't know this. We only find out about it later when suddenly a tx is included on the chain with the same nonce.

@francovenica
Copy link
Contributor

An issue I have with MM mobile.

Speeding up the tx in the Safe App creates a 2nd transaction in the MM phone app that is meant to replace the first one. This makes the safe app to get stuck waiting for that sped up transaction
This doesn't happen if you speed it up in the MM phone app. When you speed it up there, there is no "2nd transaction" shown in the list, is just the first one being replaced right away. With this the tx is executed normally.

Steps to make it clearly:
Speeding it up in the MM phone app

  • Create a tx (send funds) with 0.000000001 gas fee
  • Execute in the phone
  • Check the list of tx in the phone app.
  • Tap the 1st tx and check in blockexplorer to see the Tx hash
  • Come back and speed it up with "aggresive" settings (it sets the gas fee as 2 Gwei like we do in our speed up). Save and execute
  • Check the list of tx in the phone app again. Still only 1 tx is at the top as pending
  • Check the tx hash on that transaction. It should be a new hash
  • The tx executes

Speeding it up in the Safe app

  • Create a tx (send funds) with 0.000000001 gas fee
  • Execute in the phone
  • Check the list of tx in the phone app.
  • 1 transaction is at the top being pending
  • Check the safe app and speed up the transaction there
  • Check the list of tx in the phone app.
  • Now 2 transactions are in peding
  • Wait here as long as you want, the transaction will not execute
  • In the phone app, tap the 2nd tx in the list (The one that was created first) and cancel it
  • Now the newest transaction (the one created as you speed it up in the safe app) should execute in a few seconds

image

@francovenica
Copy link
Contributor

francovenica commented Apr 1, 2024

Question: In polygon the speed up option doesn't show up. Waited for like 5 mins. Is the feature not present there? (I've checked the admin and I didn't see a feature toggle for it)
Note: Didn't test in ethereum cuz I don't have much funds, but I ask the same here

@francovenica
Copy link
Contributor

Execution of a batched tx works fine, but looks confusing. The speed up feature show in all of them and if you use one it just dissapears from one of the tx

Idk if there is anythign here to fix without design helping out

Note: This is an edge case since we don't allow gas fee edition in tx in bulk, you have to edit it manually in your wallet. So this is low prio

image

There are less tx in this snapshot because it was a 2nd attempt, but it happened the same for the 3 tx above
image

@compojoom
Copy link
Collaborator

An issue I have with MM mobile.

Speeding up the tx in the Safe App creates a 2nd transaction in the MM phone app that is meant to replace the first one. This makes the safe app to get stuck waiting for that sped up transaction This doesn't happen if you speed it up in the MM phone app. When you speed it up there, there is no "2nd transaction" shown in the list, is just the first one being replaced right away. With this the tx is executed normally.

Steps to make it clearly: Speeding it up in the MM phone app

* Create a tx (send funds) with 0.000000001 gas fee

* Execute in the phone

* Check the list of tx in the phone app.

* Tap the 1st tx and check in blockexplorer to see the Tx hash

* Come back and speed it up with "aggresive" settings (it sets the gas fee as 2 Gwei like we do in our speed up). Save and execute

* Check the list of tx in the phone app again. Still only 1 tx is at the top as pending

* Check the tx hash on that transaction. It should be a new hash

* The tx executes

Speeding it up in the Safe app

* Create a tx (send funds) with 0.000000001 gas fee

* Execute in the phone

* Check the list of tx in the phone app.

* 1 transaction is at the top being pending

* Check the safe app and speed up the transaction there

* Check the list of tx in the phone app.

* Now 2 transactions are in peding

* Wait here as long as you want, the transaction will not execute

* In the phone app, tap the 2nd tx in the list (The one that was created first) and cancel it

* Now the newest transaction (the one created as you speed it up in the safe app) should execute in a few seconds

image

This is a bug in MM Mobile. I've reported it here MetaMask/metamask-mobile#9118
Right now there is nothing in our side we could do to overcome it. Maybe we can follow up the suggestion to offer speed up only on whitelisted wallets.

schmanu and others added 2 commits April 3, 2024 17:09
Co-authored-by: Usame Algan <5880855+usame-algan@users.noreply.github.com>
Co-authored-by: Daniel Dimitrov <daniel.d@safe.global>
Copy link

github-actions bot commented Apr 3, 2024

ESLint Summary View Full Report

Annotations are provided inline on the Files Changed tab. You can also see all annotations that were generated on the annotations page.

Type Occurrences Fixable
Errors 0 0
Warnings 0 0
Ignored 0 N/A
  • Result: ✅ success
  • Annotations: 0 total

Report generated by eslint-plus-action

@compojoom
Copy link
Collaborator

@francovenica I just rebased, please try again once a new version is deployed. With the latest changes that @schmanu did you should be able to speed up txs on polygon as well. The problem there was that we were polling the rpc node for the transaction status, but if the transaction is submitted with a too low gas then no RPC is indexing the TX. Now, we are storing the tx data locally and are able to offer speed up even if the RPC doesn't know the TX.

@francovenica
Copy link
Contributor

francovenica commented Apr 3, 2024

@compojoom @schmanu
Cool. I'll give it a try.
EDIT: It works now. thanks
image

Can we fix the visual issues like this one? so we can create the RC
To see this one create 2 tx with the same nonce and queue them
image

@francovenica
Copy link
Contributor

francovenica commented Apr 4, 2024

Now that Poly works I decided to try a few phone apps
Zerion:
It completely ignores our suggestion from safe. So if the tx is slow, even the speedup we send is going to have the fee ignored. Is up to the user to change the fee manually in his phone

1inch:
If you lower the suggested fee we send it by just 20% the app would show an error, it won't even allow changing the fee we suggest.
You have to send a tx with a proper fee. The one we estimate from the get go in the tx form works fine
image

Rainbow:
It also ignores our suggestion. the dapp doesn't even allow custom gas fee changes, it gives you 3 speeds and that's it. So our speed up feature cannot be used here
image

Trust:
This receives our suggestion, and you can edit them in the phone app as well, but if you set something too low it won't even let you try to execute the tx.
image

Also this trust app has issues.
First it already tells you the tx will fail in the form:
image

The tx doesn't go through in our app and a ton of errors show up in the console, but in the blockexplorer you can see the tx actually executed just fine
https://polygonscan.com/tx/0x8c4908720dd7063fb6d1dae6c2f5803f49fc89414197b53c5c380570e1545759
image

Conclussion:
It seems that beyond MM that kinda allows anything for the gas fee, this dapps seems to have safety features to assure users don't get stuck by setting the gas too low, so probably we won't have to worry about Mobile phone apps connected through WC

@compojoom
Copy link
Collaborator

Btw, just tested with Rabby and it has the same issue as MM Mobile. It ignores the nonce we provide and instead sets one higher. This leads to a stuck tx.
grafik

The user would have to speed up the first tx and then the second will execute.

@@ -0,0 +1,19 @@
import { useEffect, useState } from 'react'

export const useCounter = (startTimestamp: number | undefined) => {
Copy link
Member

Choose a reason for hiding this comment

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

Can't we use the existing useIntervalCounter?

Comment on lines +120 to +144
? {
chainId,
safeAddress,
txId,
status: PendingStatus.PROCESSING,
txHash: detail.txHash,
signerAddress: detail.signerAddress,
signerNonce: detail.signerNonce,
submittedAt: Date.now(),
txType: PendingTxType.CUSTOM_TX,
data: detail.data,
to: detail.to,
}
: {
chainId,
safeAddress,
txId,
status: PendingStatus.PROCESSING,
txHash: detail.txHash,
signerAddress: detail.signerAddress,
signerNonce: detail.signerNonce,
submittedAt: Date.now(),
gasLimit: detail.gasLimit,
txType: PendingTxType.SAFE_TX,
}
Copy link
Member

Choose a reason for hiding this comment

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

Is it possible to reduce the code duplication here?

Comment on lines +135 to +220
export const dispatchSafeTxSpeedUp = async (
txOptions: Omit<TransactionOptions, 'nonce'> & { nonce: number },
txId: string,
onboard: OnboardAPI,
chainId: SafeInfo['chainId'],
safeAddress: string,
) => {
const sdkUnchecked = await getUncheckedSafeSDK(onboard, chainId)
const eventParams = { txId }
const wallet = await assertWalletChain(onboard, chainId)
const signerNonce = txOptions.nonce

// Execute the tx
let result: TransactionResult | undefined
try {
const safeTx = await createExistingTx(chainId, safeAddress, txId)
result = await sdkUnchecked.executeTransaction(safeTx, txOptions)
txDispatch(TxEvent.EXECUTING, eventParams)
} catch (error) {
txDispatch(TxEvent.SPEEDUP_FAILED, { ...eventParams, error: asError(error) })
throw error
}

txDispatch(TxEvent.PROCESSING, {
...eventParams,
txHash: result.hash,
signerAddress: wallet.address,
signerNonce,
gasLimit: txOptions.gasLimit,
txType: 'SafeTx',
})

const provider = getWeb3ReadOnly()

if (provider) {
// don't await as we don't want to block
waitForTx(provider, [txId], result.hash, safeAddress, wallet.address, signerNonce)
}

return result.hash
}

export const dispatchCustomTxSpeedUp = async (
txOptions: Omit<TransactionOptions, 'nonce'> & { nonce: number },
txId: string,
to: string,
data: string,
onboard: OnboardAPI,
chainId: SafeInfo['chainId'],
safeAddress: string,
) => {
const eventParams = { txId }
const wallet = await assertWalletChain(onboard, chainId)
const signerNonce = txOptions.nonce
const web3Provider = createWeb3(wallet.provider)
const signer = await web3Provider.getSigner()

// Execute the tx
let result: TransactionResponse | undefined
try {
result = await signer.sendTransaction({ to, data, ...txOptions })
txDispatch(TxEvent.EXECUTING, eventParams)
} catch (error) {
txDispatch(TxEvent.SPEEDUP_FAILED, { ...eventParams, error: asError(error) })
throw error
}

txDispatch(TxEvent.PROCESSING, {
txHash: result.hash,
signerAddress: wallet.address,
signerNonce,
data,
to,
groupKey: result?.hash,
txType: 'Custom',
})

const provider = getWeb3ReadOnly()

if (provider) {
// don't await as we don't want to block
waitForTx(provider, [txId], result.hash, safeAddress, wallet.address, signerNonce)
}

return result.hash
}
Copy link
Member

Choose a reason for hiding this comment

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

Again, these are extremely similar, possible to exract the common part?

There are a lot of wallets out there that ignore the specified nonce. If we offer the option to speed up when the tx is not signed we can end up with multiple transactions in the wallet. The moment the user manages to speed the one tx that is stuck all subsequent txs will be executed and this could lead to potential loss of funds(funds sent multiple times). Because of this we no longer display the speed up option, but rather ask the user to manually speed up through the wallet.
@francovenica
Copy link
Contributor

francovenica commented Apr 8, 2024

The ticket is not in QA, but still I've checked the fix regarding the buttons positions and looks good.

I don't agree with the last commit. I think a big point of this feature is that wallets that do not have the speed up option like physical devices (trezor/ledger) have now the chance of speeding it up.
I understand the concern that causes being able to speed up a tx that might get replaced by another, but at least on the safe side we don't allow a new tx to be executed while another one is in the process of being executed, so the only scenario where I think it could happen what is being mentioned in the commit comment is if the user uses his wallet in another app that is not the safe.

@katspaugh
Copy link
Member

@francovenica speeding up is not disabled for hw wallets. It's only disabled for immediately executed tx (unsigned txs) with all wallets.

@katspaugh katspaugh merged commit 868e397 into dev Apr 8, 2024
14 checks passed
@katspaugh katspaugh deleted the feat/pending-txs branch April 8, 2024 08:17
@github-actions github-actions bot locked and limited conversation to collaborators Apr 8, 2024
@francovenica
Copy link
Contributor

@katspaugh I'm aware of that. but most people in safes 1/1 dont' sign, queue the tx and then execute, they execute right away, making these particular trezor/ledger users prone to see a message saying "go and speed it up in your wallet" whne they cannot do that. I still think the risk we are trying to avoid are not worth the disconfort of these users.

@katspaugh
Copy link
Member

I see, thanks for clarifying. That's a fair point. However, consider the following:

  • This feature wasn't there before, so we're not making existing UX worse.
  • Ledger is 1.2% of our users, Trezor is 0.36%
  • The risk when speeding up an unsigned tx is that you can submit the same tx twice (due to the nonce not being validated for immediate executions on the contract) – so you can potentially send your money twice if we don't disable this – IMHO it's definitely worth it to avoid this risk.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Speed-up pending transaction
5 participants