2

I'm using MetaMask to make Ethereum transactions from my website, as described here: https://metamask.github.io/metamask-docs/Main_Concepts/Sending_Transactions

It works perfectly. I capture the transaction hash in the callback, then use it to track the transaction.

But I just noticed something; metamask has the option to "speed up" the transaction. I'm not sure exactly how it works, but this basically creates a new transaction with a larger gas price. However the callback is not called again.

I'm not sure exactly what it is doing. When I searched for the original transaction hash on an explorer, it doesn't exist. So they canceled it somehow?

I guess my problem is; how does my website know the original txhash is dead and receive the new txhash? How do people deal with this?

I also considered tracking the user transactions from the blockchain side, using subscribe to "Pending Transactions" function in web3, however this call cannot be filtered and so I get ALL pending transactions, not just transactions to my smart contract. This might be ok if I was running my own node, but I am using Infura. I would need to call Infura to get details on every pending transaction, probably they would ban me if I did that.

Does anyone have any insights?

5
  • Is it a contract execution or a transfer of ethers? Why do you need to keep track of transactions hashes? For contracts it is better to listen for events.
    – Ismael
    Sep 28, 2019 at 17:53
  • Contract. Events are only fired when transactions are mined. I wanted to keep a track of the transaction while it is pending. Sep 29, 2019 at 18:04
  • Why do you need to keep track of the pending transaction? A hash doesn't have any meaning and it can be replaced even after they were mined.
    – Ismael
    Sep 30, 2019 at 3:09
  • The txhash does have meaning as it identifies the transaction. The txhash can be used to identify and retrieve the transaction details after it has been mined using services such as Infura. I don't understand what you mean when you say "a hash can be replaced after it has been mined" this is not true. the txhash is literally the hash of the transaction, it does not change. Sep 30, 2019 at 9:27
  • In case of a chain reorg it is possible for a mined transaction to be replaced for a new one, so for some uses it is better to wait for confirmation a few blocks before trusting a transaction.
    – Ismael
    Sep 30, 2019 at 12:58

2 Answers 2

3

To "speed up a transaction" there's only one possible option: to send a new transaction with higher gas price but with the same nonce. This way if nodes see both of the transactions they will most likely pick up the one with the higher gas price and once that is mined the other transaction becomes invalid (a tx with that nonce has already been mined) and is ignored & dropped.

Why you can't see the transaction hash of the second transaction is beyond me. It's a new transaction and should have a new transaction hash.

Some further reading on the topic: https://kb.myetherwallet.com/en/transactions/checking-or-replacing-a-tx-after-sending/

2
  • I can see the second transaction on the network, and it is mined perfectly. However the javascript callback is not executed a second time with that second txhash -- are you saying that it should? Sep 27, 2019 at 18:40
  • 1
    sorry, I have no idea how that is supposed to work. Maybe such transactions are supposed to work with some other logic - that's up to MetaMask Sep 27, 2019 at 18:46
0

Answering to @Peter Prographo, yes every dApp should have a support for when a user speeds up a tx in clients such as MetaMask.

Right now what is happening when a user speeds up a tx is that MetaMask will create a new tx. If the new tx with higher gas gets mined first, the old tx returns no receipt object. And the front-end is listening for that specific receipt object. Which never is returned so front-end doesn't know that a new tx has been already processed.

The problem seems to touch all WEB3 API clients, such as web3.js, ethers.js etc. This issue has not been yet solved but there is a EIP for it. here : https://eips.ethereum.org/EIPS/eip-2831

So far the only solution that I found is to use ethers.js that since 05.2021 supports these cases in "some" cases.

Here is an update regarding the update from ethers.js

https://blog.ricmoo.com/highlights-ethers-js-may-2021-2826e858277d

Go to the article and scroll down to "Detecting Replacement Transactions". There you have example code.

Here extra link to ethers.js github thread https://github.com/ethers-io/ethers.js/issues/1477

I have been trying to implement this functionality into my front-end but the problem is that it doesn't really work on BSC or POLYGON when you on purpose slow down a transaction to then replace it. Since that is the only way you have the time to create a replacement transaction. Otherwise miners pick the tx almost immediately.

If somebody found a way to test it for all EVM chains, please share.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.