Repository navigation
perf(users): avoid full-table sorts in list queries - #774
Conversation
|
@coderabbitai review |
|
Important Review skippedAuto reviews are disabled on base/target branches other than the default branch. Please check the settings in the CodeRabbit UI or the ⚙️ Run configuration
You can disable this status message by setting the Use the checkbox below for a quick retry:
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info
WalkthroughUser listing now uses deterministic sorting and narrow filtered count queries. The database schema adds a ChangesUser list query scaling
Estimated code review effort: 3 (Moderate) | ~20 minutes Suggested reviewers: Merge Risk: ⚪ Minimal · up to This change optimizes user-list counting and pagination while preserving the API contract; no actionable merge-blocking risk remains beyond normal checks and review. 🚥 Pre-merge checks | ✅ 5
✨ Finishing Touches
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. A rabbit sorted users in line, Comment |
✅ Action performedReview finished.
|
fd99ff4 to
181187c
Compare
…rrent head The migration branched off an older revision, and a merge migration joined it to dev's head (b4c7e8f1a2d3). That works alone, but once another migration PR lands the same way, dev has two Alembic heads and `alembic upgrade head` fails with "Multiple head revisions". Point the migration at dev's head and drop the merge migration. Also drop an extra blank line after the imports that ruff flags (I001).
Resolve app/db/crud/user.py after the HWID count change: keep this PR's _build_user_sort_clauses, which already routes every option through _build_user_sort_clause (including the hwid_count subquery) and adds an id tie-break for every sort, and its _build_user_count_stmt.
…the user list sort index The previous migration PR in the series (PasarGuard#774) has landed, so point this migration at its revision (b7e2c4d91f60) to keep a single Alembic head.
* perf(statistics): reduce historical query load * test: remove added PR tests * docs: remove statistics performance notes * fix(migrations): chain statistics index after latest dev migration * fix(migrations): chain the subscription update index migration onto the current head The migration branched off an older revision, and a merge migration joined it to dev's head (b4c7e8f1a2d3). That works alone, but once another migration PR lands the same way, dev has two Alembic heads and `alembic upgrade head` fails with "Multiple head revisions". Point the migration at dev's head and drop the merge migration. Also drop an extra blank line after the imports that ruff flags (I001). * fix(migrations): chain the subscription update index migration after the user list sort index The previous migration PR in the series (#774) has landed, so point this migration at its revision (b7e2c4d91f60) to keep a single Alembic head. --------- Co-authored-by: T3ST3ST3R0N <T3ST3ST3R0N@gmail.com>
… node and core sort order The other migration PRs in the series (PasarGuard#774, PasarGuard#865, PasarGuard#875) have landed, so point this migration at the latest revision (d73f8a2c4e91) to keep a single Alembic head.
* perf(groups): scale membership summaries * test: remove added PR tests * test: remove PR-specific changes to existing tests * fix(migrations): chain the group membership index migration onto the current head The migration branched off an older revision, and a merge migration joined it to dev's head (b4c7e8f1a2d3). That works alone, but once another migration PR lands the same way, dev has two Alembic heads and `alembic upgrade head` fails with "Multiple head revisions". Point the migration at dev's head and drop the merge migration. Also drop an extra blank line after the imports that ruff flags (I001). * refactor(groups): keep only the reverse membership indexes The member count rewrite overlaps #967, which counts members in SQL in load_group_attrs without loading them and keeps a fallback when the count was not loaded. Leave Group.total_users and get_group as on dev so this PR adds only the reverse membership indexes, which those group-centric counts and bulk membership deletes use. * fix(migrations): chain the group membership index migration after the node and core sort order The other migration PRs in the series (#774, #865, #875) have landed, so point this migration at the latest revision (d73f8a2c4e91) to keep a single Alembic head. --------- Co-authored-by: T3ST3ST3R0N <T3ST3ST3R0N@gmail.com>
Summary
/api/userstotal-count queryidtie-breaker for deterministic offset pagination(created_at, id)for the dashboard's default user-list orderCloses #773
Type of change
Checklist
Testing
uv run ruff check .— passeduv run pytest -q tests/test_user_list_query_scaling.py— 4 passeduv run pytest -q tests/api/test_user.py— 82 passeduv run alembic checkon SQLite — no new upgrade operationsCREATE INDEX CONCURRENTLY/DROP INDEX CONCURRENTLYSynthetic SQLite benchmark with 500,000 users and a 50-row page:
Before the change both plans used a full scan and temporary B-tree sort. The optimized page uses
idx_users_created_at_id; the count no longer sorts. The benchmark is directional, not a production guarantee.Screenshots
Not applicable (backend/database-only change).
Notes for reviewers
autocommit_block().devmigration head. If one lands first, the other migration should be rebased onto the new head before merge to avoid parallel Alembic heads.Summary by CodeRabbit
Performance
Bug Fixes