173 lines
5.8 KiB
Python
173 lines
5.8 KiB
Python
"""
|
|
Diagnostic script to check staff hierarchy data
|
|
"""
|
|
import os
|
|
import sys
|
|
import django
|
|
|
|
# Setup Django
|
|
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'PX360.settings')
|
|
sys.path.insert(0, '/home/ismail/projects/HH')
|
|
django.setup()
|
|
|
|
from apps.organizations.models import Staff, Hospital, Department
|
|
from django.db.models import Count, Q
|
|
|
|
print("=" * 80)
|
|
print("STAFF HIERARCHY DIAGNOSTIC REPORT")
|
|
print("=" * 80)
|
|
|
|
# 1. Check if staff data exists
|
|
print("\n1. STAFF DATA CHECK")
|
|
print("-" * 80)
|
|
total_staff = Staff.objects.count()
|
|
print(f"Total staff members in database: {total_staff}")
|
|
|
|
if total_staff == 0:
|
|
print("\n❌ NO STAFF DATA FOUND")
|
|
print(" The staff hierarchy cannot be displayed because no staff data exists.")
|
|
print(" Please import staff data using:")
|
|
print(" python manage.py import_staff_csv sample_staff_data.csv --hospital-code ALH")
|
|
sys.exit(0)
|
|
|
|
# Check active staff
|
|
active_staff = Staff.objects.filter(status='active').count()
|
|
print(f"Active staff members: {active_staff}")
|
|
|
|
# 2. Check manager relationships
|
|
print("\n2. MANAGER RELATIONSHIP CHECK")
|
|
print("-" * 80)
|
|
with_manager = Staff.objects.filter(report_to__isnull=False).count()
|
|
without_manager = total_staff - with_manager
|
|
|
|
print(f"Staff WITH manager assigned: {with_manager}")
|
|
print(f"Staff WITHOUT manager assigned: {without_manager}")
|
|
|
|
if with_manager == 0:
|
|
print("\n⚠️ WARNING: No staff have manager relationships assigned")
|
|
print(" The hierarchy requires staff to have report_to relationships set.")
|
|
|
|
# 3. Check for broken relationships
|
|
print("\n3. BROKEN RELATIONSHIP CHECK")
|
|
print("-" * 80)
|
|
broken_relationships = Staff.objects.exclude(report_to__isnull=True).exclude(
|
|
report_to__in=Staff.objects.all()
|
|
).count()
|
|
|
|
print(f"Staff with broken manager references: {broken_relationships}")
|
|
|
|
if broken_relationships > 0:
|
|
print("\n⚠️ WARNING: Found staff with references to non-existent managers")
|
|
broken_staff = Staff.objects.exclude(report_to__isnull=True).exclude(
|
|
report_to__in=Staff.objects.all()
|
|
).select_related('report_to')[:5]
|
|
print(" Examples:")
|
|
for staff in broken_staff:
|
|
print(f" - {staff.name} (ID: {staff.employee_id}) references manager ID: {staff.report_to_id}")
|
|
|
|
# 4. Check hospital and department assignments
|
|
print("\n4. ORGANIZATION STRUCTURE CHECK")
|
|
print("-" * 80)
|
|
hospitals = Hospital.objects.count()
|
|
departments = Department.objects.count()
|
|
|
|
print(f"Hospitals: {hospitals}")
|
|
print(f"Departments: {departments}")
|
|
|
|
staff_with_hospital = Staff.objects.filter(hospital__isnull=False).count()
|
|
staff_with_department = Staff.objects.filter(department__isnull=False).count()
|
|
|
|
print(f"Staff with hospital assigned: {staff_with_hospital}")
|
|
print(f"Staff with department assigned: {staff_with_department}")
|
|
|
|
# 5. Analyze hierarchy structure
|
|
print("\n5. HIERARCHY STRUCTURE ANALYSIS")
|
|
print("-" * 80)
|
|
|
|
# Find potential root nodes (no manager OR manager not in same hospital)
|
|
all_staff_ids = set(Staff.objects.values_list('id', flat=True))
|
|
root_candidates = Staff.objects.filter(
|
|
Q(report_to__isnull=True) | ~Q(report_to__in=all_staff_ids)
|
|
)
|
|
|
|
print(f"Potential root nodes (no manager or manager outside set): {root_candidates.count()}")
|
|
|
|
# Count staff by hierarchy level
|
|
print("\nStaff by number of direct reports:")
|
|
report_counts = Staff.objects.annotate(
|
|
report_count=Count('direct_reports')
|
|
).values('report_count').annotate(count=Count('id')).order_by('-report_count')
|
|
|
|
for rc in report_counts:
|
|
count = rc['report_count']
|
|
num_staff = rc['count']
|
|
label = f"{count} reports" if count > 0 else "No reports (leaf nodes)"
|
|
print(f" {label}: {num_staff}")
|
|
|
|
# 6. Sample hierarchy data
|
|
print("\n6. SAMPLE HIERARCHY DATA")
|
|
print("-" * 80)
|
|
sample_staff = Staff.objects.select_related('report_to', 'hospital', 'department')[:5]
|
|
|
|
for staff in sample_staff:
|
|
manager_info = f"→ {staff.report_to.name}" if staff.report_to else "(No manager)"
|
|
print(f"{staff.name} ({staff.employee_id}) {manager_info}")
|
|
print(f" Hospital: {staff.hospital.name if staff.hospital else 'None'}")
|
|
print(f" Department: {staff.department.name if staff.department else 'None'}")
|
|
print()
|
|
|
|
# 7. Test hierarchy building logic
|
|
print("\n7. HIERARCHY BUILDING TEST")
|
|
print("-" * 80)
|
|
staff_list = list(Staff.objects.select_related('report_to'))
|
|
staff_dict = {staff.id: staff for staff in staff_list}
|
|
|
|
# Find root nodes (matching API logic)
|
|
root_staff = [
|
|
staff for staff in staff_list
|
|
if staff.report_to_id is None or staff.report_to_id not in staff_dict
|
|
]
|
|
|
|
print(f"Root nodes detected by API logic: {len(root_staff)}")
|
|
|
|
if root_staff:
|
|
print("\nRoot nodes:")
|
|
for i, staff in enumerate(root_staff[:10], 1):
|
|
# Count total team size
|
|
def count_team(staff_id):
|
|
count = 1
|
|
reports = [s for s in staff_list if s.report_to_id == staff_id]
|
|
for r in reports:
|
|
count += count_team(r.id)
|
|
return count
|
|
|
|
team_size = count_team(staff.id)
|
|
print(f" {i}. {staff.name} (ID: {staff.employee_id}) - Team size: {team_size}")
|
|
|
|
# 8. Summary and recommendations
|
|
print("\n" + "=" * 80)
|
|
print("DIAGNOSTIC SUMMARY")
|
|
print("=" * 80)
|
|
|
|
issues = []
|
|
if total_staff == 0:
|
|
issues.append("❌ No staff data exists")
|
|
elif with_manager == 0:
|
|
issues.append("❌ No manager relationships assigned")
|
|
elif broken_relationships > 0:
|
|
issues.append(f"⚠️ {broken_relationships} broken manager references")
|
|
elif len(root_staff) == 0:
|
|
issues.append("❌ No root nodes found in hierarchy")
|
|
elif len(root_staff) > 10:
|
|
issues.append(f"⚠️ Many disconnected hierarchies ({len(root_staff)} root nodes)")
|
|
|
|
if issues:
|
|
print("\nISSUES FOUND:")
|
|
for issue in issues:
|
|
print(f" {issue}")
|
|
else:
|
|
print("\n✓ No critical issues detected")
|
|
print(" Staff data exists and hierarchy structure appears valid")
|
|
|
|
print("\n" + "=" * 80)
|