feat: add admin client policy control
This commit is contained in:
@@ -11,7 +11,13 @@ from django.contrib.auth import get_user_model
|
||||
from django.db import IntegrityError, transaction
|
||||
from django.utils import timezone
|
||||
|
||||
from config.client_subscription_policy import (
|
||||
build_client_subscription_policy,
|
||||
get_client_subscription_policy,
|
||||
)
|
||||
from apps.licensing.models import (
|
||||
ClientSubscriptionPolicy,
|
||||
ClientSubscriptionPolicyAudit,
|
||||
ClientDevice,
|
||||
DeviceCredential,
|
||||
DeviceBindingAudit,
|
||||
@@ -289,6 +295,57 @@ def _required_reason(reason: str) -> str:
|
||||
return normalized_reason
|
||||
|
||||
|
||||
def get_published_client_subscription_policy() -> dict:
|
||||
"""Return the admin override when present, otherwise the T-635 env fallback."""
|
||||
|
||||
policy = ClientSubscriptionPolicy.objects.filter(pk=1).only("mode", "updated_at").first()
|
||||
if policy is None:
|
||||
return get_client_subscription_policy()
|
||||
return build_client_subscription_policy(mode=policy.mode, updated_at=policy.updated_at)
|
||||
|
||||
|
||||
@transaction.atomic
|
||||
def set_client_subscription_policy(*, mode: str, reason: str, actor) -> ClientSubscriptionPolicy:
|
||||
"""Persist one audited policy transition without allowing a second singleton."""
|
||||
|
||||
normalized_mode = str(mode or "").strip().lower()
|
||||
if normalized_mode not in ClientSubscriptionPolicy.Mode.values:
|
||||
raise LicensingError("bad_request", "客户端订阅策略不合法")
|
||||
normalized_reason = _required_reason(reason)
|
||||
|
||||
policy = ClientSubscriptionPolicy.objects.select_for_update().filter(pk=1).first()
|
||||
created = policy is None
|
||||
if policy is None:
|
||||
try:
|
||||
with transaction.atomic():
|
||||
policy = ClientSubscriptionPolicy.objects.create(
|
||||
singleton_id=1,
|
||||
mode=normalized_mode,
|
||||
updated_by=actor,
|
||||
)
|
||||
except IntegrityError:
|
||||
policy = ClientSubscriptionPolicy.objects.select_for_update().get(pk=1)
|
||||
created = False
|
||||
|
||||
if not created and policy.mode == normalized_mode:
|
||||
raise LicensingError("policy_unchanged", "请选择不同的客户端订阅策略")
|
||||
|
||||
previous_mode = "" if created else policy.mode
|
||||
if not created:
|
||||
policy.mode = normalized_mode
|
||||
policy.updated_by = actor
|
||||
policy.save(update_fields=("mode", "updated_by", "updated_at"))
|
||||
|
||||
ClientSubscriptionPolicyAudit.objects.create(
|
||||
policy=policy,
|
||||
previous_mode=previous_mode,
|
||||
mode=normalized_mode,
|
||||
reason=normalized_reason,
|
||||
changed_by=actor,
|
||||
)
|
||||
return policy
|
||||
|
||||
|
||||
def _create_license_event(
|
||||
*,
|
||||
entitlement: SoftwareEntitlement,
|
||||
|
||||
Reference in New Issue
Block a user