Repository navigation
perf(bulk): batch user reloads and aggregate reset usage - #854
Conversation
|
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 configurationConfiguration used: Organization UI Review profile: CHILL Plan: Team Run ID: 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⚙️ Run configurationConfiguration used: Organization UI Review profile: CHILL Plan: Team Run ID: 📒 Files selected for processing (3)
Included review availability: Your plan provides up to 8 included reviews per hour; 5 remain after this review. WalkthroughBulk CRUD operations now capture affected user IDs and reload users through a shared batched query. New tests cover response data, relationship refreshes, query counts, state changes, and empty scopes. A benchmark compares the current implementation with a baseline. ChangesBulk user reload optimization
Estimated code review effort: 3 (Moderate) | ~25 minutes Merge Risk: ⚪ Minimal · up to Bulk user operations now reload affected users in batches and calculate lifetime usage without materializing reset-history rows. The covered behavior preserves returned data and state transitions, with no current merge-blocking risk identified. Poem
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
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. Comment |
|
@coderabbitai review |
✅ Action performedReview finished.
|
Summary
Bulk expiry, data-limit and group changes loaded admin/role, next plan, reset history and groups separately for each returned user. Bulk proxy updates already batched those relationships, but still materialized every reset-history row. For 100 affected users with 1,000 reset records each, this loaded 100,000 history objects after a single bulk operation.
Reuse the existing user-select builder to join scalar relationships, batch-load admin roles/groups and calculate lifetime usage with an indexed SQL aggregate. Apply the same reload to all five bulk operations. Group removal and proxy updates capture IDs before mutation rather than loading full user objects twice.
The reload uses
populate_existing=True, which also fixes stale group collections: withexpire_on_commit=False, a user whose groups were already loaded could retain the old membership after a bulk add/remove. The returned object now reflects the committed membership.Before / after
Local benchmark: 100 users, 1,000 reset records per user, one shared admin/role and one group. Complete CRUD call, including target selection, mutation, commit and reload:
Reset-history ORM objects: 100,000 → 0 in every case. The benchmark asserts equal affected counts and complete serialized
UserResponsevalues for both implementations, including lifetime usage, updated fields and group membership.Method: Python 3.14.6 on Windows, SQLite in memory, baseline
234ab68c. One warmup per version, five timing samples per version with alternating execution order, fresh sessions and equivalent fixture state for each sample. SQL/object counts andtracemallocpeaks are measured in separate untimed runs. Fixture setup/reset, response validation and node dispatch are excluded. Peak allocations are not process RSS or database memory. These are local CRUD measurements, not production PostgreSQL/MySQL or end-to-end API latency claims.Reproduce from the repository root:
The script uses its own in-memory database. A separate
--users 2 --logs 0 --runs 1smoke run also verified equal responses with no history.Type of change
Testing
46 passed, including 20 new regression cases and existing node-sync, WireGuard and admin tests:
The database override isolates the existing admin test suite from a local
test.dbreferencing a migration absent from this branch. The new bulk tests always create their own in-memory database.Regression coverage includes all five operations, full response validation, absence of history-object loads, positive/negative adjustments, unchanged and empty scopes, cached membership refresh, and query growth across SQLAlchemy's 500-parent select-in batch boundary. Before the fix, the initial regressions reproduced history loads, stale memberships, and 192 SQL statements for 62 returned users; the latter now uses 6.
ruff check --no-fix,ruff format --checkon all three changed files, andgit diff --checkpassed.Checklist
Screenshots
Not applicable; no UI changes.
Notes for reviewers
dev. Onlyapp/db/crud/bulk.pychanges application behavior.usage_logsaccess is no longer eagerly supported by these bulk results; current callers only use them for allocation/node sync. Lifetime values remain available through the aggregate.Summary by CodeRabbit