Implement majority-wins transaction voting strategy
We currently have two ways we set up transactions in the coordinator:
- With the primary-wins feature flag, the primary will always
succeed no matter what the secondaries vote.
- Without the flag, all nodes need to agree.
The first strategy really is only to ensure smoother transitioning towards using reference transactions and is going away at some point in time. The second voting strategy is the one that's going to stay, but right now it's really pessimistic because it will always require all nodes to agree on the same thing.
Let's refine this strategy and move it to the next level, which is a quorum-based approach: instead of requiring all nodes to agree, we will now require a majority of nodes to agree. In this case, we define majority to:
- Always include the primary node. This is a hard requirement, as
the primary node is the one who's executing hooks. If it failed
and the transaction succeeded, we'd have changes persisted to disk
but none of the hooks were run, which may lead to inconsistent
state.
- Require at least half of the secondaries to agree, rounded up. As
a special case, if there's only a single secondary, then it's not
required to agree with the primary.
This would result in the following typical scenarios:
- 1 primary, 0 secondaries: Primary always wins.
- 1 primary, 1 secondary: Primary always wins.
- 1 primary, 2 secondaries: Primary and a single secondary required.
- 1 primary, 3 secondaries: Primary and two secondaries required.
- 1 primary, 4 secondaries: Primary and two secondaries required.
This commit implements the above by changing the default transaction setup in case the primary-wins feature flag is disabled and adds/adjusts some of our tests to match this new strategy.