Skip to content

fix(user-usage): keep manual resets out of reset cycles#458

Open
Rerowros wants to merge 4 commits into
PasarGuard:devfrom
Rerowros:fix/user-usage-reset-cycle
Open

fix(user-usage): keep manual resets out of reset cycles#458
Rerowros wants to merge 4 commits into
PasarGuard:devfrom
Rerowros:fix/user-usage-reset-cycle

Conversation

@Rerowros
Copy link
Copy Markdown
Contributor

@Rerowros Rerowros commented May 10, 2026

Summary

This pull request fixes how traffic reset cycles are calculated when a user is reset manually from the panel or API.

Previously, all reset events were stored as the same kind of usage reset log. The panel then used the latest reset log as the anchor for the next periodic reset. Because of that, a manual reset could accidentally move a user's monthly, weekly, daily, or yearly reset date forward.

That behavior makes manual paid resets less useful: if a user pays only to clear current traffic usage, the regular plan reset should not be postponed.

Traffic Reset Cycle Logic

  • Added explicit reset source tracking for user usage reset logs in app/db/models.py, distinguishing manual, scheduled, and next_plan reset events.
  • Added a database migration for user_usage_logs.reset_source in app/db/migrations/versions/b8e4e47b9f2c_add_user_usage_reset_source.py. Existing reset logs are marked as scheduled so current users keep their existing reset-cycle anchors after upgrade.
  • Updated periodic reset selection in app/db/crud/user.py so only scheduled and next_plan reset logs are used to calculate whether a user is due for the next automatic reset.
  • Updated the scheduled reset job in app/jobs/reset_user_data_usage.py to write reset logs with reset_source=scheduled.
  • Updated next-plan activation in app/db/crud/user.py to write reset logs with reset_source=next_plan, because applying a next plan should start a new usage cycle.

Manual and API Reset Behavior

  • Kept manual user resets as reset_source=manual in app/db/crud/user.py, so panel/API resets clear current usage without changing the user's plan reset cycle.
  • Updated bulk user reset handling in app/db/crud/user.py so bulk manual resets use the same source-aware logic.
  • Updated global reset-all handling in app/db/crud/bulk.py to log manual reset events instead of deleting reset history. This preserves lifetime traffic accounting while still preventing manual resets from moving scheduled reset dates.

Reset Date Visibility

  • Added last_traffic_reset_at and next_traffic_reset_at to user response models in app/models/user.py.
  • Populated reset date fields for subscription users in app/operation/subscription.py.
  • Displayed the next traffic reset date on the subscription HTML page in app/templates/subscription/index.html.
  • Added reset date fields to dashboard API types in dashboard/src/service/api/index.ts.
  • Displayed last and next traffic reset dates in the dashboard user modal in dashboard/src/components/dialogs/user-modal.tsx.

Dashboard Date Handling

  • Updated user expiration sorting to use the shared date parser instead of native date coercion in dashboard/src/components/users/columns.tsx.
  • Updated status badge expiry parsing to use the shared date parser in dashboard/src/components/users/status-badge.tsx.
  • Updated cleanup date filters to send full-day ranges instead of raw picker timestamps in dashboard/src/pages/_dashboard.settings.cleanup.tsx.

Test Coverage

  • Added a regression test in tests/api/test_user_usage_reset_cycle.py proving that a manual reset does not delay the next periodic reset.
  • Extended subscription tests in tests/api/test_user.py to verify reset dates are exposed through subscription info and rendered on the subscription HTML page.
  • Updated API test setup in tests/api/conftest.py so JWT secret lookups use the test database consistently.

Why This Is Better

The new model separates business intent instead of inferring it from a timestamp.

A scheduled reset means the user's plan cycle advanced. A next-plan reset means the user's next plan was activated and should also become the new cycle anchor. A manual reset means an admin or API caller cleared current usage immediately, but did not change the user's regular reset schedule.

This makes the behavior more predictable for operators and fairer for users who buy or receive an extra traffic reset. Manual reset becomes an additive action instead of something that can silently postpone the normal plan reset.

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 10, 2026

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 75db6631-1f1d-4ebb-af41-d299be6f5ae7

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Tip

💬 Introducing Slack Agent: The best way for teams to turn conversations into code.

Slack Agent is built on CodeRabbit's deep understanding of your code, so your team can collaborate across the entire SDLC without losing context.

  • Generate code and open pull requests
  • Plan features and break down work
  • Investigate incidents and troubleshoot customer tickets together
  • Automate recurring tasks and respond to alerts with triggers
  • Summarize progress and report instantly

Built for teams:

  • Shared memory across your entire org—no repeating context
  • Per-thread sandboxes to safely plan and execute work
  • Governance built-in—scoped access, auditability, and budget controls

One agent for your entire SDLC. Right inside Slack.

👉 Get started


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.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@M03ED
Copy link
Copy Markdown
Contributor

M03ED commented May 10, 2026

thanks for pr, there are some points i should write here
first of all why these 3 pr are related ? they have completely different subjects
second is this behavior was implemented since day one and it will be counted as major change,
third this remember me something i forgot to do, using next_plan and reset strategy at the same time should be rejected by api, its better for user to use only one of them (at some periods i had plan to remove next plan but that is not happening, at least today) and i don't know why people use 2 strategy at the same time

i check 2 other pr later but this pr stays open for a now, i will discuss it with other developers

@Rerowros
Copy link
Copy Markdown
Contributor Author

thanks for pr, there are some points i should write here first of all why these 3 pr are related ? they have completely different subjects second is this behavior was implemented since day one and it will be counted as major change, third this remember me something i forgot to do, using next_plan and reset strategy at the same time should be rejected by api, its better for user to use only one of them (at some periods i had plan to remove next plan but that is not happening, at least today) and i don't know why people use 2 strategy at the same time

Thanks for reviewing.

About the behavior change: I agree this is user-visible and can be considered major. I proposed it because the current implementation uses the latest usage reset log as the cycle anchor, so a manual/API reset also postpones the user's monthly/weekly/daily/yearly reset.

Manual/API reset and scheduled reset have different meanings: manual/API reset is a one-off administrative action, while scheduled reset is the user's reset-cycle boundary. Right now both actions use the same anchor, so a manual reset can unexpectedly change the next scheduled reset.

I do not want to force this behavior if the project considers the old logic intentional. I can adjust the PR to make the behavior explicit/backward-compatible, for example by adding an option such as reset_cycle / preserve_reset_cycle, or by separating "reset usage only" from "reset usage and restart cycle" in the API/UI.

Regarding next_plan + reset strategy: I agree this combination is confusing. My intent with reset_source=next_plan was only to say that applying a next plan starts a new usage cycle. If the preferred direction is to reject next_plan together with a reset strategy, I can move that validation into a separate PR and keep this PR focused only on manual resets not silently changing the scheduled cycle.

I can also remove the unrelated dashboard date parsing changes from this PR to keep the scope smaller.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants