Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Consider this scenario: - `retries_remaining` starts at 1, so we have 1 main execution and 1 additional speculative execution to spawn. - Main execution does some retries and exhausts execution plan this way. - It sends the last attempt to DB and waits for response. - Now the speculative execution starts. - The plan is empty, so it immediately finishes and enters `None` block of the `match`. - `async_tasks` is not empty, because main execution is still ongoing, so nothing happens. - Main execution finishes with ignorable error, e.g. broken connection. - `can_be_ignored` returns true, so we don't return and only assign to `last_error` - Now `async_tasks` is empty, so `async_tasks.select_next_some()` branch of `select!` will never be executed again. - Only `&mut sleep` will be executed (once) and do nothing because `retries_remaining == 0`. - That means we are hanging forever - or until client timeout happens if one was configured. This commit fixes this bug by simplifying the logic. The new logic always checks if the resolved task is the last one, and if so it returns, so it's not possible for the tasks to be exhausted without finishing the `select!`.
- Loading branch information