undated enforcement

This commit is contained in:
2026-09-18 00:06:25 +05:00
parent 47c292f4cd
commit b67f3f5999
3 changed files with 93 additions and 11 deletions
+87 -9
View File
@@ -553,8 +553,6 @@ def _clean_old_state() -> None:
]
continue
# Keep recent history instead
# of deleting everything.
dates = sorted(
user_usage.keys()
)
@@ -770,6 +768,86 @@ def evaluate_user(
or allowed_by_grant
)
# ---------------------------------------------------------
# DAILY USAGE ACCOUNTING
#
# The scheduler runs once every second.
#
# Only count usage when:
# 1. The user is actually logged in.
# 2. The user is inside an allowed access window.
# 3. The user still has daily allowance remaining.
#
# Temporary grants are consumed separately below.
# ---------------------------------------------------------
if (
logged_in
and inside_window
and allowance_remaining > 0
):
record_usage(
user_id,
1,
)
# Refresh the usage value immediately so
# the returned policy information reflects
# the second we just consumed.
usage_seconds += 1
allowance_remaining = max(
0,
allowance_seconds
- usage_seconds,
)
total_remaining = (
allowance_remaining
+ grant_seconds
)
# If this second consumed the final
# allowance second, the user must be
# locked during this same scheduler pass.
if allowance_remaining <= 0:
should_allow = (
grant_seconds > 0
)
# ---------------------------------------------------------
# TEMPORARY GRANT ACCOUNTING
#
# Temporary time is consumed only while the
# user is actually logged in and is being
# allowed by the temporary grant.
#
# The grant also has its own expires_at timestamp,
# so it cannot remain valid beyond its expiry.
# ---------------------------------------------------------
if (
logged_in
and grant_seconds > 0
):
consume_grant_seconds(
user_id,
1,
)
grant_seconds = max(
0,
grant_seconds - 1,
)
total_remaining = (
allowance_remaining
+ grant_seconds
)
should_allow = (
allowed_by_schedule
or grant_seconds > 0
)
try:
locked = is_locked(
username
@@ -784,8 +862,6 @@ def evaluate_user(
username
)
# Re-check the state after
# unlocking.
if not is_locked(
username
):
@@ -795,9 +871,6 @@ def evaluate_user(
with _state_lock:
state = load_state()
# The enforcement loop must
# continue even if one account
# cannot be unlocked.
_ = state
_ = exc
@@ -831,8 +904,13 @@ def evaluate_user(
"allowance_remaining": allowance_remaining,
"grant_seconds": grant_seconds,
"total_remaining": total_remaining,
"allowed_by_schedule": allowed_by_schedule,
"allowed_by_grant": allowed_by_grant,
"allowed_by_schedule": (
inside_window
and allowance_remaining > 0
),
"allowed_by_grant": (
grant_seconds > 0
),
"allowed": should_allow,
}