Skip to content

Commit

Permalink
add list and detail serializer for consultation bed
Browse files Browse the repository at this point in the history
  • Loading branch information
GeekGawd committed Jul 11, 2023
1 parent 2cdf17c commit 806d88e
Show file tree
Hide file tree
Showing 3 changed files with 135 additions and 4 deletions.
125 changes: 125 additions & 0 deletions care/facility/api/serializers/bed.py
Original file line number Diff line number Diff line change
Expand Up @@ -174,8 +174,133 @@ class Meta:


class ConsultationBedSerializer(ModelSerializer):
# Remove when issue #5492 is complete
id = UUIDField(source="external_id", read_only=True)

bed_object = BedDetailSerializer(source="bed", read_only=True)

consultation = ExternalIdSerializerField(
queryset=PatientConsultation.objects.all(), write_only=True, required=True
)
bed = ExternalIdSerializerField(
queryset=Bed.objects.all(), write_only=True, required=True
)

class Meta:
model = ConsultationBed
exclude = ("deleted", "external_id")
read_only_fields = TIMESTAMP_FIELDS

def validate(self, attrs):
user = self.context["request"].user
if "consultation" in attrs and "bed" in attrs and "start_date" in attrs:
bed = attrs["bed"]
facilities = get_facility_queryset(user)
permitted_consultations = get_consultation_queryset(user)
consultation = get_object_or_404(
permitted_consultations.filter(id=attrs["consultation"].id)
)
if not facilities.filter(id=bed.facility.id).exists():
raise PermissionError()
if consultation.facility.id != bed.facility.id:
raise ValidationError(
{"consultation": "Should be in the same facility as the bed"}
)
start_date = attrs["start_date"]
end_date = attrs.get("end_date", None)
existing_qs = ConsultationBed.objects.filter(
consultation=consultation, bed=bed
)
qs = ConsultationBed.objects.filter(consultation=consultation)
# Validations based of the latest entry
if qs.exists():
latest_qs = qs.latest("id")
if latest_qs.bed == bed:
raise ValidationError({"bed": "Bed is already in use"})
if start_date < latest_qs.start_date:
raise ValidationError(
{
"start_date": "Start date cannot be before the latest start date"
}
)
if end_date and end_date < latest_qs.start_date:
raise ValidationError(
{"end_date": "End date cannot be before the latest start date"}
)
existing_qs = ConsultationBed.objects.filter(consultation=consultation)
# Conflict checking logic
if existing_qs.filter(start_date__gt=start_date).exists():
raise ValidationError({"start_date": "Cannot create conflicting entry"})
if end_date:
if existing_qs.filter(
start_date__gt=end_date, end_date__lt=end_date
).exists():
raise ValidationError(
{"end_date": "Cannot create conflicting entry"}
)
else:
raise ValidationError(
{
"consultation": "Field is Required",
"bed": "Field is Required",
"start_date": "Field is Required",
}
)
return super().validate(attrs)

def create(self, validated_data):
consultation = validated_data["consultation"]
bed = validated_data["bed"]

if not consultation.patient.is_active:
raise ValidationError(
{"patient:": ["Patient is already discharged from CARE"]}
)

occupied_beds = ConsultationBed.objects.filter(end_date__isnull=True)

if occupied_beds.filter(bed=bed).exists():
raise ValidationError({"bed:": ["Bed already in use by patient"]})

occupied_beds.filter(consultation=consultation).update(
end_date=validated_data["start_date"]
)

# This needs better logic, when an update occurs and the latest bed is no longer the last bed consultation relation added.
obj = super().create(validated_data)
consultation.current_bed = obj
consultation.save(update_fields=["current_bed"])
return obj


class BareMinimumAssetLocationSerializer(ModelSerializer):
class Meta:
model = AssetLocation
fields = ["id", "name"]


class BareMinimumBedSerializer(ModelSerializer):
location_object = BareMinimumAssetLocationSerializer(
source="location", read_only=True
)

class Meta:
model = Bed
fields = ["id", "name", "location_object"]


class ConsulationBedListSerializer(ModelSerializer):
id = UUIDField(source="external_id", read_only=True)

bed_object = BareMinimumBedSerializer(source="bed", read_only=True)

class Meta:
model = ConsultationBed
fields = ["id", "bed_object", "start_date", "end_date"]
read_only_fields = TIMESTAMP_FIELDS


class ConsultationBedDetailSerializer(ConsulationBedListSerializer):
bed_object = BedDetailSerializer(source="bed", read_only=True)

consultation = ExternalIdSerializerField(
Expand Down
4 changes: 2 additions & 2 deletions care/facility/api/serializers/patient_consultation.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
from rest_framework.exceptions import ValidationError

from care.facility.api.serializers import TIMESTAMP_FIELDS
from care.facility.api.serializers.bed import ConsultationBedSerializer
from care.facility.api.serializers.bed import ConsultationBedDetailSerializer
from care.facility.api.serializers.daily_round import DailyRoundSerializer
from care.facility.api.serializers.facility import FacilityBasicInfoSerializer
from care.facility.models import (
Expand Down Expand Up @@ -91,7 +91,7 @@ class PatientConsultationSerializer(serializers.ModelSerializer):
created_by = UserBaseMinimumSerializer(read_only=True)
last_daily_round = DailyRoundSerializer(read_only=True)

current_bed = ConsultationBedSerializer(read_only=True)
current_bed = ConsultationBedDetailSerializer(read_only=True)

bed = ExternalIdSerializerField(queryset=Bed.objects.all(), required=False)

Expand Down
10 changes: 8 additions & 2 deletions care/facility/api/viewsets/bed.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,8 @@
AssetBedSerializer,
BedDetailSerializer,
BedListSerializer,
ConsultationBedSerializer,
ConsulationBedListSerializer,
ConsultationBedDetailSerializer,
PatientAssetBedSerializer,
)
from care.facility.models.bed import AssetBed, Bed, ConsultationBed
Expand Down Expand Up @@ -193,11 +194,16 @@ class ConsultationBedViewSet(
.select_related("consultation", "bed")
.order_by("-created_date")
)
serializer_class = ConsultationBedSerializer
serializer_class = ConsultationBedDetailSerializer
filter_backends = (filters.DjangoFilterBackend,)
filterset_class = ConsultationBedFilter
lookup_field = "external_id"

def get_serializer_class(self):
if self.action == "list":
return ConsulationBedListSerializer
return self.serializer_class

def get_queryset(self):
user = self.request.user
queryset = self.queryset
Expand Down

0 comments on commit 806d88e

Please sign in to comment.