from django.db import migrations BASE_UNIT_PERMISSIONS = { "tickets": {"view_ticket", "add_ticket", "change_ticket", "claim_ticket", "transfer_ticket", "share_ticket", "change_ticket_priority", "dispatch_group_tickets"}, "messaging": {"add_message", "view_message"}, "customers": {"view_customerprofile", "add_customerprofile", "change_customerprofile", "view_contactgroup", "add_contactgroup", "change_contactgroup"}, "notifications": {"view_smstemplate", "add_smstemplate", "change_smstemplate"}, } AUDIT_ROLES = {"SALES_MANAGER", "CEO", "GENERAL_ADMIN"} def bootstrap_legacy_staff(apps, schema_editor): """Give pre-RBAC staff a safe editable default unit during an in-place upgrade.""" StaffProfile = apps.get_model("staff", "StaffProfile") if not StaffProfile.objects.exists(): return OrganizationalUnit = apps.get_model("staff", "OrganizationalUnit") UnitMembership = apps.get_model("staff", "UnitMembership") Permission = apps.get_model("auth", "Permission") unit, _ = OrganizationalUnit.objects.get_or_create( slug="sales", defaults={"name": "فروش", "description": "واحد پیش‌فرض برای کارشناسان موجود پیش از راه‌اندازی RBAC"}, ) query = None from django.db.models import Q for app_label, codenames in BASE_UNIT_PERMISSIONS.items(): part = Q(content_type__app_label=app_label, codename__in=codenames) query = part if query is None else query | part unit.permissions.add(*Permission.objects.filter(query)) audit_permission = Permission.objects.filter(content_type__app_label="accounts", codename="view_ticketmagiclink").first() for profile in StaffProfile.objects.select_related("user"): if profile.primary_unit_id is None: profile.primary_unit_id = unit.pk profile.save(update_fields=["primary_unit"]) membership, _ = UnitMembership.objects.get_or_create(user_id=profile.user_id, unit=unit, defaults={"is_primary": True, "is_active": True}) changed = False if not membership.is_active: membership.is_active = True; changed = True if profile.primary_unit_id == unit.pk and not membership.is_primary: membership.is_primary = True; changed = True if changed: membership.save(update_fields=["is_active", "is_primary", "updated_at"]) if audit_permission and (profile.role in AUDIT_ROLES or profile.user.is_superuser): membership.permissions.add(audit_permission) class Migration(migrations.Migration): dependencies = [ ("accounts", "0004_ticketmagiclink_created_unit_and_more"), ("customers", "0004_contactgroup_unit_customerprofile_groups_and_more"), ("notifications", "0006_alter_smstemplate_allowed_tags"), ("staff", "0004_organizationalunit_staffprofile_primary_unit_and_more"), ("tickets", "0004_tickettag_ticket_assigned_unit_ticket_created_by_and_more"), ] operations = [migrations.RunPython(bootstrap_legacy_staff, migrations.RunPython.noop)]