4.5 KiB
4.5 KiB
Complaint Categories Fix - Multi-Hospital Support
Problem
The ComplaintCategory model had a ForeignKey relationship to Hospital, which prevented categories from being shared across multiple hospitals. Each category could only belong to one hospital.
Solution
Changed the ComplaintCategory model from a ForeignKey to a ManyToMany relationship with Hospital. This allows:
- Categories to be assigned to multiple hospitals
- Categories with no hospitals (system-wide) to be available to all hospitals
- Each hospital to have its own custom categories while also accessing system-wide categories
Changes Made
1. Model Changes (apps/complaints/models.py)
- Changed
hospital = models.ForeignKey(...)tohospitals = models.ManyToManyField(...) - Removed
Meta.indexesthat referenced the old hospital field - Removed hospital-related
Meta.constraints - Updated docstrings to reflect the new relationship
2. Migration Created (apps/complaints/migrations/0003_alter_complaintcategory_options_and_more.py)
- Removes the old
hospitalfield and its index - Adds the new
hospitalsManyToMany field - Applies the changes successfully
3. Admin Interface Updated (apps/complaints/admin.py)
- Added filter_horizontal = ['hospitals'] for better UI
- Updated
hospitals_displaymethod to handle ManyToMany - Shows hospital count or "System-wide" for categories
4. Management Command Updated (apps/complaints/management/commands/load_complaint_categories.py)
- Removed hospital reference from category/subcategory creation
- Categories are now created without hospital assignments (system-wide)
- Works correctly with the ManyToMany field
5. API Endpoint Updated (apps/complaints/ui_views.py)
# Old code:
categories_queryset = ComplaintCategory.objects.filter(
Q(hospital_id=hospital_id) | Q(hospital__isnull=True),
is_active=True
).order_by('-hospital', 'order', 'name_en')
# New code:
categories_queryset = ComplaintCategory.objects.filter(
Q(hospitals__id=hospital_id) | Q(hospitals__isnull=True),
is_active=True
).distinct().order_by('order', 'name_en')
Key changes:
- Changed
hospital_id=hospital_idtohospitals__id=hospital_id - Changed
hospital__isnull=Truetohospitals__isnull=True - Added
.distinct()to remove duplicates - Removed
-hospitalfrom ordering (no longer applicable)
Testing Results
Database Verification
Total parent categories: 5
Categories with hospitals: 0
System-wide categories: 5
API Endpoint Test
Response status: 200
Categories count: 21
Sample categories:
- Cleanliness (Parent ID: 8952a7e3..., ID: 43ec2d94...) ← Subcategory
- Diagnosis concerns (Parent ID: 9e99195c..., ID: 20ce76ab...) ← Subcategory
- Privacy & Confidentiality (Parent ID: 755b053e..., ID: 564583fd...) ← Subcategory
- Quality of Care & Treatment (Parent ID: None, ID: 9e99195c...) ← Parent
- Staff attitude (Parent ID: b6302801..., ID: ffa88ba9...) ← Subcategory
How It Works
System-Wide Categories (Default)
Categories created without any hospital assignments are available to ALL hospitals:
category = ComplaintCategory.objects.create(
code='quality_care',
name_en='Quality of Care & Treatment',
# No hospitals specified → available to all
)
Hospital-Specific Categories
Categories can be assigned to specific hospitals:
from apps.organizations.models import Hospital
hospitals = Hospital.objects.filter(status='active')
category = ComplaintCategory.objects.create(
code='special_category',
name_en='Special Category'
)
category.hospitals.add(*hospitals) # Assign to multiple hospitals
Querying Categories
The API endpoint returns:
- Hospital-specific categories (assigned to the hospital)
- System-wide categories (no hospital assignment)
- Both parent categories and their subcategories
Benefits
- Flexibility: Hospitals can share common categories while maintaining custom ones
- Efficiency: No need to duplicate categories for each hospital
- Scalability: Easy to add new categories that apply to all hospitals
- Maintainability: System-wide changes can be made in one place
Future Enhancements
- Category Prioritization: Add a field to prioritize hospital-specific over system-wide categories
- Category Copying: Create a management command to copy system-wide categories to hospital-specific
- Category Versioning: Track changes to categories over time
- Category Analytics: Report on which categories are most used per hospital