def post(self): import api.util as util import data.crud as crud import service.assoc as assoc from models import Patient try: request_body = _get_request_body() except: return {"HTTP 400": decoding_error}, 400 if not request_body["patientId"]: return {"HTTP 400": "Patient Id is empty."}, 400 # Emulate old API functionality with new systems, use of /api/associations is # preferred over this method now patient = crud.read(Patient, patientId=request_body["patientId"]) if patient: user = util.current_user() facility = user.healthFacility if not assoc.has_association(patient, facility, user): assoc.associate(patient, facility, user) else: abort(409, message="Duplicate entry") return { "message": "patient has been added to facility successfully" }, 201 else: abort(404, message="This patient does not exist.")
def post(): json = request.get_json(force=True) # Populate the dateAssessed and healthCareWorkerId fields of the followup json["dateAssessed"] = get_current_time() user = util.current_user() json["healthcareWorkerId"] = user.id error_message = assessments.validate(json) if error_message is not None: abort(400, message=error_message) follow_up = marshal.unmarshal(FollowUp, json) # Check that reading id which doesn’t reference an existing reading in the database reading = crud.read(Reading, readingId=follow_up.readingId) if not reading: abort(404, message=f"No reading with id {follow_up.readingId}") crud.create(follow_up) # Creating an assessment also marks any referral attached to the associated # reading as "assessed" if follow_up.reading.referral: follow_up.reading.referral.isAssessed = True data.db_session.commit() return follow_up.id, 201
def post(): json = request.get_json(force=True) # Populate the dateAssessed and healthCareWorkerId fields of the followup json["dateAssessed"] = get_current_time() user = util.current_user() json["healthcareWorkerId"] = user.id error_message = assessments.validate(json) if error_message is not None: abort(400, message=error_message) # TODO: validate that assessment's reading id references an actual reading and # return 404 if it doesn't follow_up = marshal.unmarshal(FollowUp, json) crud.create(follow_up) # Creating an assessment also marks any referral attached to the associated # reading as "assessed" if follow_up.reading.referral: follow_up.reading.referral.isAssessed = True data.db_session.commit() return follow_up.id, 201
def post(): json = request.get_json(force=True) error_message = patients.validate(json) if error_message is not None: abort(400, message=error_message) patient = marshal.unmarshal(Patient, json) if crud.read(Patient, patientId=patient.patientId): abort(409, message=f"A patient already exists with id: {patient.patientId}") # Resolve invariants and set the creation timestamp for the patient ensuring # that both the created and lastEdited fields have the exact same value. invariant.resolve_reading_invariants(patient) creation_time = get_current_time() patient.created = creation_time patient.lastEdited = creation_time crud.create(patient, refresh=True) # Associate the patient with the user who created them user = util.current_user() assoc.associate_by_user_role(patient, user) # If the patient has any readings, and those readings have referrals, we # associate the patient with the facilities they were referred to for reading in patient.readings: referral = reading.referral if referral and not assoc.has_association(patient, referral.healthFacility): assoc.associate(patient, facility=referral.healthFacility) # The associate function performs a database commit, since this will # wipe out the patient we want to return we must refresh it. data.db_session.refresh(patient) return marshal.marshal(patient), 201
def get(): user = util.current_user() patients = view.patient_view_for_user(user) if util.query_param_bool(request, name="simplified"): # TODO: Compute simplified view for each patient return [] else: return [marshal.marshal(p) for p in patients]
def get(): user = util.current_user() referrals = view.referral_view_for_user(user) # If the request does not specifically specify "all=true", then only return the # referrals which have not been assessed. if not util.query_param_bool(request, "all"): referrals = [r for r in referrals if not r.isAssessed] return [marshal.marshal(r) for r in referrals]
def post(): # Get all patients for this user timestamp: int = request.args.get("since", None, type=int) if not timestamp: abort(400, message="'since' query parameter is required") # ~~~~~~~~~~~~~~~~~~~~~~ new Logic ~~~~~~~~~~~~~~~~~~~~~~~~~~ json = request.get_json(force=True) patients_on_server_chache = set() for r in json: if r.get("patientId") not in patients_on_server_chache: patient_on_server = crud.read(Patient, patientId=r.get("patientId")) if patient_on_server is None: continue else: patients_on_server_chache.add(patient_on_server.patientId) if crud.read(Reading, readingId=r.get("readingId")): continue else: error_message = readings.validate(r) if error_message is not None: abort(400, message=error_message) reading = marshal.unmarshal(Reading, r) invariant.resolve_reading_invariants(reading) crud.create(reading, refresh=True) user = util.current_user() # TODO: create custome DB calls for referral and followup all_patients = view.patient_view_for_user(user) new_readings = [] new_referral = [] new_followup = [] for p in all_patients: for r in p["readings"]: if r["dateTimeTaken"] > timestamp: new_readings.append(r) if (r["referral"] and r["referral"]["dateReferred"] > timestamp and r["dateTimeTaken"] < timestamp): new_referral.append(r["referral"]) if (r["followup"] and r["followup"]["dateAssessed"] > timestamp and r["dateTimeTaken"] < timestamp): new_followup.append(r["followup"]) return { "total": len(new_readings) + len(new_referral) + len(new_followup), "readings": new_readings, "newReferralsForOldReadings": new_referral, "newFollowupsForOldReadings": new_followup, }
def get(): timestamp: int = request.args.get("since", None, type=int) if not timestamp: abort(400, message="'since' query parameter is required") # Get all patients for this user user = util.current_user() all_patients = view.patient_view_for_user(user) # New patients are patients who are created after the timestamp new_patients = [ p.patientId for p in all_patients if p.created > timestamp ] # Edited patients are patients who were created before the timestamp but # edited after it edited_patients = [ p.patientId for p in all_patients if p.created < p.lastEdited and p.created <= timestamp < p.lastEdited ] # New readings created after the timestamp for patients who where created before # the timestamp readings = [] # New followups which were created after the timestamp for readings which were # created before the timestamp followups = [] for p in all_patients: for r in p.readings: r_time = int(r.dateTimeTaken) if p.created <= timestamp < r_time: readings.append(r.readingId) if r.followup and r_time < timestamp < int( r.followup.dateAssessed): followups.append(r.followup.id) return { "newPatients": new_patients, "editedPatients": edited_patients, "readings": readings, "followups": followups, }
def get(): user = util.current_user() limit = util.query_param_limit(request, name="limit") page = util.query_param_page(request, name="page") sort_by = util.query_param_sortBy(request, name="sortBy") sort_dir = util.query_param_sortDir(request, name="sortDir") search = util.query_param_search(request, name="search") referrals = view.referral_view_for_user( user, limit=limit, page=page, sortBy=sort_by, sortDir=sort_dir, search=search, ) return [serialize.serialize_referral(r) for r in referrals]
def post(): json: dict = request.get_json(force=True) error_message = associations.validate(json) if error_message is not None: abort(400, message=error_message) patient_id = json.get("patientId") facility_name = json.get("healthFacilityName") user_id = json.get("userId") patient = crud.read(Patient, patientId=patient_id) if not patient: abort(400, message=f"No patient exists with id: {patient_id}") if facility_name: facility = crud.read(HealthFacility, healthFacilityName=facility_name) if not facility: abort(400, message=f"No health facility with name: {facility_name}") else: facility = None if user_id: user = crud.read(User, id=user_id) if not user: abort(400, message=f"No user with id: {user_id}") # if user exists but no health facility then assign the patient to the user's health facility facility = user.healthFacility else: user = None if not facility_name and not user_id: # If neither facility_name or user_id are present in the request, create a # associate patient with the current user's health facility user = util.current_user() assoc.associate(patient, user.healthFacility, user) else: # Otherwise, simply associate the provided models together if not assoc.has_association(patient, facility, user): assoc.associate(patient, facility, user) return {}, 201
def get(): user = util.current_user() # query parameters for later SQL use limit = util.query_param_limit(request, name="limit") page = util.query_param_page(request, name="page") sort_by = util.query_param_sortBy(request, name="sortBy") sort_dir = util.query_param_sortDir(request, name="sortDir") search = util.query_param_search(request, name="search") patients = view.patient_view_for_user( user, limit=limit, page=page, sortBy=sort_by, sortDir=sort_dir, search=search, ) # create JSON format return [serialize.serialize_patient(p) for p in patients]
def post(assessment_id: int): if not assessment_id: abort(404, message=f"Assessment id is required") json = request.get_json(force=True) json["dateAssessed"] = get_current_time() # get current UserID user = util.current_user() json["healthcareWorkerId"] = user.id assessment = crud.read(FollowUp, id=assessment_id) if not assessment: abort(404, message=f"No assessment with id {assessment_id}") json["readingId"] = assessment.readingId error_message = assessments.validate(json) if error_message is not None: abort(400, message=error_message) crud.update(FollowUp, json, id=assessment.id) return assessment.id, 201
def post(): # Get all patients for this user user = util.current_user() timestamp: int = request.args.get("since", None, type=int) if not timestamp: abort(400, message="'since' query parameter is required") patients_to_be_added: [Patient] = [] # ~~~~~~~~~~~~~~~~~~~~~~ new Logic ~~~~~~~~~~~~~~~~~~~~~~~~~~ json = request.get_json(force=True) for p in json: patient_on_server = crud.read(Patient, patientId=p.get("patientId")) if patient_on_server is None: error_message = patients.validate(p) if error_message is not None: abort(400, message=error_message) patient = marshal.unmarshal(Patient, p) # # Resolve invariants and set the creation timestamp for the patient ensuring # # that both the created and lastEdited fields have the exact same value. invariant.resolve_reading_invariants_mobile(patient) creation_time = get_current_time() patient.created = creation_time patient.lastEdited = creation_time patients_to_be_added.append(patient) else: if (int(patient_on_server.lastEdited) < int( p.get("lastEdited")) < timestamp): if p.get("base"): if p.get("base") != p.get("lastEdited"): abort( 409, message= "Unable to merge changes, conflict detected", ) del p["base"] p["lastEdited"] = get_current_time() crud.update(Patient, p, patientId=p["patientId"]) # TODO: revisit association logic if not assoc.has_association(patient_on_server, user=user): assoc.associate(patient_on_server, user.healthFacility, user) # update association if patients_to_be_added: crud.create_all_patients(patients_to_be_added) for new_patient in patients_to_be_added: # TODO: revisit association logic if not assoc.has_association(new_patient, user=user): assoc.associate(new_patient, user.healthFacility, user) # read all the patients from the DB # TODO: optimize to get only patients all_patients = view.patient_view_for_user(user) all_patients_edited_or_new = [ p for p in all_patients if p["lastEdited"] > timestamp ] # ~~~~~~~~~~~~~~~~~ old logic ~~~~~~~~~~~~~~~~~~~~ # New patients are patients who are created after the timestamp # new_patients = [ # p["patientId"] for p in all_patients if p["created"] > timestamp # ] # Edited patients are patients who were created before the timestamp but # edited after it # edited_patients = [ # p["patientId"] # for p in all_patients # if p["created"] < p["lastEdited"] # and p["created"] <= timestamp < p["lastEdited"] # ] # New readings created after the timestamp for patients who where created before # the timestamp # readings = [] # New followups which were created after the timestamp for readings which were # created before the timestamp # followups = [] # # for p in all_patients: # for r in p["readings"]: # r_time = int(r["dateTimeTaken"]) # if p["created"] <= timestamp < r_time: # readings.append(r["readingId"]) # # if r["followup"] and r_time < timestamp < int( # r["followup"]["dateAssessed"] # ): # followups.append(r["followup"]["id"]) return { "total": len(all_patients_edited_or_new), "patients": all_patients_edited_or_new, }
def get(): user = util.current_user() patients = view.patient_view_for_user(user) return patients, 200