
"""
Saudi-influenced data generator for PX360

This script generates realistic test data for the PX360 system with:
- Saudi hospital names
- Arabic names for patients and staff
- Saudi cities and regions
- Realistic medical specializations
- Sample complaints, surveys, and actions
"""
import os
import random
from datetime import datetime, timedelta

import django

# Setup Django
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'config.settings.dev')
# Disable Celery tasks during data generation
os.environ.setdefault('CELERY_TASK_ALWAYS_EAGER', 'True')
django.setup()

from django.contrib.auth import get_user_model
from django.contrib.contenttypes.models import ContentType
from django.utils import timezone

from apps.accounts.models import User
from apps.appreciation.models import (
    Appreciation,
    AppreciationCategory,
    AppreciationBadge,
    UserBadge,
    AppreciationStats,
    AppreciationStatus,
    AppreciationVisibility,
)
from apps.observations.models import (
    Observation,
    ObservationCategory,
    ObservationNote,
    ObservationStatusLog,
    ObservationSeverity,
    ObservationStatus,
)
from apps.complaints.models import Complaint, ComplaintCategory, ComplaintUpdate
from apps.journeys.models import (
    PatientJourneyInstance,
    PatientJourneyStageInstance,
    PatientJourneyStageTemplate,
    PatientJourneyTemplate,
)
from apps.organizations.models import Department, Hospital, Patient, Staff
from apps.projects.models import QIProject
from apps.px_action_center.models import PXAction
from apps.surveys.models import SurveyInstance, SurveyQuestion, SurveyResponse, SurveyTemplate

# Saudi-specific data
SAUDI_HOSPITALS = [
    {'name': 'Alhammadi Hospital', 'name_ar': 'مستشفى الحمادي', 'city': 'Riyadh', 'code': 'HH'},
    # {'name': 'King Faisal Specialist Hospital', 'name_ar': 'مستشفى الملك فيصل التخصصي', 'city': 'Riyadh', 'code': 'KFSH'},
    # {'name': 'King Abdulaziz Medical City', 'name_ar': 'مدينة الملك عبدالعزيز الطبية', 'city': 'Riyadh', 'code': 'KAMC'},
    # {'name': 'King Khalid University Hospital', 'name_ar': 'مستشفى الملك خالد الجامعي', 'city': 'Riyadh', 'code': 'KKUH'},
    # {'name': 'King Abdullah Medical Complex', 'name_ar': 'مجمع الملك عبدالله الطبي', 'city': 'Jeddah', 'code': 'KAMC-JED'},
]

SAUDI_CITIES = ['Riyadh', 'Jeddah', 'Mecca', 'Medina', 'Dammam', 'Khobar', 'Dhahran', 'Taif', 'Buraidah', 'Tabuk']

ARABIC_FIRST_NAMES_MALE = ['محمد', 'أحمد', 'عبدالله', 'خالد', 'سعود', 'فهد', 'عبدالعزيز', 'سلطان', 'فيصل', 'عمر']
ARABIC_FIRST_NAMES_FEMALE = ['فاطمة', 'عائشة', 'مريم', 'نورة', 'سارة', 'هند', 'لطيفة', 'منى', 'ريم', 'جواهر']
ARABIC_LAST_NAMES = ['العتيبي', 'الدوسري', 'القحطاني', 'الشمري', 'الحربي', 'المطيري', 'العنزي', 'الزهراني', 'الغامدي', 'الشهري']

ENGLISH_FIRST_NAMES_MALE = ['Mohammed', 'Ahmed', 'Abdullah', 'Khalid', 'Saud', 'Fahd', 'Abdulaziz', 'Sultan', 'Faisal', 'Omar']
ENGLISH_FIRST_NAMES_FEMALE = ['Fatimah', 'Aisha', 'Maryam', 'Noura', 'Sarah', 'Hind', 'Latifa', 'Mona', 'Reem', 'Jawaher']
ENGLISH_LAST_NAMES = ['Al-Otaibi', 'Al-Dosari', 'Al-Qahtani', 'Al-Shammari', 'Al-Harbi', 'Al-Mutairi', 'Al-Anazi', 'Al-Zahrani', 'Al-Ghamdi', 'Al-Shehri']

DEPARTMENTS = [
    {'name': 'Emergency Department', 'name_ar': 'قسم الطوارئ', 'code': 'ER'},
    {'name': 'Outpatient Department', 'name_ar': 'قسم العيادات الخارجية', 'code': 'OPD'},
    {'name': 'Internal Medicine', 'name_ar': 'الطب الباطني', 'code': 'IM'},
    {'name': 'Surgery', 'name_ar': 'الجراحة', 'code': 'SURG'},
    {'name': 'Pediatrics', 'name_ar': 'طب الأطفال', 'code': 'PEDS'},
    {'name': 'Obstetrics & Gynecology', 'name_ar': 'النساء والولادة', 'code': 'OBGYN'},
    {'name': 'Radiology', 'name_ar': 'الأشعة', 'code': 'RAD'},
    {'name': 'Laboratory', 'name_ar': 'المختبر', 'code': 'LAB'},
    {'name': 'Pharmacy', 'name_ar': 'الصيدلية', 'code': 'PHARM'},
    {'name': 'Cardiology', 'name_ar': 'أمراض القلب', 'code': 'CARD'},
]

SPECIALIZATIONS = [
    'Internal Medicine', 'General Surgery', 'Pediatrics', 'Obstetrics & Gynecology',
    'Cardiology', 'Orthopedics', 'Neurology', 'Dermatology', 'Ophthalmology',
    'ENT', 'Urology', 'Nephrology', 'Gastroenterology', 'Pulmonology'
]

COMPLAINT_TITLES = [
    'Long waiting time in emergency department',
    'Poor communication from nursing staff',
    'Delayed lab results',
    'Billing discrepancy',
    'Unclean patient room',
    'Medication error',
    'Rude behavior from reception staff',
    'Difficulty scheduling appointment',
    'Lost medical records',
    'Inadequate pain management',
]

COMPLAINT_TITLES_AR = [
    'وقت انتظار طويل في قسم الطوارئ',
    'ضعف التواصل من طاقم التمريض',
    'تأخر نتائج المختبر',
    'خطأ في الفاتورة',
    'غرفة المريض غير نظيفة',
    'خطأ في الدواء',
    'سلوك غير لائق من موظف الاستقبال',
    'صعوبة في حجز موعد',
    'فقدان السجلات الطبية',
    'إدارة غير كافية للألم',
]


def clear_existing_data():
    """Clear all existing data from the database"""
    print("\n" + "="*60)
    print("Clearing Existing Data...")
    print("="*60 + "\n")

    from apps.feedback.models import Feedback, FeedbackAttachment, FeedbackResponse
    from apps.social.models import SocialMention
    from apps.callcenter.models import CallCenterInteraction

    # Delete in reverse order of dependencies
    print("Deleting survey instances...")
    SurveyResponse.objects.all().delete()
    SurveyInstance.objects.all().delete()

    print("Deleting journey instances...")
    PatientJourneyStageInstance.objects.all().delete()
    PatientJourneyInstance.objects.all().delete()

    print("Deleting PX actions...")
    PXAction.objects.all().delete()

    print("Deleting QI projects...")
    QIProject.objects.all().delete()

    print("Deleting social mentions...")
    SocialMention.objects.all().delete()

    print("Deleting call center interactions...")
    CallCenterInteraction.objects.all().delete()

    print("Deleting feedback...")
    FeedbackResponse.objects.all().delete()
    FeedbackAttachment.objects.all().delete()
    Feedback.objects.all().delete()

    print("Deleting complaints...")
    ComplaintUpdate.objects.all().delete()
    Complaint.objects.all().delete()

    print("Deleting survey templates...")
    SurveyQuestion.objects.all().delete()
    SurveyTemplate.objects.all().delete()

    print("Deleting journey templates...")
    PatientJourneyStageTemplate.objects.all().delete()
    PatientJourneyTemplate.objects.all().delete()

    print("Deleting patients...")
    Patient.objects.all().delete()

    print("Deleting physician ratings...")
    from apps.physicians.models import PhysicianMonthlyRating
    PhysicianMonthlyRating.objects.all().delete()

    print("Deleting staff...")
    Staff.objects.all().delete()

    print("Deleting departments...")
    Department.objects.all().delete()

    print("Deleting hospitals...")
    Hospital.objects.all().delete()

    print("Deleting users (except superusers)...")
    User.objects.filter(is_superuser=False).delete()

    print("\n✓ All existing data cleared successfully!\n")


def generate_saudi_phone():
    """Generate Saudi phone number"""
    return f"+966{random.choice(['50', '53', '54', '55', '56', '58'])}{random.randint(1000000, 9999999)}"


def generate_mrn():
    """Generate Medical Record Number"""
    return f"MRN{random.randint(100000, 999999)}"


def generate_national_id():
    """Generate Saudi National ID"""
    return f"{random.randint(1000000000, 2999999999)}"


def create_hospitals():
    """Create Saudi hospitals"""
    print("Creating hospitals...")
    hospitals = []
    for hosp_data in SAUDI_HOSPITALS:
        hospital, created = Hospital.objects.get_or_create(
            code=hosp_data['code'],
            defaults={
                'name': hosp_data['name'],
                'name_ar': hosp_data['name_ar'],
                'city': hosp_data['city'],
                'phone': generate_saudi_phone(),
                'status': 'active',
                'capacity': random.randint(200, 800),
            }
        )
        hospitals.append(hospital)
        if created:
            print(f"  Created: {hospital.name}")
    return hospitals


def create_departments(hospitals):
    """Create departments for each hospital"""
    print("Creating departments...")
    departments = []
    for hospital in hospitals:
        for dept_data in DEPARTMENTS:
            dept, created = Department.objects.get_or_create(
                hospital=hospital,
                code=dept_data['code'],
                defaults={
                    'name': dept_data['name'],
                    'name_ar': dept_data['name_ar'],
                    'status': 'active',
                }
            )
            departments.append(dept)
            if created:
                print(f"  Created: {hospital.name} - {dept.name}")
    return departments


def create_staff(hospitals, departments):
    """Create staff"""
    print("Creating staff...")
    staff = []
    for i in range(50):
        hospital = random.choice(hospitals)
        dept = random.choice([d for d in departments if d.hospital == hospital])

        first_name_ar = random.choice(ARABIC_FIRST_NAMES_MALE)
        last_name_ar = random.choice(ARABIC_LAST_NAMES)
        first_name = random.choice(ENGLISH_FIRST_NAMES_MALE)
        last_name = random.choice(ENGLISH_LAST_NAMES)

        staff_member, created = Staff.objects.get_or_create(
            license_number=f"LIC{random.randint(10000, 99999)}",
            defaults={
                'first_name': first_name,
                'last_name': last_name,
                'first_name_ar': first_name_ar,
                'last_name_ar': last_name_ar,
                'specialization': random.choice(SPECIALIZATIONS),
                'hospital': hospital,
                'department': dept,
                # 'phone': generate_saudi_phone(),
                'status': 'active',
                'employee_id': f"EMP{random.randint(10000, 99999)}",
            }
        )
        staff.append(staff_member)
    print(f"  Created {len(staff)} staff members")
    return staff


def create_patients(hospitals):
    """Create patients"""
    print("Creating patients...")
    patients = []
    for i in range(100):
        gender = random.choice(['male', 'female'])
        if gender == 'male':
            first_name_ar = random.choice(ARABIC_FIRST_NAMES_MALE)
            first_name = random.choice(ENGLISH_FIRST_NAMES_MALE)
        else:
            first_name_ar = random.choice(ARABIC_FIRST_NAMES_FEMALE)
            first_name = random.choice(ENGLISH_FIRST_NAMES_FEMALE)

        last_name_ar = random.choice(ARABIC_LAST_NAMES)
        last_name = random.choice(ENGLISH_LAST_NAMES)

        patient, created = Patient.objects.get_or_create(
            mrn=generate_mrn(),
            defaults={
                'first_name': first_name,
                'last_name': last_name,
                'first_name_ar': first_name_ar,
                'last_name_ar': last_name_ar,
                'national_id': generate_national_id(),
                'phone': generate_saudi_phone(),
                'email': f"{first_name.lower()}.{last_name.lower()}@example.com",
                'gender': gender,
                'date_of_birth': datetime.now().date() - timedelta(days=random.randint(365*18, 365*80)),
                'city': random.choice(SAUDI_CITIES),
                'primary_hospital': random.choice(hospitals),
                'status': 'active',
            }
        )
        patients.append(patient)
    print(f"  Created {len(patients)} patients")
    return patients


def create_users(hospitals):
    """Create system users"""
    print("Creating users...")
    from django.contrib.auth.models import Group

    # Create or get groups
    px_admin_group, _ = Group.objects.get_or_create(name='PX Admin')
    hospital_admin_group, _ = Group.objects.get_or_create(name='Hospital Admin')

    # Create PX Admin
    px_admin, created = User.objects.get_or_create(
        username='px_admin',
        defaults={
            'email': 'px.admin@alhammadi.sa',
            'first_name': 'PX',
            'last_name': 'Administrator',
            'is_staff': True,
            'is_superuser': True,
        }
    )
    if created:
        px_admin.set_password('admin123')
        px_admin.save()
        px_admin.groups.add(px_admin_group)
        print("  Created PX Admin")

    # Create Hospital Admins
    for hospital in hospitals:
        user, created = User.objects.get_or_create(
            username=f'admin_{hospital.code.lower()}',
            defaults={
                'email': f'admin@{hospital.code.lower()}.sa',
                'first_name': 'Hospital',
                'last_name': 'Admin',
                'hospital': hospital,
                'is_staff': True,
            }
        )
        if created:
            user.set_password('admin123')
            user.save()
            user.groups.add(hospital_admin_group)
            print(f"  Created Hospital Admin for {hospital.name}")


def create_complaint_categories(hospitals):
    """Create complaint categories"""
    print("Creating complaint categories...")

    # System-wide categories (hospital=None)
    system_categories = [
        {'code': 'CLINICAL', 'name_en': 'Clinical Care', 'name_ar': 'الرعاية السريرية', 'order': 1},
        {'code': 'STAFF', 'name_en': 'Staff Behavior', 'name_ar': 'سلوك الموظفين', 'order': 2},
        {'code': 'FACILITY', 'name_en': 'Facility Issues', 'name_ar': 'مشاكل المرافق', 'order': 3},
        {'code': 'WAIT_TIME', 'name_en': 'Wait Time', 'name_ar': 'وقت الانتظار', 'order': 4},
        {'code': 'BILLING', 'name_en': 'Billing & Insurance', 'name_ar': 'الفوترة والتأمين', 'order': 5},
        {'code': 'COMM', 'name_en': 'Communication', 'name_ar': 'التواصل', 'order': 6},
    ]

    categories = []

    # Create system-wide categories
    for cat_data in system_categories:
        category, created = ComplaintCategory.objects.get_or_create(
            code=cat_data['code'],
            hospital=None,
            defaults={
                'name_en': cat_data['name_en'],
                'name_ar': cat_data['name_ar'],
                'order': cat_data['order'],
                'is_active': True,
            }
        )
        categories.append(category)
        if created:
            print(f"  Created system-wide category: {category.name_en}")

    # Create hospital-specific categories for each hospital
    hospital_specific_categories = [
        {'code': 'ER', 'name_en': 'Emergency Services', 'name_ar': 'خدمات الطوارئ'},
        {'code': 'SURGERY', 'name_en': 'Surgery Department', 'name_ar': 'قسم الجراحة'},
        {'code': 'LAB', 'name_en': 'Laboratory Services', 'name_ar': 'خدمات المختبر'},
    ]

    for hospital in hospitals:
        for cat_data in hospital_specific_categories:
            category, created = ComplaintCategory.objects.get_or_create(
                code=f"{cat_data['code']}_{hospital.code}",
                hospital=hospital,
                defaults={
                    'name_en': cat_data['name_en'],
                    'name_ar': cat_data['name_ar'],
                    'order': random.randint(10, 20),
                    'is_active': True,
                }
            )
            categories.append(category)
            if created:
                print(f"  Created hospital category for {hospital.name}: {category.name_en}")

    print(f"  Created {len(categories)} complaint categories")
    return categories


def create_complaints(patients, hospitals, staff, users):
    """Create sample complaints with 2 years of data"""
    print("Creating complaints (2 years of data)...")

    # Get available complaint categories
    categories = list(ComplaintCategory.objects.filter(is_active=True))
    if not categories:
        print("  ERROR: No complaint categories found! Please create categories first.")
        return []

    complaints = []
    now = timezone.now()

    # Generate complaints over 2 years (730 days)
    # Average 3-5 complaints per day = ~1200-1800 total
    for day_offset in range(730):
        # Random number of complaints per day (0-8, weighted towards 2-4)
        num_complaints = random.choices([0, 1, 2, 3, 4, 5, 6, 7, 8], weights=[5, 10, 20, 25, 20, 10, 5, 3, 2])[0]

        for _ in range(num_complaints):
            patient = random.choice(patients)
            hospital = patient.primary_hospital or random.choice(hospitals)
            created_date = now - timedelta(days=day_offset, hours=random.randint(0, 23), minutes=random.randint(0, 59))

            # Status distribution based on age
            if day_offset < 7:  # Last week - more open/in_progress
                status = random.choices(['open', 'in_progress', 'resolved', 'closed'], weights=[30, 40, 20, 10])[0]
            elif day_offset < 30:  # Last month
                status = random.choices(['open', 'in_progress', 'resolved', 'closed'], weights=[10, 30, 40, 20])[0]
            else:  # Older - mostly resolved/closed
                status = random.choices(['open', 'in_progress', 'resolved', 'closed'], weights=[2, 5, 30, 63])[0]

            # Select appropriate category (system-wide or hospital-specific)
            hospital_categories = [c for c in categories if c.hospital == hospital]
            system_categories_list = [c for c in categories if c.hospital is None]

            # Prefer hospital-specific categories if available, otherwise use system-wide
            available_categories = hospital_categories if hospital_categories else system_categories_list

            complaint = Complaint.objects.create(
                patient=patient,
                hospital=hospital,
                department=random.choice(hospital.departments.all()) if hospital.departments.exists() else None,
                staff=random.choice(staff) if random.random() > 0.5 else None,
                title=random.choice(COMPLAINT_TITLES),
                description=f"Detailed description of the complaint. Patient experienced issues during their visit.",
                category=random.choice(available_categories),
                priority=random.choice(['low', 'medium', 'high']),
                severity=random.choice(['low', 'medium', 'high', 'critical']),
                source=random.choice(['patient', 'family', 'survey', 'call_center', 'moh', 'other']),
                status=status,
                encounter_id=f"ENC{random.randint(100000, 999999)}",
                assigned_to=random.choice(users) if random.random() > 0.5 else None,
            )

            # Override created_at
            complaint.created_at = created_date

            # Set resolved/closed dates if applicable
            if status in ['resolved', 'closed']:
                complaint.resolved_at = created_date + timedelta(hours=random.randint(24, 168))
                complaint.resolved_by = random.choice(users)
                if status == 'closed':
                    complaint.closed_at = complaint.resolved_at + timedelta(hours=random.randint(1, 48))
                    complaint.closed_by = random.choice(users)

            complaint.save()
            complaints.append(complaint)

    print(f"  Created {len(complaints)} complaints over 2 years")
    return complaints


def create_inquiries(patients, hospitals, users):
    """Create inquiries with 2 years of data"""
    print("Creating inquiries (2 years of data)...")
    from apps.complaints.models import Inquiry

    inquiries = []
    now = timezone.now()

    inquiry_subjects = [
        'Question about appointment scheduling',
        'Billing inquiry',
        'Request for medical records',
        'General information request',
        'Pharmacy hours inquiry',
        'Lab results inquiry',
        'Insurance coverage question',
        'Visitor policy question',
        'Parking information',
        'Department location inquiry',
    ]

    # Generate inquiries over 2 years (730 days)
    # Average 1-2 inquiries per day = ~500-700 total
    for day_offset in range(730):
        num_inquiries = random.choices([0, 1, 2, 3], weights=[30, 40, 25, 5])[0]

        for _ in range(num_inquiries):
            patient = random.choice(patients) if random.random() > 0.3 else None
            hospital = (patient.primary_hospital if patient else None) or random.choice(hospitals)
            created_date = now - timedelta(days=day_offset, hours=random.randint(0, 23), minutes=random.randint(0, 59))

            # Status distribution based on age
            if day_offset < 7:  # Last week
                status = random.choices(['open', 'in_progress', 'resolved', 'closed'], weights=[40, 35, 20, 5])[0]
            elif day_offset < 30:  # Last month
                status = random.choices(['open', 'in_progress', 'resolved', 'closed'], weights=[15, 30, 40, 15])[0]
            else:  # Older
                status = random.choices(['open', 'in_progress', 'resolved', 'closed'], weights=[3, 7, 40, 50])[0]

            inquiry = Inquiry.objects.create(
                patient=patient,
                contact_name=f"{random.choice(ENGLISH_FIRST_NAMES_MALE)} {random.choice(ENGLISH_LAST_NAMES)}" if not patient else '',
                contact_phone=generate_saudi_phone() if not patient else '',
                contact_email=f"inquiry{random.randint(1000,9999)}@example.com" if not patient else '',
                hospital=hospital,
                department=random.choice(hospital.departments.all()) if hospital.departments.exists() and random.random() > 0.6 else None,
                subject=random.choice(inquiry_subjects),
                message=f"I would like to inquire about {random.choice(['appointment', 'billing', 'services', 'procedures'])}. Please provide information.",
                category=random.choice(['appointment', 'billing', 'medical_records', 'general', 'other']),
                status=status,
                assigned_to=random.choice(users) if random.random() > 0.5 else None,
            )

            # Override created_at
            inquiry.created_at = created_date

            # Set response if resolved/closed
            if status in ['resolved', 'closed']:
                inquiry.response = "Thank you for your inquiry. We have addressed your question."
                inquiry.responded_at = created_date + timedelta(hours=random.randint(2, 72))
                inquiry.responded_by = random.choice(users)

            inquiry.save()
            inquiries.append(inquiry)

    print(f"  Created {len(inquiries)} inquiries over 2 years")
    return inquiries


def create_feedback(patients, hospitals, staff, users):
    """Create sample feedback"""
    print("Creating feedback...")
    from apps.feedback.models import Feedback, FeedbackResponse

    feedback_titles = [
        'Excellent care from Dr. Ahmed',
        'Very satisfied with the service',
        'Suggestion to improve waiting area',
        'Great experience at the hospital',
        'Staff was very helpful and kind',
        'Clean and well-maintained facility',
        'Quick and efficient service',
        'Appreciate the professionalism',
        'Suggestion for better parking',
        'Outstanding nursing care',
    ]

    feedback_messages = [
        'I had a wonderful experience. The staff was very professional and caring.',
        'The doctor took time to explain everything clearly. Very satisfied.',
        'I suggest adding more seating in the waiting area for better comfort.',
        'Everything was excellent from registration to discharge.',
        'The nurses were extremely helpful and answered all my questions.',
        'The facility is very clean and well-organized.',
        'I was seen quickly and the process was very smooth.',
        'I appreciate the high level of professionalism shown by all staff.',
        'The parking area could be improved with better signage.',
        'The nursing staff provided outstanding care during my stay.',
    ]

    feedbacks = []
    for i in range(40):
        patient = random.choice(patients)
        hospital = patient.primary_hospital or random.choice(hospitals)
        is_anonymous = random.random() < 0.2  # 20% anonymous

        feedback = Feedback.objects.create(
            patient=None if is_anonymous else patient,
            is_anonymous=is_anonymous,
            contact_name=f"{random.choice(ENGLISH_FIRST_NAMES_MALE)} {random.choice(ENGLISH_LAST_NAMES)}" if is_anonymous else '',
            contact_email=f"anonymous{i}@example.com" if is_anonymous else '',
            contact_phone=generate_saudi_phone() if is_anonymous else '',
            hospital=hospital,
            department=random.choice(hospital.departments.all()) if hospital.departments.exists() and random.random() > 0.5 else None,
            staff=random.choice(staff) if random.random() > 0.6 else None,
            feedback_type=random.choice(['compliment', 'suggestion', 'general', 'inquiry']),
            title=random.choice(feedback_titles),
            message=random.choice(feedback_messages),
            category=random.choice(['clinical_care', 'staff_service', 'facility', 'communication', 'appointment', 'cleanliness']),
            rating=random.randint(3, 5) if random.random() > 0.3 else None,
            priority=random.choice(['low', 'medium', 'high']),
            sentiment=random.choice(['positive', 'neutral', 'negative']),
            sentiment_score=random.uniform(0.3, 1.0) if random.random() > 0.7 else None,
            status=random.choice(['submitted', 'reviewed', 'acknowledged', 'closed']),
            encounter_id=f"ENC{random.randint(100000, 999999)}" if random.random() > 0.5 else '',
            assigned_to=random.choice(users) if random.random() > 0.5 else None,
            is_featured=random.random() < 0.15,  # 15% featured
            requires_follow_up=random.random() < 0.2,  # 20% require follow-up
        )

        # Add initial response
        FeedbackResponse.objects.create(
            feedback=feedback,
            response_type='note',
            message=f"Feedback received and logged in the system.",
            created_by=random.choice(users),
            is_internal=True,
        )

        # Add additional responses for some feedback
        if feedback.status in ['reviewed', 'acknowledged', 'closed'] and random.random() > 0.5:
            FeedbackResponse.objects.create(
                feedback=feedback,
                response_type='response',
                message="Thank you for your feedback. We appreciate your input and will work to improve our services.",
                created_by=random.choice(users),
                is_internal=False,
            )

        feedbacks.append(feedback)

    print(f"  Created {len(feedbacks)} feedback items")
    return feedbacks


def create_survey_templates(hospitals):
    """Create survey templates"""
    print("Creating survey templates...")
    # Check if templates already exist
    existing_count = SurveyTemplate.objects.count()
    if existing_count > 0:
        print(f"  Survey templates already exist ({existing_count} found), skipping creation...")
        return

    for hospital in hospitals[:2]:  # Create for first 2 hospitals
        # OPD Survey
        template = SurveyTemplate.objects.create(
            name=f'OPD Patient Satisfaction Survey - {hospital.code}',
            name_ar='استبيان رضا مرضى العيادات الخارجية',
            description='Survey for outpatient department visits',
            description_ar='استبيان لزيارات قسم العيادات الخارجية',
            hospital=hospital,
            survey_type='stage',
            scoring_method='average',
            negative_threshold=3.0,
            is_active=True,
        )

        # Create questions
        questions_data = [
            {'text': 'How would you rate your overall experience?', 'text_ar': 'كيف تقيم تجربتك الإجمالية؟', 'type': 'rating'},
            {'text': 'How likely are you to recommend us?', 'text_ar': 'ما مدى احتمالية توصيتك بنا؟', 'type': 'nps'},
            {'text': 'Was the staff courteous and helpful?', 'text_ar': 'هل كان الموظفون مهذبين ومتعاونين؟', 'type': 'yes_no'},
            {'text': 'Any additional comments?', 'text_ar': 'أي تعليقات إضافية؟', 'type': 'textarea'},
        ]

        for idx, q_data in enumerate(questions_data):
            SurveyQuestion.objects.create(
                survey_template=template,
                text=q_data['text'],
                text_ar=q_data['text_ar'],
                question_type=q_data['type'],
                order=idx,
                is_required=True if idx < 2 else False,
            )

        print(f"  Created survey template for {hospital.name}")


def create_journey_templates(hospitals):
    """Create journey templates"""
    print("Creating journey templates...")
    for hospital in hospitals[:2]:
        # OPD Journey
        journey_template, created = PatientJourneyTemplate.objects.get_or_create(
            hospital=hospital,
            journey_type='opd',
            name='OPD Journey',
            defaults={
                'name_ar': 'رحلة العيادات الخارجية',
                'is_active': True,
                'is_default': True,
            }
        )

        if created:
            # Create stages
            stages_data = [
                {'name': 'Registration', 'name_ar': 'التسجيل', 'code': 'REG', 'trigger': 'OPD_REGISTRATION'},
                {'name': 'MD Consultation', 'name_ar': 'استشارة الطبيب', 'code': 'MD', 'trigger': 'OPD_VISIT_COMPLETED'},
                {'name': 'Laboratory', 'name_ar': 'المختبر', 'code': 'LAB', 'trigger': 'LAB_COMPLETED'},
                {'name': 'Pharmacy', 'name_ar': 'الصيدلية', 'code': 'PHARM', 'trigger': 'PHARMACY_DISPENSED'},
            ]

            for idx, stage_data in enumerate(stages_data):
                PatientJourneyStageTemplate.objects.create(
                    journey_template=journey_template,
                    name=stage_data['name'],
                    name_ar=stage_data['name_ar'],
                    code=stage_data['code'],
                    order=idx,
                    trigger_event_code=stage_data['trigger'],
                    is_active=True,
                )

            print(f"  Created journey template for {hospital.name}")


def create_qi_projects(hospitals):
    """Create QI projects"""
    print("Creating QI projects...")
    project_names = [
        ('Reduce ER Wait Times', 'تقليل أوقات الانتظار في الطوارئ'),
        ('Improve Patient Satisfaction Scores', 'تحسين درجات رضا المرضى'),
        ('Enhance Medication Safety', 'تعزيز سلامة الأدوية'),
        ('Streamline Discharge Process', 'تبسيط عملية الخروج'),
    ]

    projects = []
    for hospital in hospitals[:2]:
        for name_en, name_ar in project_names[:2]:
            project = QIProject.objects.create(
                name=name_en,
                name_ar=name_ar,
                description=f"Quality improvement initiative to {name_en.lower()}",
                hospital=hospital,
                status=random.choice(['active', 'pending', 'completed']),
                start_date=datetime.now().date() - timedelta(days=random.randint(30, 180)),
                target_completion_date=datetime.now().date() + timedelta(days=random.randint(30, 180)),
            )
            projects.append(project)
    print(f"  Created {len(projects)} QI projects")
    return projects


def create_px_actions(complaints, hospitals, users):
    """Create PX actions"""
    print("Creating PX actions...")
    actions = []
    for i in range(20):
        hospital = random.choice(hospitals)
        action = PXAction.objects.create(
            source_type=random.choice(['survey', 'complaint', 'social_media', 'call_center']),
            title=f"Action: {random.choice(COMPLAINT_TITLES)}",
            description="Action created to address patient feedback and improve experience.",
            hospital=hospital,
            department=random.choice(hospital.departments.all()) if hospital.departments.exists() else None,
            category=random.choice(['clinical_quality', 'patient_safety', 'service_quality', 'staff_behavior']),
            priority=random.choice(['low', 'medium', 'high', 'urgent']),
            severity=random.choice(['low', 'medium', 'high', 'critical']),
            status=random.choice(['open', 'in_progress', 'pending_approval', 'approved', 'closed']),
            assigned_to=random.choice(users) if random.random() > 0.3 else None,
        )
        actions.append(action)
    print(f"  Created {len(actions)} PX actions")
    return actions


def create_journey_instances(journey_templates, patients):
    """Create journey instances"""
    print("Creating journey instances...")
    from apps.journeys.models import PatientJourneyTemplate

    templates = PatientJourneyTemplate.objects.filter(is_active=True)
    if not templates.exists():
        print("  No journey templates found, skipping...")
        return []

    instances = []
    for i in range(20):
        template = random.choice(templates)
        patient = random.choice(patients)

        instance = PatientJourneyInstance.objects.create(
            journey_template=template,
            patient=patient,
            encounter_id=f"ENC{random.randint(100000, 999999)}",
            hospital=template.hospital,
            status=random.choice(['active', 'completed']),
        )

        # Create stage instances
        for stage_template in template.stages.all():
            PatientJourneyStageInstance.objects.create(
                journey_instance=instance,
                stage_template=stage_template,
                status=random.choice(['pending', 'completed']),
            )

        instances.append(instance)
    print(f"  Created {len(instances)} journey instances")
    return instances


def create_survey_instances(survey_templates, patients, staff):
    """Create survey instances"""
    print("Creating survey instances...")
    from apps.surveys.models import SurveyTemplate

    templates = SurveyTemplate.objects.filter(is_active=True)
    if not templates.exists():
        print("  No survey templates found, skipping...")
        return []

    instances = []
    for i in range(30):
        template = random.choice(templates)
        patient = random.choice(patients)
        staff_member = random.choice(staff) if random.random() > 0.3 else None

        instance = SurveyInstance.objects.create(
            survey_template=template,
            patient=patient,
            delivery_channel=random.choice(['sms', 'whatsapp', 'email']),
            recipient_phone=patient.phone,
            recipient_email=patient.email,
            status=random.choice(['sent', 'completed']),
            sent_at=timezone.now() - timedelta(days=random.randint(1, 30)),
            metadata={'staff_id': str(staff_member.id)} if staff_member else {},
        )

        # If completed, add responses
        if instance.status == 'completed':
            instance.completed_at = timezone.now() - timedelta(days=random.randint(0, 29))
            for question in template.questions.all():
                if question.question_type in ['rating', 'likert']:
                    SurveyResponse.objects.create(
                        survey_instance=instance,
                        question=question,
                        numeric_value=random.randint(1, 5),
                    )
                elif question.question_type == 'nps':
                    SurveyResponse.objects.create(
                        survey_instance=instance,
                        question=question,
                        numeric_value=random.randint(0, 10),
                    )
            instance.calculate_score()
            instance.save()

        instances.append(instance)
    print(f"  Created {len(instances)} survey instances")
    return instances


def create_call_center_interactions(patients, hospitals, users):
    """Create call center interactions"""
    print("Creating call center interactions...")
    from apps.callcenter.models import CallCenterInteraction

    interactions = []
    for i in range(25):
        patient = random.choice(patients)
        hospital = patient.primary_hospital or random.choice(hospitals)

        interaction = CallCenterInteraction.objects.create(
            patient=patient,
            hospital=hospital,
            agent=random.choice(users) if random.random() > 0.3 else None,
            call_type=random.choice(['inquiry', 'complaint', 'appointment', 'follow_up', 'feedback']),
            subject=f"Call regarding {random.choice(['appointment', 'billing', 'test results', 'medication'])}",
            notes="Patient called with inquiry. Issue resolved during call.",
            satisfaction_rating=random.randint(1, 5),
            wait_time_seconds=random.randint(30, 600),
            call_duration_seconds=random.randint(120, 900),
            resolved=random.choice([True, False]),
        )
        interactions.append(interaction)
    print(f"  Created {len(interactions)} call center interactions")
    return interactions


def create_social_mentions(hospitals):
    """Create social media mentions"""
    print("Creating social media mentions...")
    from apps.social.models import SocialMention

    mentions = []
    for i in range(15):
        hospital = random.choice(hospitals)

        mention = SocialMention.objects.create(
            platform=random.choice(['twitter', 'facebook', 'instagram']),
            post_url=f"https://twitter.com/user/status/{random.randint(1000000, 9999999)}",
            post_id=f"POST{random.randint(100000, 999999)}",
            author_username=f"user{random.randint(100, 999)}",
            author_name=f"{random.choice(ENGLISH_FIRST_NAMES_MALE)} {random.choice(ENGLISH_LAST_NAMES)}",
            content=f"Great experience at {hospital.name}! The staff was very professional.",
            hospital=hospital,
            sentiment=random.choice(['positive', 'neutral', 'negative']),
            sentiment_score=random.uniform(-1, 1),
            likes_count=random.randint(0, 100),
            shares_count=random.randint(0, 50),
            comments_count=random.randint(0, 30),
            posted_at=timezone.now() - timedelta(days=random.randint(1, 30)),
        )
        mentions.append(mention)
    print(f"  Created {len(mentions)} social media mentions")
    return mentions


def create_staff_monthly_ratings(staff):
    """Create staff monthly ratings for last 6 months"""
    print("Creating staff monthly ratings...")
    from apps.physicians.models import PhysicianMonthlyRating
    from decimal import Decimal

    ratings = []
    now = datetime.now()

    # Generate ratings for last 6 months
    for staff_member in staff:
        for months_ago in range(6):
            target_date = now - timedelta(days=30 * months_ago)
            year = target_date.year
            month = target_date.month

            # Generate realistic ratings (mostly good, some variation)
            base_rating = random.uniform(3.5, 4.8)
            total_surveys = random.randint(5, 25)

            # Calculate sentiment counts based on rating
            if base_rating >= 4.0:
                positive_count = int(total_surveys * random.uniform(0.7, 0.9))
                negative_count = int(total_surveys * random.uniform(0.05, 0.15))
            elif base_rating >= 3.0:
                positive_count = int(total_surveys * random.uniform(0.4, 0.6))
                negative_count = int(total_surveys * random.uniform(0.15, 0.3))
            else:
                positive_count = int(total_surveys * random.uniform(0.2, 0.4))
                negative_count = int(total_surveys * random.uniform(0.3, 0.5))

            neutral_count = total_surveys - positive_count - negative_count

            rating, created = PhysicianMonthlyRating.objects.get_or_create(
                physician=staff_member,
                year=year,
                month=month,
                defaults={
                    'average_rating': Decimal(str(round(base_rating, 2))),
                    'total_surveys': total_surveys,
                    'positive_count': positive_count,
                    'neutral_count': neutral_count,
                    'negative_count': negative_count,
                    'md_consult_rating': Decimal(str(round(base_rating + random.uniform(-0.3, 0.3), 2))),
                    'metadata': {
                        'generated': True,
                        'generated_at': now.isoformat()
                    }
                }
            )
            ratings.append(rating)

    print(f"  Created {len(ratings)} physician monthly ratings")

    # Update rankings for each month
    print("  Updating physician rankings...")
    from apps.physicians.models import PhysicianMonthlyRating
    from apps.organizations.models import Hospital, Department

    # Get unique year-month combinations
    periods = PhysicianMonthlyRating.objects.values_list('year', 'month').distinct()

    for year, month in periods:
        # Update hospital rankings
        hospitals = Hospital.objects.filter(status='active')
        for hospital in hospitals:
            hospital_ratings = PhysicianMonthlyRating.objects.filter(
                physician__hospital=hospital,
                year=year,
                month=month
            ).order_by('-average_rating')

            for rank, rating in enumerate(hospital_ratings, start=1):
                rating.hospital_rank = rank
                rating.save(update_fields=['hospital_rank'])

        # Update department rankings
        departments = Department.objects.filter(status='active')
        for department in departments:
            dept_ratings = PhysicianMonthlyRating.objects.filter(
                physician__department=department,
                year=year,
                month=month
            ).order_by('-average_rating')

            for rank, rating in enumerate(dept_ratings, start=1):
                rating.department_rank = rank
                rating.save(update_fields=['department_rank'])

    print("  ✓ Rankings updated successfully")
    return ratings


def create_appreciations(users, physicians, hospitals, departments, categories):
    """Create appreciations with 2 years of historical data"""
    print("Creating appreciations (2 years of data)...")

    # Get ContentType for User and Physician
    user_ct = ContentType.objects.get_for_model(User)
    physician_ct = ContentType.objects.get_for_model(Physician)

    # Message templates for generating realistic appreciations
    message_templates_en = [
        "Thank you for {action}. Your {quality} made a real difference in our patient's care.",
        "I want to express my sincere appreciation for {action}. Your {quality} is truly exceptional.",
        "Outstanding work! Your {action} and {quality} have not gone unnoticed.",
        "Grateful for your {action}. The {quality} you demonstrate every day inspires us all.",
        "A big thank you for {action}. Your {quality} sets an excellent example.",
        "Exceptional job on {action}. Your {quality} is invaluable to our team.",
        "Words cannot express how much I appreciate your {action}. Your {quality} shines through.",
        "Thank you for going above and beyond with {action}. Your {quality} makes our hospital better.",
        "Deeply grateful for your {action}. The {quality} you show is remarkable.",
        "Your {action} has made a significant impact. Your {quality} is truly appreciated.",
    ]

    message_templates_ar = [
        "شكراً لك على {action}. {quality} الخاص بك أحدث فرقاً حقيقياً في رعاية مرضانا.",
        "أود أن أعرب عن تقديري الخالص لـ {action}. {quality} استثنائي حقاً.",
        "عمل رائع! {action} و{quality} لم يمرا مرور الكرام.",
        "ممتن لـ {action}. {quality} الذي تظهره كل يوم يلهمنا جميعاً.",
        "شكراً جزيلاً على {action}. {quality} يضع مثالاً ممتازاً.",
        "عمل استثنائي في {action}. {quality} لا يقدر بثمن لفريقنا.",
        "الكلمات لا تعبر عن مدى تقديري لـ {action}. {quality} يظهر بوضوح.",
        "شكراً لتجاوز التوقعات مع {action}. {quality} يجعل مستشفانا أفضل.",
        "عميق الامتنان لـ {action}. {quality} الذي تظهره مذهل.",
        "لقد حدث {action} تأثيراً كبيراً. {quality} حقاً مقدر.",
    ]

    actions = [
        "providing excellent patient care", "outstanding teamwork", "quick response in emergency",
        "thorough diagnosis", "compassionate patient interaction", "efficient workflow management",
        "mentoring junior staff", "innovative solution implementation", "attention to detail",
        "going the extra mile", "maintaining patient safety", "clear communication",
        "timely treatment", "excellent bedside manner", "professional conduct",
    ]

    qualities = [
        "professionalism", "dedication", "expertise", "compassion", "attention to detail",
        "efficiency", "leadership", "teamwork", "reliability", "positive attitude",
        "patience", "kindness", "commitment", "excellence", "integrity",
    ]

    appreciations = []
    now = timezone.now()

    # Weighted category distribution
    category_weights = {
        'excellent_care': 30,
        'team_player': 20,
        'going_extra_mile': 15,
        'positive_attitude': 12,
        'leadership': 10,
        'innovation': 8,
        'reliability': 3,
        'mentorship': 2,
    }

    # Create category code mapping
    category_map = {cat.code: cat for cat in categories}

    # Generate appreciations over 2 years (730 days)
    # Average 1-2 appreciations per day = ~800-1200 total
    for day_offset in range(730):
        # Recency bias: more appreciations in recent months
        recency_factor = max(0.5, 1.0 - (day_offset / 1460))  # 0.5 to 1.0

        # Number of appreciations per day (weighted by recency)
        base_count = random.choices([0, 1, 2], weights=[30, 50, 20])[0]
        num_appreciations = max(0, int(base_count * recency_factor))

        for _ in range(num_appreciations):
            # Select sender (users only - users send appreciations)
            sender = random.choice(users)

            # Select recipient (70% physician, 30% user)
            is_physician_recipient = random.random() < 0.7

            if is_physician_recipient:
                recipient = random.choice(physicians)
                recipient_ct = physician_ct
            else:
                # User recipients (excluding sender)
                potential_recipients = [u for u in users if u.id != sender.id]
                if not potential_recipients:
                    continue
                recipient = random.choice(potential_recipients)
                recipient_ct = user_ct

            # Ensure sender ≠ recipient
            if sender.id == recipient.id:
                continue

            # Determine hospital context
            if is_physician_recipient:
                hospital = recipient.hospital
            else:
                hospital = recipient.hospital if recipient.hospital else sender.hospital

            if not hospital:
                continue

            # Determine department context
            department = None
            if is_physician_recipient and recipient.department:
                department = recipient.department
            elif random.random() < 0.3:
                # Some appreciations have department context
                hospital_depts = [d for d in departments if d.hospital == hospital]
                if hospital_depts:
                    department = random.choice(hospital_depts)

            # Select category (weighted distribution)
            category_codes = list(category_map.keys())
            weights = [category_weights[code] for code in category_codes]
            category_code = random.choices(category_codes, weights=weights, k=1)[0]
            category = category_map.get(category_code)

            if not category:
                continue

            # Generate message
            action = random.choice(actions)
            quality = random.choice(qualities)
            message_en = random.choice(message_templates_en).format(action=action, quality=quality)
            message_ar = random.choice(message_templates_ar).format(action=action, quality=quality)

            # Select visibility (40% private, 25% dept, 25% hospital, 10% public)
            visibility = random.choices(
                list(AppreciationVisibility.values),
                weights=[40, 25, 25, 10],
                k=1
            )[0]

            # Determine status based on age
            if day_offset < 1:  # Last 24 hours
                status = random.choices(
                    list(AppreciationStatus.values),
                    weights=[20, 50, 30],  # draft, sent, acknowledged
                    k=1
                )[0]
            elif day_offset < 7:  # Last week
                status = random.choices(
                    list(AppreciationStatus.values),
                    weights=[5, 40, 55],
                    k=1
                )[0]
            else:  # Older
                status = random.choices(
                    list(AppreciationStatus.values),
                    weights=[1, 10, 89],
                    k=1
                )[0]

            # Calculate timestamps
            created_date = now - timedelta(
                days=day_offset,
                hours=random.randint(0, 23),
                minutes=random.randint(0, 59)
            )

            sent_at = None
            acknowledged_at = None

            if status != AppreciationStatus.DRAFT:
                # Sent time: 0-24 hours after creation (for older appreciations)
                if day_offset < 1:
                    sent_delay = random.randint(0, 23)
                else:
                    sent_delay = random.randint(1, 24)
                sent_at = created_date + timedelta(hours=sent_delay)

            if status == AppreciationStatus.ACKNOWLEDGED:
                # Acknowledged time: 1-72 hours after sent
                acknowledge_delay = random.randint(1, 72)
                acknowledged_at = sent_at + timedelta(hours=acknowledge_delay)

            # Anonymous option (15% anonymous)
            is_anonymous = random.random() < 0.15

            # Create appreciation
            appreciation = Appreciation(
                sender=sender if not is_anonymous else None,
                recipient_content_type=recipient_ct,
                recipient_object_id=recipient.id,
                hospital=hospital,
                department=department,
                category=category,
                message_en=message_en,
                message_ar=message_ar,
                visibility=visibility,
                status=status,
                is_anonymous=is_anonymous,
                sent_at=sent_at,
                acknowledged_at=acknowledged_at,
            )

            # Override created_at for historical data
            appreciation.created_at = created_date
            appreciation.save()

            appreciations.append(appreciation)

    print(f"  Created {len(appreciations)} appreciations over 2 years")
    return appreciations


def award_badges(badges, users, physicians, categories):
    """Award badges to users and physicians based on appreciations"""
    print("Awarding badges...")
    user_badges = []

    # Get ContentType for User and Physician
    user_ct = ContentType.objects.get_for_model(User)
    physician_ct = ContentType.objects.get_for_model(Physician)

    # Badge criteria mapping (using codes from seed command)
    badge_criteria = {
        'first_appreciation': {'min_count': 1, 'categories': None},
        'appreciated_5': {'min_count': 5, 'categories': None},
        'appreciated_10': {'min_count': 10, 'categories': None},
        'appreciated_25': {'min_count': 25, 'categories': None},
        'appreciated_50': {'min_count': 50, 'categories': None},
        # Monthly champion and other badges have complex criteria, award randomly
        'monthly_champion': {'min_count': 10, 'categories': None},
        'streak_4_weeks': {'min_count': 15, 'categories': None},
        'diverse_appreciation': {'min_count': 20, 'categories': None},
    }

    badge_map = {badge.code: badge for badge in badges}

    # Award badges to users (30% get badges)
    for user in users:
        if random.random() > 0.7:  # 30% of users get badges
            continue

        # Count appreciations received by this user
        received_count = Appreciation.objects.filter(
            recipient_content_type=user_ct,
            recipient_object_id=user.id,
            status=AppreciationStatus.ACKNOWLEDGED
        ).count()

        # Award appropriate badges
        for badge_code, criteria in badge_criteria.items():
            if badge_code not in badge_map:
                continue

            if received_count >= criteria['min_count']:
                # Check if already has this badge
                existing = UserBadge.objects.filter(
                    recipient_content_type=user_ct,
                    recipient_object_id=user.id,
                    badge=badge_map[badge_code]
                ).first()

                if not existing:
                    # Random chance to award (not guaranteed even if criteria met)
                    if random.random() < 0.6:
                        user_badges.append(UserBadge(
                            recipient_content_type=user_ct,
                            recipient_object_id=user.id,
                            badge=badge_map[badge_code],
                            appreciation_count=received_count,
                        ))

    # Award badges to physicians (60% get badges)
    for physician in physicians:
        if random.random() > 0.6:  # 60% of physicians get badges
            continue

        # Count appreciations received by this physician
        received_count = Appreciation.objects.filter(
            recipient_content_type=physician_ct,
            recipient_object_id=physician.id,
            status=AppreciationStatus.ACKNOWLEDGED
        ).count()

        # Award appropriate badges
        for badge_code, criteria in badge_criteria.items():
            if badge_code not in badge_map:
                continue

            if received_count >= criteria['min_count']:
                # Check if already has this badge
                existing = UserBadge.objects.filter(
                    recipient_content_type=physician_ct,
                    recipient_object_id=physician.id,
                    badge=badge_map[badge_code]
                ).first()

                if not existing:
                    # Higher chance for physicians
                    if random.random() < 0.7:
                        user_badges.append(UserBadge(
                            recipient_content_type=physician_ct,
                            recipient_object_id=physician.id,
                            badge=badge_map[badge_code],
                            appreciation_count=received_count,
                        ))

    # Bulk create user badges
    UserBadge.objects.bulk_create(user_badges)

    print(f"  Awarded {len(user_badges)} badges to users and physicians")
    return user_badges


def generate_appreciation_stats(users, physicians, hospitals):
    """Generate appreciation statistics for users and physicians"""
    print("Generating appreciation statistics...")
    stats = []
    now = timezone.now()

    # Get ContentType for User and Physician
    user_ct = ContentType.objects.get_for_model(User)
    physician_ct = ContentType.objects.get_for_model(Physician)

    # Get current year and month
    year = now.year
    month = now.month

    # Generate stats for users (70% have stats)
    for user in users:
        if random.random() > 0.7:
            continue

        # Generate realistic stats
        received_count = random.randint(0, 30)
        sent_count = random.randint(0, 50)
        acknowledged_count = int(received_count * random.uniform(0.6, 1.0))

        stats.append(AppreciationStats(
            recipient_content_type=user_ct,
            recipient_object_id=user.id,
            year=year,
            month=month,
            hospital=user.hospital if user.hospital else random.choice(hospitals),
            received_count=received_count,
            sent_count=sent_count,
            acknowledged_count=acknowledged_count,
            hospital_rank=random.randint(1, 20) if received_count > 0 else None,
        ))

    # Generate stats for physicians (90% have stats)
    for physician in physicians:
        if random.random() > 0.1:  # 90% have stats
            # Physicians typically receive more appreciations
            received_count = random.randint(5, 50)
            sent_count = random.randint(0, 20)  # Physicians send less
            acknowledged_count = int(received_count * random.uniform(0.7, 1.0))

            stats.append(AppreciationStats(
                recipient_content_type=physician_ct,
                recipient_object_id=physician.id,
                year=year,
                month=month,
                hospital=physician.hospital,
                department=physician.department,
                received_count=received_count,
                sent_count=sent_count,
                acknowledged_count=acknowledged_count,
                hospital_rank=random.randint(1, 10) if received_count > 5 else None,
            ))

    # Bulk create stats
    AppreciationStats.objects.bulk_create(stats)

    print(f"  Generated {len(stats)} appreciation statistics")
    return stats


def create_observations(hospitals, departments, users):
    """Create observations with 2 years of historical data"""
    print("Creating observations (2 years of data)...")

    # Get observation categories (should be seeded)
    obs_categories = list(ObservationCategory.objects.filter(is_active=True))
    if not obs_categories:
        print("  WARNING: No observation categories found. Run: python manage.py seed_observation_categories")
        return []

    # Observation descriptions
    observation_descriptions = [
        "Noticed a wet floor near the elevator without any warning signs. This could be a slip hazard for patients and visitors.",
        "Observed expired hand sanitizer in the dispenser near the main entrance. The expiration date was 3 months ago.",
        "Fire extinguisher in corridor B appears to be missing its inspection tag. Last visible inspection was over a year ago.",
        "Patient call button in room 205 is not functioning properly. Patient had to wait for assistance.",
        "Medication cart was left unattended in the hallway for approximately 15 minutes during shift change.",
        "Emergency exit sign on the 3rd floor is not illuminated. This could be a safety concern during power outages.",
        "Observed staff member not wearing proper PPE while handling biohazard materials.",
        "Temperature in the medication storage room seems higher than normal. Thermometer shows 28°C.",
        "Wheelchair in the lobby has a broken wheel lock mechanism. Could be dangerous for patients.",
        "Noticed a strong chemical smell in the laboratory area. Ventilation may not be working properly.",
        "Patient identification wristband was found on the floor in the waiting area.",
        "Sharps container in treatment room 3 is overfilled and needs immediate replacement.",
        "Observed water leak from ceiling tiles in the radiology waiting area.",
        "Emergency shower station in the lab has not been tested recently according to the log.",
        "Noticed outdated patient safety posters in the pediatric ward.",
    ]

    observation_titles = [
        "Wet floor hazard",
        "Expired sanitizer",
        "Fire safety concern",
        "Equipment malfunction",
        "Medication security",
        "Emergency signage issue",
        "PPE compliance",
        "Temperature control",
        "Equipment maintenance",
        "Ventilation concern",
        "Patient safety",
        "Waste disposal",
        "Facility maintenance",
        "Safety equipment",
        "Signage update needed",
    ]

    locations = [
        "Main Entrance", "Emergency Department", "ICU", "Pediatric Ward", "Surgery Floor",
        "Radiology Department", "Laboratory", "Pharmacy", "Cafeteria", "Parking Garage",
        "Outpatient Clinic", "Rehabilitation Center", "Administration Building", "Staff Lounge",
        "Patient Rooms Floor 2", "Patient Rooms Floor 3", "Waiting Area", "Reception",
    ]

    observations = []
    now = timezone.now()

    # Generate observations over 2 years (730 days)
    # Average 1-3 observations per day
    for day_offset in range(730):
        num_observations = random.choices([0, 1, 2, 3, 4], weights=[20, 35, 30, 10, 5])[0]

        for _ in range(num_observations):
            hospital = random.choice(hospitals)
            hospital_depts = [d for d in departments if d.hospital == hospital]

            created_date = now - timedelta(
                days=day_offset,
                hours=random.randint(0, 23),
                minutes=random.randint(0, 59)
            )

            # Status distribution based on age
            if day_offset < 7:  # Last week
                status = random.choices(
                    [ObservationStatus.NEW, ObservationStatus.TRIAGED, ObservationStatus.ASSIGNED,
                     ObservationStatus.IN_PROGRESS, ObservationStatus.RESOLVED, ObservationStatus.CLOSED],
                    weights=[25, 20, 20, 20, 10, 5]
                )[0]
            elif day_offset < 30:  # Last month
                status = random.choices(
                    [ObservationStatus.NEW, ObservationStatus.TRIAGED, ObservationStatus.ASSIGNED,
                     ObservationStatus.IN_PROGRESS, ObservationStatus.RESOLVED, ObservationStatus.CLOSED],
                    weights=[5, 10, 15, 20, 30, 20]
                )[0]
            else:  # Older
                status = random.choices(
                    [ObservationStatus.NEW, ObservationStatus.TRIAGED, ObservationStatus.ASSIGNED,
                     ObservationStatus.IN_PROGRESS, ObservationStatus.RESOLVED, ObservationStatus.CLOSED,
                     ObservationStatus.REJECTED, ObservationStatus.DUPLICATE],
                    weights=[2, 3, 5, 5, 40, 40, 3, 2]
                )[0]

            # Severity distribution
            severity = random.choices(
                [ObservationSeverity.LOW, ObservationSeverity.MEDIUM,
                 ObservationSeverity.HIGH, ObservationSeverity.CRITICAL],
                weights=[30, 45, 20, 5]
            )[0]

            # Anonymous vs identified (60% anonymous)
            is_anonymous = random.random() < 0.6

            # Generate tracking code
            import secrets
            tracking_code = f"OBS-{secrets.token_hex(3).upper()}"

            observation = Observation(
                tracking_code=tracking_code,
                category=random.choice(obs_categories),
                title=random.choice(observation_titles),
                description=random.choice(observation_descriptions),
                severity=severity,
                location_text=random.choice(locations),
                incident_datetime=created_date - timedelta(hours=random.randint(0, 48)),
                reporter_staff_id=f"EMP{random.randint(1000, 9999)}" if not is_anonymous else '',
                reporter_name=f"{random.choice(ENGLISH_FIRST_NAMES_MALE)} {random.choice(ENGLISH_LAST_NAMES)}" if not is_anonymous else '',
                reporter_phone=generate_saudi_phone() if not is_anonymous and random.random() > 0.5 else '',
                reporter_email=f"staff{random.randint(100, 999)}@alhammadi.sa" if not is_anonymous and random.random() > 0.5 else '',
                status=status,
                assigned_department=random.choice(hospital_depts) if hospital_depts and status not in [ObservationStatus.NEW] else None,
                assigned_to=random.choice(users) if status in [ObservationStatus.ASSIGNED, ObservationStatus.IN_PROGRESS, ObservationStatus.RESOLVED, ObservationStatus.CLOSED] and random.random() > 0.3 else None,
            )

            # Set timestamps based on status
            if status not in [ObservationStatus.NEW]:
                observation.triaged_at = created_date + timedelta(hours=random.randint(1, 24))
                observation.triaged_by = random.choice(users)

            if status in [ObservationStatus.RESOLVED, ObservationStatus.CLOSED]:
                observation.resolved_at = created_date + timedelta(hours=random.randint(24, 168))

            if status == ObservationStatus.CLOSED:
                observation.closed_at = (observation.resolved_at or created_date) + timedelta(hours=random.randint(1, 48))

            observation.save()

            # Override created_at
            Observation.objects.filter(pk=observation.pk).update(created_at=created_date)

            # Add status log entries
            if status != ObservationStatus.NEW:
                ObservationStatusLog.objects.create(
                    observation=observation,
                    from_status=ObservationStatus.NEW,
                    to_status=ObservationStatus.TRIAGED,
                    changed_by=random.choice(users),
                    comment="Observation triaged and categorized."
                )

            if status in [ObservationStatus.ASSIGNED, ObservationStatus.IN_PROGRESS, ObservationStatus.RESOLVED, ObservationStatus.CLOSED]:
                ObservationStatusLog.objects.create(
                    observation=observation,
                    from_status=ObservationStatus.TRIAGED,
                    to_status=ObservationStatus.ASSIGNED,
                    changed_by=random.choice(users),
                    comment="Assigned to responsible department."
                )

            if status in [ObservationStatus.RESOLVED, ObservationStatus.CLOSED]:
                ObservationStatusLog.objects.create(
                    observation=observation,
                    from_status=ObservationStatus.IN_PROGRESS if status != ObservationStatus.RESOLVED else ObservationStatus.ASSIGNED,
                    to_status=ObservationStatus.RESOLVED,
                    changed_by=random.choice(users),
                    comment="Issue has been addressed and resolved."
                )

            # Add internal notes for some observations
            if random.random() > 0.6:
                ObservationNote.objects.create(
                    observation=observation,
                    note="Initial assessment completed. Following up with relevant department.",
                    created_by=random.choice(users),
                    is_internal=True
                )

            observations.append(observation)

    print(f"  Created {len(observations)} observations over 2 years")
    return observations


def main():
    """Main data generation function"""
    print("\n" + "="*60)
    print("PX360 - Saudi-Influenced Data Generator")
    print("="*60 + "\n")

    # Clear existing data first
    # clear_existing_data()

    # Create base data
    # hospitals = create_hospitals()
    hospitals = Hospital.objects.all()

    departments = create_departments(hospitals)
    staff = create_staff(hospitals, departments)
    patients = create_patients(hospitals)
    # create_users(hospitals)

    # Get all users for assignments
    # users = list(User.objects.all())

    # Create complaint categories first
    # categories = create_complaint_categories(hospitals)

    # Create operational data
    # complaints = create_complaints(patients, hospitals, physicians, users)
    # inquiries = create_inquiries(patients, hospitals, users)
    # feedbacks = create_feedback(patients, hospitals, physicians, users)
    # create_survey_templates(hospitals)
    # create_journey_templates(hospitals)
    # projects = create_qi_projects(hospitals)
    # actions = create_px_actions(complaints, hospitals, users)
    # journey_instances = create_journey_instances(None, patients)
    # survey_instances = create_survey_instances(None, patients, physicians)
    # call_interactions = create_call_center_interactions(patients, hospitals, users)
    # social_mentions = create_social_mentions(hospitals)
    # physician_ratings = create_physician_monthly_ratings(physicians)

    print("\n" + "="*60)
    print("Data Generation Complete!")
    print("="*60)
    print(f"\nCreated:")
    print(f"  - {len(hospitals)} Hospitals")
    print(f"  - {len(departments)} Departments")
    print(f"  - {len(staff)} Staff")
    print(f"  - {len(patients)} Patients")
    # print(f"  - {len(users)} Users")
    # print(f"  - {len(complaints)} Complaints (2 years)")
    # print(f"  - {len(inquiries)} Inquiries (2 years)")
    # print(f"  - {len(feedbacks)} Feedback Items")
    # print(f"  - {len(actions)} PX Actions")
    # print(f"  - {len(journey_instances)} Journey Instances")
    # print(f"  - {len(survey_instances)} Survey Instances")
    # print(f"  - {len(call_interactions)} Call Center Interactions")
    # print(f"  - {len(social_mentions)} Social Media Mentions")
    # print(f"  - {len(projects)} QI Projects")
    # print(f"  - {len(staff_ratings)} Staff Monthly Ratings")
    # print(f"  - {len(appreciations)} Appreciations (2 years)")
    # print(f"  - {len(user_badges)} Badges Awarded")
    # print(f"  - {len(appreciation_stats)} Appreciation Statistics")
    # print(f"  - {len(observations)} Observations (2 years)")
    print(f"\nYou can now login with:")
    print(f"  Username: px_admin")
    print(f"  Password: admin123")
    print(f"\nOr hospital admins:")
    print(f"  Username: admin_kfmc (or admin_kfsh, admin_kamc, etc.)")
    print(f"  Password: admin123")
    print(f"\nAccess the system at: http://127.0.0.1:8000/")
    print("\n")


if __name__ == '__main__':
    main()
