Ban-pick: one-time pool veto for low-rated players (port of Botlatro's tuple veto)
Nobody has claimed this yet.
Assessment
- Difficulty
- 5/5
- Estimated time
- Over a week
- Newbie friendliness
- 35/100
Research direction
Start with the gamemode/queue config, matchmaking_ratings.rating, and the match/draft payload. Trace the API engine's build_pool flow, host state and Confirm/Random button configuration, then inspect decorate_tile in the Speedrun mod. Done means server-computed can_veto, server-side one-time consumption and broadcast, a correctly gated UI button, and mercy-aware pool generation.
Written by the indexing model from the issue text.
Description
What
Port Botlatro-Multiplayer's match veto into the in-game ban-pick draft: a
one-time-per-match button letting a low-rated player reroll the candidate pool,
with a difficulty-mercy bias.
Reference semantics (Botlatro-Multiplayer, verified in source)
- Tuple-ban queues generate 9 weighted (deck, stake) tuples; teams ban from the list.
- Veto (
veto-tuples-handler): only match participants with
elo <= queues.veto_mmr_threshold(fallback 200) may press it. Effect: full
tuple-list regeneration with a mercy rule --TupleBans.veto()forces white-stake
generation when the list holds fewer than 4 white-stake options
(vetoWhiteAmount = 4). One veto per match, shared (tupleVetoUsedkeyed by
match id): if both players are eligible, first press consumes it. No vote --
unilateral, by design (it is a low-rated-player protection). - Contrast: Reroll Options is the consensual sibling -- any participant may
trigger it but it runs a vote of all match players, also once per match. - Rank names (STONE etc.) are Discord roles (
queue_roles.mmr_threshold) and are
display-only; the veto gate is an independent raw threshold. The bot does not
tie veto to rank either -- the numbers are just aligned by convention.
Two bot bugs the port should NOT copy
- Button visibility checks the WHOLE QUEUE, not the match:
SELECT elo FROM queue_users WHERE queue_id = $1+.some(...)
(matchHelpers.ts) -- the VETO button renders whenever anyone in the queue is
under threshold, and the real gate only happens at press time. - Open TODO: the veto button disappears permanently after a reroll.
Design: server-computed eligibility (client never knows the rule)
The server computes can_veto per player per match and includes it in the
match/draft payload. The client renders the button only when true; the host/server
still validates the veto action itself (client-side gating alone is spoofable).
This keeps the eligibility RULE server-side and swappable: start with bot parity
(rating <= threshold in gamemode/queue config, using matchmaking_ratings.rating),
and later move to named tiers if/when the server grows a tier concept -- today the
schema has only integer ratings and leaderboard positions, no named ranks -- all
without touching the mod or API.
Depends on
#13 (weighted tuple pool policy) -- the mercy rule only has meaning against a weighted tuple pool. Eligibility and pool policy are both per modId + gameMode, so PvP and Speedrun configure independently.
Work items
- Server: veto threshold in gamemode/queue config; compute per-player
can_vetointo the match payload; validate + consume the veto action
(once per match) server-side. - API engine:
vetoaction -- host regenerates the pool (consumer
build_poolre-run with a mercy flag), resets the ban schedule, broadcasts;
once-per-draft guard mirrored in host state. - API UI: Veto button in the ban-pick button row (definition-time
button
config + per-frame check, same pattern as Confirm/Random); rendered only when
the payload sayscan_veto; removed once consumed. - Speedrun mod: pool builder honours the mercy rule (the white-stake-bias
equivalent for its pools; engine already supports{key, stake}tuple items +
decorate_tile).
Open questions
- Threshold value per gamemode (bot default is 200; new-server ratings default 600
-- numbers need re-basing). - Veto on plain deck drafts too, or only tuple (deck+stake) pools?
- Repool semantics: bot restarts the tuple ban list -- mirror that (full draft
restart) or preserve prior bans?
- Dominant language
- Lua
- Stars
- 7
- Forks
- 3
- PR merge metrics
- No merged PRs in 30d
Contributor guide
No contributing guide indexed for this repository
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
More from Balatro-Multiplayer/BalatroMultiplayerAPI
-
Difficulty 5/5 Over a week Newbie friendliness 35/100
-
Difficulty 3/5 1-2 days Newbie friendliness 62/100
All issues in Balatro-Multiplayer/BalatroMultiplayerAPI
Similar issues
-
Difficulty 1/5 Under an hour Newbie friendliness 88/100
-
[BUG] [25.12.5] Open
Difficulty 2/5 1-3 hours Newbie friendliness 72/100
-
Difficulty 2/5 1-3 hours Newbie friendliness 76/100
pterodactyl/game-eggs#637 ·
-
Difficulty 2/5 1-3 hours Newbie friendliness 84/100
-
Difficulty 2/5 1-3 hours Newbie friendliness 70/100
openSUSE/python-rpm-macros#219 ·