Skip to content
This repository was archived by the owner on Nov 15, 2023. It is now read-only.
This repository was archived by the owner on Nov 15, 2023. It is now read-only.

Some invalid transactions removed from the pool should be revalidated #5139

@tomusdrw

Description

@tomusdrw

During block authorship we attempt to detect invalid transactions that are still in the pool.
Since pool is being cleaned asynchronously, it is a completely legal and valid situation - in the front of the ready queue we have transactions that just got included to recently imported/authored block.
However the transactions that are detected invalid are removed from the pool via remove_invalid call.
That in turn causes the entire subtree of transactions to be removed (i.e. all transactions that depend on the invalid ones), as we assume that since their predecessor is invalid they are going to be invalid too.

As an example, let's imagine we have a following set of transactions in the pool (coming from the same sender):

tx(nonce=1)
tx(2)
tx(3)
tx(4)
  1. now, we import a block that contains tx(1), but don't clear the pool.
  2. If we attempt to produce another block, tx(1) will cause InvalidTransaction::Stale error to be returned, hence we will mark it as invalid.
  3. Next we will try to execute tx(2), but it will obviously succeed.
  4. Then imagine that tx(3) does not fit to the block - we finish up block authoring and should resume the next block starting off with including tx(3).
  5. However remove_invalid(tx(1)) will cause the entire subtree originating in tx(1) to be removed from the pool, so tx(3) and tx(4) will no longer be there.

Solution

There are two ways to solve that issue:

  1. Either attempt to resubmit transactions that were not directly invalid, but just transitevly (tx(2),tx(3),tx(4) in the example)
  2. Or remove only invalid transactions reported directly, not their subtrees - this may leave some more invalid transactions in the pool, but they should just be detected on next attempts.

I'd vote for option (2), cause it's more suited for frame-based runtimes, since most likely the transactions left in the pool are still valid. We can possibly implement both solutions and have that configurable as well.

Metadata

Metadata

Assignees

Labels

I3-bugThe node fails to follow expected behavior.U2-some_time_soonIssue is worth doing soon.

Type

No type

Projects

No projects

Relationships

None yet

Development

No branches or pull requests

Issue actions