Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Production Release; Aug Week 5 #1562

Merged
merged 12 commits into from
Aug 27, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 0 additions & 33 deletions .github/workflows/docs_new.yml

This file was deleted.

11 changes: 11 additions & 0 deletions care/abdm/api/serializers/health_facility.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
from rest_framework import serializers

from care.abdm.models import HealthFacility


class HealthFacilitySerializer(serializers.ModelSerializer):
id = serializers.CharField(source="external_id", read_only=True)

class Meta:
model = HealthFacility
exclude = ("deleted",)
1 change: 1 addition & 0 deletions care/abdm/api/viewsets/auth.py
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,7 @@ def post(self, request, *args, **kwargs):

AbdmGateway().data_notify(
{
"health_id": consent["notification"]["consentDetail"]["patient"]["id"],
"consent_id": data["hiRequest"]["consent"]["id"],
"transaction_id": data["transactionId"],
"care_contexts": list(
Expand Down
72 changes: 72 additions & 0 deletions care/abdm/api/viewsets/health_facility.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
from django.shortcuts import get_object_or_404
from rest_framework.mixins import (
CreateModelMixin,
ListModelMixin,
RetrieveModelMixin,
UpdateModelMixin,
)
from rest_framework.permissions import IsAuthenticated
from rest_framework.response import Response
from rest_framework.viewsets import GenericViewSet

from care.abdm.api.serializers.health_facility import HealthFacilitySerializer
from care.abdm.models import HealthFacility
from care.abdm.utils.api_call import Bridge
from care.utils.queryset.facility import get_facility_queryset


class HealthFacilityViewSet(
GenericViewSet,
CreateModelMixin,
ListModelMixin,
RetrieveModelMixin,
UpdateModelMixin,
):
serializer_class = HealthFacilitySerializer
model = HealthFacility
queryset = HealthFacility.objects.all()
permission_classes = (IsAuthenticated,)
lookup_field = "facility__external_id"

def get_queryset(self):
queryset = self.queryset
facilities = get_facility_queryset(self.request.user)
return queryset.filter(facility__in=facilities)

def get_facility(self, facility_external_id):
facilities = get_facility_queryset(self.request.user)
return get_object_or_404(facilities.filter(external_id=facility_external_id))

def link_health_facility(self, hf_id, facility_id):
facility = self.get_facility(facility_id)
return Bridge().add_update_service(
{
"id": hf_id,
"name": facility.name,
"type": "HIP",
"active": True,
"alias": ["CARE_HIP"],
}
)

def create(self, request, *args, **kwargs):
if (
self.link_health_facility(
request.data["hf_id"], request.data["facility"]
).status_code
== 200
):
return super().create(request, *args, **kwargs)

return Response({"message": "Error linking health facility"}, status=400)

def update(self, request, *args, **kwargs):
if (
self.link_health_facility(
request.data["hf_id"], kwargs["facility__external_id"]
).status_code
== 200
):
return super().update(request, *args, **kwargs)

return Response({"message": "Error linking health facility"}, status=400)
4 changes: 3 additions & 1 deletion care/abdm/api/viewsets/healthid.py
Original file line number Diff line number Diff line change
Expand Up @@ -470,7 +470,9 @@ def patient_sms_notify(self, request, *args, **kwargs):
status=status.HTTP_404_NOT_FOUND,
)

response = AbdmGateway().patient_sms_notify({"phone": patient.phone_number})
response = AbdmGateway().patient_sms_notify(
{"phone": patient.phone_number, "healthId": patient.abha_number.health_id}
)

return Response(response, status=status.HTTP_202_ACCEPTED)

Expand Down
55 changes: 55 additions & 0 deletions care/abdm/migrations/0009_healthfacility.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
# Generated by Django 4.2.2 on 2023-08-21 09:53

import uuid

import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):
dependencies = [
("facility", "0378_consultationbedasset_consultationbed_assets"),
("abdm", "0008_abhanumber_new"),
]

operations = [
migrations.CreateModel(
name="HealthFacility",
fields=[
(
"id",
models.BigAutoField(
auto_created=True,
primary_key=True,
serialize=False,
verbose_name="ID",
),
),
(
"external_id",
models.UUIDField(db_index=True, default=uuid.uuid4, unique=True),
),
(
"created_date",
models.DateTimeField(auto_now_add=True, db_index=True, null=True),
),
(
"modified_date",
models.DateTimeField(auto_now=True, db_index=True, null=True),
),
("deleted", models.BooleanField(db_index=True, default=False)),
("hf_id", models.CharField(max_length=50, unique=True)),
(
"facility",
models.OneToOneField(
on_delete=django.db.models.deletion.PROTECT,
to="facility.facility",
to_field="external_id",
),
),
],
options={
"abstract": False,
},
),
]
10 changes: 10 additions & 0 deletions care/abdm/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -35,3 +35,13 @@ class AbhaNumber(BaseModel):

def __str__(self):
return self.abha_number


class HealthFacility(BaseModel):
hf_id = models.CharField(max_length=50, unique=True)
facility = models.OneToOneField(
"facility.Facility", on_delete=models.PROTECT, to_field="external_id"
)

def __str__(self):
return self.hf_id + " " + self.facility.name
40 changes: 32 additions & 8 deletions care/abdm/utils/api_call.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

GATEWAY_API_URL = settings.ABDM_URL
HEALTH_SERVICE_API_URL = settings.HEALTH_SERVICE_API_URL
ABDM_DEVSERVICE_URL = GATEWAY_API_URL + "/devservice"
ABDM_GATEWAY_URL = GATEWAY_API_URL + "/gateway"
ABDM_TOKEN_URL = ABDM_GATEWAY_URL + "/v0.5/sessions"
ABDM_TOKEN_CACHE_KEY = "abdm_token"
Expand All @@ -42,6 +43,8 @@ def __init__(self, gateway, token):
self.url = GATEWAY_API_URL
elif gateway == "abdm_gateway":
self.url = ABDM_GATEWAY_URL
elif gateway == "abdm_devservice":
self.url = ABDM_DEVSERVICE_URL
else:
self.url = GATEWAY_API_URL
self.token = token
Expand Down Expand Up @@ -115,7 +118,7 @@ def get(self, path, params=None, auth=None):
logger.info("{} Response: {}".format(response.status_code, response.text))
return response

def post(self, path, data=None, auth=None, additional_headers=None):
def post(self, path, data=None, auth=None, additional_headers=None, method="POST"):
url = self.url + path
headers = {
"Content-Type": "application/json",
Expand All @@ -133,7 +136,7 @@ def post(self, path, data=None, auth=None, additional_headers=None):
data_json = json.dumps(data)
# logger.info("curl -X POST {} {} -d {}".format(url, headers_string, data_json))
logger.info("Posting Request to: {}".format(url))
response = requests.post(url, headers=headers, data=data_json)
response = requests.request(method, url, headers=headers, data=data_json)
logger.info("{} Response: {}".format(response.status_code, response.text))
return response

Expand Down Expand Up @@ -338,12 +341,17 @@ def verify_document_mobile_otp(self, data):
class AbdmGateway:
# TODO: replace this with in-memory db (redis)
temp_memory = {}
hip_name = "Coronasafe Care 01"
hip_id = "IN3210000017"

def __init__(self):
self.api = APIGateway("abdm_gateway", None)

def get_hip_id_by_health_id(self, health_id):
return (
AbhaNumber.objects.filter(Q(abha_number=health_id) | Q(health_id=health_id))
.first()
.patientregistration.facility.healthfacility.hf_id
)

def add_care_context(self, access_token, request_id):
if request_id not in self.temp_memory:
return
Expand Down Expand Up @@ -415,7 +423,10 @@ def fetch_modes(self, data):
"query": {
"id": data["healthId"],
"purpose": data["purpose"] if "purpose" in data else "KYC_AND_LINK",
"requester": {"type": "HIP", "id": self.hip_id},
"requester": {
"type": "HIP",
"id": self.get_hip_id_by_health_id(data["healthId"]),
},
},
}
response = self.api.post(path, payload, None, additional_headers)
Expand Down Expand Up @@ -443,7 +454,10 @@ def init(self, prev_request_id):
"id": data["healthId"],
"purpose": data["purpose"] if "purpose" in data else "KYC_AND_LINK",
"authMode": data["authMode"] if "authMode" in data else "DEMOGRAPHICS",
"requester": {"type": "HIP", "id": self.hip_id},
"requester": {
"type": "HIP",
"id": self.get_hip_id_by_health_id(data["healthId"]),
},
},
}
response = self.api.post(path, payload, None, additional_headers)
Expand Down Expand Up @@ -705,7 +719,7 @@ def data_notify(self, data):
),
"statusNotification": {
"sessionStatus": "TRANSFERRED",
"hipId": self.hip_id,
"hipId": self.get_hip_id_by_health_id(data["health_id"]),
"statusResponses": list(
map(
lambda context: {
Expand Down Expand Up @@ -753,7 +767,7 @@ def patient_sms_notify(self, data):
),
"notification": {
"phoneNo": f"+91-{data['phone']}",
"hip": {"name": self.hip_name, "id": self.hip_id},
"hip": {"id": self.get_hip_id_by_health_id(data["healthId"])},
},
}

Expand All @@ -766,3 +780,13 @@ def on_share(self, data):
additional_headers = {"X-CM-ID": settings.X_CM_ID}
response = self.api.post(path, data, None, additional_headers)
return response


class Bridge:
def __init__(self):
self.api = APIGateway("abdm_devservice", None)

def add_update_service(self, data):
path = "/v1/bridges/addUpdateServices"
response = self.api.post(path, data, method="PUT")
return response
2 changes: 1 addition & 1 deletion care/abdm/utils/fhir.py
Original file line number Diff line number Diff line change
Expand Up @@ -211,7 +211,7 @@ def _careplan(self):
else None,
),
note=[
Annotation(text=self.consultation.prescribed_medication),
Annotation(text=self.consultation.treatment_plan),
Annotation(text=self.consultation.consultation_notes),
Annotation(text=self.consultation.special_instruction),
],
Expand Down
Loading
Loading