from users.serializers import GetFullUserSerializer,UserPermissionsSerializer,UserAssignedRoleSerializer
from organisations.models import *
from users.models import UserSession, UserPermissions, UserAssignedRole
from rest_framework.pagination import PageNumberPagination
from datetime import datetime
import smtplib, ssl
from email.message import EmailMessage

logged_in_user_key = None

def custom_jwt_response_handler(token_data, user=None, request=None):
    # Extract access token from SimpleJWT response
    if isinstance(token_data, dict) and 'access' in token_data:
        access_token = token_data['access']
    else:
        access_token = token_data
    
    if user is not None:
        user_session = UserSession.objects.filter(user=user, session_token = access_token).first()
        organisation_id = user.user_organisation_branch.branch_organisation.id
        organisation_branch_id = user.user_organisation_branch.id
        # Check 2FA Status
        allow_access = False
        if user.two_fa_status == True:
            allow_access = False
        else:
            allow_access = True

        if not user_session:
            UserSession.objects.create(user=user, session_token = access_token,allow_access = allow_access, data={"organisation_id":organisation_id, "organisation_branch_id":organisation_branch_id})
        else:
            user_session.data = {"organisation_id":organisation_id, "organisation_branch_id":organisation_branch_id}
            user_session.allow_access = allow_access
            user_session.save()

    organisation_settings_list = {}
    organisation_settings = OrganisationSetting.objects.filter(org_setting__id=user.user_organisation_branch.branch_organisation.id).all()
    for organisation_setting in organisation_settings:
        organisation_settings_list[organisation_setting.setting_key] = organisation_setting.setting_value
    
    role_name = ''
    user_role = UserAssignedRole.objects.filter(user=user).first()
    if user_role:
        role_name = user_role.assigned_role.role_name

    organisation = user.user_organisation_branch.branch_organisation

    return {
        'is_locked':False,
        'allow_access':allow_access,
        'token' : access_token,
        'logged_in_time' : datetime.now().strftime('%Y-%m-%d %H:%M'),
        'user':GetFullUserSerializer(user, context={'request' : request}).data,
        'role':role_name,
        "organisation":{
            "id":organisation.id, 
            "name":organisation.name,
            "short_name":organisation.short_name,
            "logo_url":organisation.logo_url,
            "city":organisation.city,
            "address":organisation.address,
            "phone_number":organisation.phone_number,
            "admin_organisation_id":organisation.admin_organisation_id
        },
        "branch":{
            "id":user.user_organisation_branch.id,
            "name":user.user_organisation_branch.name, 
            "short_name":user.user_organisation_branch.short_name,
            "address":user.user_organisation_branch.address
        },
        "organisation_settings":organisation_settings_list,
        "permissions":UserPermissionsSerializer(UserPermissions.objects.filter(user_id=user.id,is_feature_active=True,is_org_comp_active=True,is_role_active=True,is_role_component_active=True,is_user_role_active=True).all(), many=True).data, 
        "profile_url":user.user_staff.profile_url
    }

def get_current_user(request, session_key = None, default=None):
    user_id = request.user.id
    user_session = None
    data = {"user__id": user_id}
    if request.META.get('HTTP_AUTHORIZATION', None):
        token = request.META.get('HTTP_AUTHORIZATION').split(' ')[1]        
        data['session_token'] = token
        user_session = UserSession.objects.filter(**data).first()
    if session_key and user_session:
        if session_key in user_session.data:
            for key, value in user_session.data.items():
                if key == session_key:
                    return value
        else:
            return default if default else 0

    if not user_session and default:
         return default

    return user_session.data if user_session else {}

def get_logged_in_user_key():
    global logged_in_user_key
    return logged_in_user_key

def set_logged_in_user_key(new_key):
    global logged_in_user_key
    logged_in_user_key = new_key

def jwt_switched_session_response_handler(token,old_user_token,new_user,old_user):
    
    user_session = UserSession.objects.filter(user=new_user, session_token = token).first()
    organisation_id = new_user.user_organisation_branch.branch_organisation.id
    organisation_branch_id = new_user.user_organisation_branch.id
    if not user_session:
        UserSession.objects.create(user=new_user, session_token = token, allow_access = True,data={"organisation_id":organisation_id, "organisation_branch_id":organisation_branch_id})
    else:
        user_session.data = {"organisation_id":organisation_id, "organisation_branch_id":organisation_branch_id}
        user_session.allow_access = True
        user_session.save()

    organisation_settings_list = {}
    organisation_settings = OrganisationSetting.objects.filter(org_setting__id=new_user.user_organisation_branch.branch_organisation.id).all()
    for organisation_setting in organisation_settings:

        organisation_settings_list[organisation_setting.setting_key] = organisation_setting.setting_value
    
    role_name = ''
    user_role = UserAssignedRole.objects.filter(user=new_user).first()
    if user_role:
        role_name = user_role.assigned_role.role_name

    organisation = new_user.user_organisation_branch.branch_organisation

    return {
        'is_locked':False,
        'allow_access':True,
        'token' : token,
        'user':GetFullUserSerializer(new_user).data,
        'role':role_name,
        'old_user':GetFullUserSerializer(old_user).data,
        'old_token' :old_user_token,
        "organisation":{
            "id":organisation.id, 
            "name":organisation.name,
            "short_name":organisation.short_name,
            "logo_url":organisation.logo_url,
            "city":organisation.city,
            "address":organisation.address,
            "phone_number":organisation.phone_number,
            "admin_organisation_id":organisation.admin_organisation_id
        },
        "branch":{
            "id":new_user.user_organisation_branch.id,
            "name":new_user.user_organisation_branch.name, 
            "short_name":new_user.user_organisation_branch.short_name,
            "address":new_user.user_organisation_branch.address
        },
        "organisation_settings":organisation_settings_list,
        "permissions":UserPermissionsSerializer(UserPermissions.objects.filter(user_id=new_user.id,is_feature_active=True,is_org_comp_active=True,is_role_active=True,is_role_component_active=True,is_user_role_active=True).all(), many=True).data, 
        "profile_url":new_user.user_staff.profile_url
    }

def send_email(message, subject, receiver_email = None):
    port = 465  # For SSL
    smtp_server = "smtp.gmail.com"
    sender_email = "qbcore.cronjob@gmail.com"  
    receiver_email = "bdikan@questdigito.com"  if not receiver_email else receiver_email
    # cc_email = "bdikan@questdigito.com" if receiver_email == 'wamulabash1@gmail.com' else None
    password = "jaeq ampf gmey mfqj"

    msg = EmailMessage()
    msg.set_content(message)

    msg['Subject'] = subject
    msg['From'] = sender_email
    msg['To'] = receiver_email
    to_addrs = receiver_email

    # if cc_email:
    #     msg['Cc'] = cc_email
    #     to_addrs = [receiver_email] + [cc_email]

    context = ssl._create_unverified_context()
    with smtplib.SMTP_SSL(smtp_server, port, context=context) as server:
        server.login(sender_email, password)
        server.send_message(msg, from_addr=sender_email, to_addrs=to_addrs)
        server.quit()
    
    return True
