from apps.customer.models import ( ResponsibleGroup as ResponsibleGroupModel, ShiveAshenaei as ShiveAshenaeiModel, Customer as CustomerModel, CustomerNote as CustomerNoteModel ) from apps.reminder.models import Reminder as ReminderModel from apps.workspace.models import Workspace as WorkspaceModel from apps.cuser.models import CuserRole as CuserRoleModel from rest_framework import exceptions from utils.get_user_workspace import get_user_workspace, get_user_workspace_uuid from utils.get_cuser_role import get_cuser_role from django.db import transaction, IntegrityError from django.core.exceptions import ValidationError as DjangoValidationError from utils.validations.mobile import normalize_mobile from django.contrib.auth import get_user_model import uuid import random CUser = get_user_model() @transaction.atomic def customer_panel_access(request, mobile: int, customer_id: int, status: bool) -> CuserRoleModel: try: workspace = get_user_workspace(request) customer = CustomerModel.objects.get(id=customer_id, sys_ws=workspace) mobile = normalize_mobile(mobile) if customer.mobile != mobile: raise exceptions.ValidationError({'mobile': 'شماره موبایل باید با شماره مشتری یکسان باشد.'}) # Disabling access must not create an unrelated account or a new role. if not status: if customer.cuser_role_id: if customer.cuser_role.sys_ws_id != workspace.pk: raise exceptions.ValidationError('اتصال پنل متعلق به این فضای کاری نیست؛ ابتدا اتصال را اصلاح کنید.') customer.cuser_role.customer_panel = False customer.cuser_role.save(update_fields=['customer_panel']) return customer.cuser_role try: cuser_obj = CUser.objects.get(mobile=mobile) except CUser.DoesNotExist: cuser_obj = CUser.objects.create_user( username=uuid.uuid4(), mobile=mobile, name_family=customer.name_family, password=f"{random.randint(10000, 900000)}!@#{random.randint(10000, 9000000)}", is_active=True, ) from apps.cuser.models import RoleType if not cuser_obj.is_active: raise exceptions.PermissionDenied('حساب کاربری مربوط به این شماره غیرفعال است.') role_type = RoleType.objects.get(role_name_en='workspace_customer') cuser_role_obj, _ = CuserRoleModel.objects.get_or_create( cuser=cuser_obj, role_type=role_type, sys_ws=workspace, defaults={'name_family': customer.name_family, 'mobile': mobile, 'mobile_verify': True, 'is_active': True, 'customer_panel': True}, ) if CustomerModel.objects.filter(cuser_role=cuser_role_obj, sys_ws=workspace).exclude(pk=customer.pk).exists(): raise exceptions.ValidationError({'mobile': 'این شماره قبلاً به پنل مشتری دیگری متصل شده است.'}) cuser_role_obj.customer_panel = True cuser_role_obj.save(update_fields=['customer_panel']) customer.cuser_role = cuser_role_obj customer.full_clean() customer.save() return cuser_role_obj except exceptions.APIException: raise except DjangoValidationError as exp: raise exceptions.ValidationError(exp.message_dict) except IntegrityError: raise exceptions.ValidationError({'mobile': 'این شماره موبایل قبلاً ثبت شده است.'}) except Exception as exp: message = f'Error Create or Update Customer panel accsess: {exp}' raise exceptions.ValidationError({'error': message}) def create_responsible_group(name: str, workspace: WorkspaceModel): try: responsible_group_obj = ResponsibleGroupModel(name=name, sys_ws=workspace) responsible_group_obj.full_clean() responsible_group_obj.save() return responsible_group_obj except Exception as exp: message = f'Error creating ResponsibleGroup: {exp}' raise exceptions.ValidationError({'error': message}) def delete_responsible_group(responsible_group_id: int, workspace_uuid: str): try: ResponsibleGroupModel.objects.get(id=responsible_group_id, sys_ws__uuid=workspace_uuid).delete() except Exception as exp: message = f'Error Deleting ResponsibleGroup: {exp}' raise exceptions.ValidationError({'error': message}) def create_shive_ashenaei(name: str, workspace: WorkspaceModel) -> ShiveAshenaeiModel: try: shive_obj = ShiveAshenaeiModel(name=name, sys_ws=workspace) shive_obj.full_clean() shive_obj.save() return shive_obj except Exception as exp: message = f'Error creating ShiveAshenaei: {exp}' raise exceptions.ValidationError({'error': message}) def delete_shive_ashenaei(shive_id: int, workspace_uuid: str) -> ShiveAshenaeiModel: try: ShiveAshenaeiModel.objects.get(id=shive_id, sys_ws__uuid=workspace_uuid).delete() except Exception as exp: message = f'Error Delete ShiveAshenaei: {exp}' raise exceptions.ValidationError({'error': message}) @transaction.atomic def create_customer(name_family: str , mobile: int, phone: int, address: str, city: int, shive_ashenaei: int, responsible_group: int, cuser_role: int = None, workspace: WorkspaceModel = None) -> CustomerModel: try: customer_obj = CustomerModel() customer_obj.name_family = name_family customer_obj.mobile = mobile customer_obj.phone = phone customer_obj.address = address customer_obj.city = city customer_obj.shive_ashenaei = shive_ashenaei customer_obj.responsible_group = responsible_group if cuser_role is not None: customer_obj.cuser_role = cuser_role customer_obj.sys_ws = workspace customer_obj.full_clean() customer_obj.save() return customer_obj except DjangoValidationError as exp: raise exceptions.ValidationError(exp.message_dict) except IntegrityError: raise exceptions.ValidationError({'mobile': 'مشتری با این شماره موبایل قبلاً ثبت شده است.'}) except Exception as exp: message = f'Error Creating Customer: {exp}' raise exceptions.ValidationError({'error': message}) def set_customer_mobile(customer, mobile): if mobile is None: return normalized = normalize_mobile(mobile) if normalized != customer.mobile and customer.cuser_role_id: role = customer.cuser_role if role.sys_ws_id == customer.sys_ws_id: role.customer_panel = False role.save(update_fields=['customer_panel']) customer.cuser_role = None customer.mobile = normalized @transaction.atomic def update_customer(customer_id: int, name_family: str = None, mobile: int = None, phone: int = None, address: str = None, city: int = None, shive_ashenaei: int = None, responsible_group: int = None, cuser_role: int = None, workspace_uuid: str = None) -> CustomerModel: try: customer = CustomerModel.objects.select_for_update().get(id=customer_id, sys_ws__uuid=workspace_uuid) set_customer_mobile(customer, mobile) fields = {'name_family': name_family, 'phone': phone, 'address': address, 'city': city, 'shive_ashenaei': shive_ashenaei, 'responsible_group': responsible_group, 'cuser_role': cuser_role} for field, value in fields.items(): if value is not None: setattr(customer, field, value) customer.full_clean() customer.save() return customer except DjangoValidationError as error: raise exceptions.ValidationError(error.message_dict) except IntegrityError: raise exceptions.ValidationError({'mobile': 'مشتری با این شماره موبایل قبلاً ثبت شده است.'}) except CustomerModel.DoesNotExist: raise exceptions.NotFound('مشتری در این فضای کاری پیدا نشد.') def delete_customer(customer_id: int, workspace_uuid: str = None) -> CustomerModel: try: CustomerModel.objects.get(id=customer_id, sys_ws__uuid=workspace_uuid).delete() except Exception as exp: message = f'Error Deleting Customer: {exp}' raise exceptions.ValidationError({'error': message}) @transaction.atomic def create_customer_v2(request, name_family: str , mobile: int, phone: int, address: str, city: int, shive_ashenaei: int, responsible_group: int, cuser_role: int = None) -> CustomerModel: try: workspace = get_user_workspace(request=request) customer_obj = CustomerModel() customer_obj.name_family = name_family customer_obj.mobile = mobile customer_obj.phone = phone customer_obj.address = address customer_obj.city_id = city customer_obj.shive_ashenaei = ShiveAshenaeiModel.objects.get(id=shive_ashenaei, sys_ws=workspace) customer_obj.responsible_group = ResponsibleGroupModel.objects.get(id=responsible_group, sys_ws=workspace) if cuser_role is not None: customer_obj.cuser_role = cuser_role customer_obj.sys_ws = workspace customer_obj.full_clean() customer_obj.save() return customer_obj except DjangoValidationError as exp: raise exceptions.ValidationError(exp.message_dict) except IntegrityError: raise exceptions.ValidationError({'mobile': 'مشتری با این شماره موبایل قبلاً ثبت شده است.'}) except Exception as exp: message = f'Error Creating Customer: {exp}' raise exceptions.ValidationError({'error': message}) def create_customer_note(request, customer_id: int, desc: str, reminder_datetime: str = None, reminder_desc: str = None) -> CustomerNoteModel: with transaction.atomic(): try: workspace = get_user_workspace(request=request) cuser_role = get_cuser_role(request=request) customer_note = CustomerNoteModel() customer_note.customer = CustomerModel.objects.get(id=customer_id, sys_ws=workspace) customer_note.desc = desc customer_note.sys_ws = workspace customer_note.cuser_role = cuser_role customer_note.save() if reminder_datetime: try: reminder = ReminderModel() reminder.type = 'NO' reminder.note = customer_note reminder.id_type = customer_note.id reminder.customer = customer_note.customer reminder.datetime = reminder_datetime if reminder_desc: reminder.desc = reminder_desc reminder.cuser_role = cuser_role reminder.sys_ws = workspace reminder.save() except Exception as exp: transaction.set_rollback(True) message = f'Error Creating Customer Note and Set Reminder: {exp}' raise exceptions.ValidationError({'error': message}) return customer_note except Exception as exp: transaction.set_rollback(True) message = f'Error Creating Customer Note: {exp}' raise exceptions.ValidationError({'error': message}) def customer_note_edit(request, customer_id: int, note_id: int, desc: str, reminder_datetime: str = None, reminder_desc: str = None) -> CustomerNoteModel: try: workspace = get_user_workspace(request) cuser_role = get_cuser_role(request) customer_note = CustomerNoteModel.objects.get(id=note_id, customer_id=customer_id, sys_ws=workspace) customer_note.desc = desc customer_note.save() if reminder_datetime: try: try: reminder = ReminderModel.objects.get(type='NO', note=customer_note, id_type=note_id, customer_id=customer_id) reminder.datetime = reminder_datetime reminder.desc = reminder_desc reminder.save() except Exception as exp: try: reminder = ReminderModel() reminder.type = 'NO' reminder.note = customer_note reminder.id_type = customer_note.id reminder.customer = customer_note.customer reminder.datetime = reminder_datetime if reminder_desc: reminder.desc = reminder_desc reminder.cuser_role = cuser_role reminder.sys_ws = workspace reminder.save() except Exception as exp: print(exp) except Exception as exp: print(exp) return customer_note except Exception as exp: message = f'Error Edit Customer Note: {exp}' raise exceptions.ValidationError({'error': message}) def customer_note_delete(request, customer_id: int, note_id: int) -> CustomerNoteModel: try: workspace = get_user_workspace_uuid(request=request) customer_note = CustomerNoteModel.objects.get(id=note_id, customer_id=customer_id, sys_ws__uuid=workspace).delete() return customer_note except Exception as exp: message = f'Error Delete Customer Note: {exp}' raise exceptions.ValidationError({'error': message})