ServicesWaiting Room

Bans and Anti-Gaming

Two layers keep a queue fair: per-room anti-gaming rules that throttle join abuse, and a ban registry that keeps specific members out.

Rejoin cooldown

A cooldown stops leave-and-rejoin cycling for a better position. Set it at room creation (or later via update); 0 disables it:

snug waiting-room create -r launch-day -c 100 --anti-gaming-rejoin-cooldown 60

Verified: join, leave, then an immediate rejoin fails until the cooldown elapses:

{
  "status": 429,
  "msg": "Please wait 60 seconds before rejoining",
  "error": "RATE_LIMITED"
}

Join rate limit

Caps join attempts per member within a sliding window:

snug waiting-room create -r launch-day -c 100 \
  --anti-gaming-rate-limit-max 2 --anti-gaming-rate-limit-window 60

Verified: with a max of 2 per 60 seconds, the third join attempt inside the window fails with 429 RATE_LIMITED - Too many join attempts. Try again in 60 seconds. Both knobs take 0 to disable.

The service also watches request patterns - rapid join/leave cycling and suspiciously regular request timing - and can auto-ban members it flags; the thresholds are internal and not per-room configurable.

Rejecting with a ban

reject removes members from the queue; adding -b <seconds> also bans them from rejoining:

snug waiting-room reject -r launch-day -m user-3 -R "abuse" -b 3600

Verified: the rejected member's next join attempt fails with 403 FORBIDDEN - Banned until 2026-08-28T15:16:02+00:00.

The ban registry (admin)

Explicit bans are managed separately from rejection. All ban commands require a platform admin token, except member-bans, which a member may also call for themselves.

snug waiting-room ban -r launch-day -m user-4 -R "bot" -d 86400  # omit -d for permanent
snug waiting-room bans -r launch-day --include-expired
snug waiting-room ban-details -r launch-day -m user-4
snug waiting-room unban -r launch-day -m user-4
snug waiting-room member-bans -m user-4     # room IDs this member is banned from

An explicit ban records the full audit trail; captured live:

{
  "room_id": "launch-day",
  "member_id": "user-4",
  "reason": "bot",
  "banned_by": "docs-wave-admin",
  "banned_at": "2026-08-28T14:16:12.838659Z",
  "banned_until": "2026-08-28T16:16:12.838659Z"
}

Two verified gotchas:

  • A ban created via reject -b blocks joins and appears in the room's bans list (member ID and expiry only), but it has no registry record: ban-details on it comes back empty. Use ban when you need an auditable reason and actor.
  • Bans are per-room. member-bans aggregates the rooms a member is banned from; there is no global ban.

Expired bans stop blocking joins immediately and are swept from the registry in the background (hourly by default; see the CONFIG reference). The exact endpoints are in the Waiting Room API reference.

On this page