Skip to content

Cache leaderboard results and clamp the maximum limit in LeaderboardService #1159

Description

@RUKAYAT-CODER

Overview

LeaderboardService.getTopPlayers() and getTopBadgeHolders() in src/gamification/leaderboards/leaderboards.service.ts run an ORDER BY ... DESC aggregate over the full user-progress/badge tables on every request, and getTopPlayers(limit) passes the caller-supplied limit straight into take() with no upper bound. Leaderboards are read-heavy and change slowly, so recomputing the sort per request is wasteful, and an unbounded limit (e.g. ?limit=1000000) lets a caller force a full-table sort and large response — a cheap DoS.

Specifications

Tasks:

  • Cache the top-N leaderboard in Redis with a short TTL and serve reads from cache; invalidate or let it expire on point/badge changes.
  • Clamp limit to a documented maximum (e.g. 100) and reject or coerce larger values.
  • Ensure the ordering column is index-backed (coordinate with the gamification index work).
  • Add tests for the max-limit clamp and for cache hit/miss behaviour.

Impacted Files:

  • src/gamification/leaderboards/leaderboards.service.ts

Acceptance Criteria

  • Repeated leaderboard reads inside the TTL do not re-run the sort query.
  • A caller cannot request more than the maximum number of rows.
  • Tests cover the clamp and caching.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions