Meerkat API

Meerkat API gives access to the data processed by meerkat abacus. It is build using flask and communicates with DB setup by Abacus. The main functionality is to aggregate data over time and location and give access to all the variables and locations in the DB. The API provides all the data for Meerkat Frontend and could be accessed by other applications. Access is granted through the meerkat_auth module.

We use flaskRESTful to create the API and flask-sqlalchemy to access the db

Structure

__init__.py - Basic intiailisation of flaks ap

app.py - Initialises flask extensions

extensions.py - Defines flask extensions

authentication.py - Methods for authentication

util/__init__.py - Various utility methods

util/data_query.py - Main utility for aggregating data over time and location

resources/: Folder containing the following files:

  • locations.py - Location information including a location tree
  • variables.py - Access to all the variables used in Abacus
  • data.py - Aggregated data over time and locations
  • alerts.py - Access to alerts and alert_investigations
  • epi_week.py - Calculating epi weeks
  • incidence.py - Calculating incidence rates.
  • explore.py - Functinality for displaying cross tables and timelines
  • export_data.py - Exports data as csv (run in the background as a celery task)
  • map.py - Mapping different data
  • indicators.py - Calculate timeline indicators
  • incidence.py - Calculate incidence rates
  • prescriptions.py - Calculating prescriptions used and remaining stock
  • reports.py - Data for specified reports
  • completeness.py - Calculating completeness of reporting
  • frontpage.py - High level information

Config

The API key needs to specified in a file pointed to by the environmental variable MEERKAT_API_SETTINGS. Authentication is handled by the meerkat_auth module.

API urls

GET /export/forms

Return a dict of forms with all their columns

Returns:

forms: dict of forms with all their variables
GET /export/data/(use_loc_ids)
GET /export/data

Export data table from db

Starts generation of data file

Args:
use_loc_ids: If we use names are location ids

Returns:

uuid
GET /aggregate_alerts/(central_review)/(hard_date_limit)
GET /aggregate_alerts/(central_review)
GET /aggregate_alerts

Aggregates all alerts based on reason and status in the following format:

{reason: {status_1: Number, status_2: Number}, reason2: …. , total: total_alerts}

Returns:

alerts(dict): Aggregagated alerts by reason and status
GET /consultation_map/(int: location)
GET /consultation_map

Map the total number of consultations

GET /key_indicators/(int: location)
GET /key_indicators

Get the aggregation for all time of the variables with the key_indicators category.

GET /locationtree

Location Tree

Accepts optional GET args:
inc_case_types - A JSON list of case types to filter the location Tree
by. A location is only included in the tree if there is an intersection between this list and the locations case_type list. Used when viewing e.g. PIP data - the user is only interested in viewing clinics/locations that are actually submitting PIP data.
exc_case_types - A JSON list of case types to filter the location tree
by. In a similar, but opposite, way to inc_case_types, a location is only included in the tree if there is NO intersection between this list and the location’s case_type list.
Args:
only_case_reports: Only include clinics that submit case reports
Returns:
Returns a location Tree
GET /refugee_page

Map and key indicators for the Refugee page

GET /num_clinics/(int: location)
GET /num_clinics

Return the total number of clinics for the country

GET /num_alerts/(int: location)
GET /num_alerts

Total Number of Alerts

GET /locations

List all Locations

Params:

deviceId: return locations for a given deviceId

Returns:

locations: Locations indexed by location_id
GET /epi_week/(date)
GET /epi_week

Get epi week of date(defaults to today)

Args:

date: date to get epi-week

Returns:

epi-week: epi-week
GET /tot_map/(int: location)
GET /tot_map

We map the total number of cases

GET /devices

Get devices in the inventory

Returns:

devices
GET /alerts

Get alert all alerts

Takes url arguments to restrict the returned alerts

reason: restricts by variable

location: restricts by location

only_latest: returns only the latest alerts

Returns:

alerts
GET /non_reporting/(variable)/(location)/(num_weeks)/(exclude_case_type)/(include_case_type)/(include_clinic_type)/(require_case_report)
GET /non_reporting/(variable)/(location)/(num_weeks)/(exclude_case_type)/(include_case_type)
GET /non_reporting/(variable)/(location)/(num_weeks)/(exclude_case_type)
GET /non_reporting/(variable)/(location)

Returns all non-reporting clinics for the last num_weeks complete epi weeks.

Args:

variable: variable_id

location: location

exclude_case_type: Exclude locations with this case_type

num_weeks: number_of_weeks

Returns:

list_of_clinics
GET /completeness/(variable)/(location)/(number_per_week)/(start_week)/(weekend)/(non_reporting_variable)/(end_date)
GET /completeness/(variable)/(location)/(number_per_week)/(start_week)/(weekend)/(non_reporting_variable)
GET /completeness/(variable)/(location)/(number_per_week)/(start_week)/(weekend)
GET /completeness/(variable)/(location)/(number_per_week)/(start_week)
GET /completeness/(variable)/(location)/(number_per_week)

Return completeness data of variable. We calculate both a score based on the average of the last two epi weeks and a timeline of the average number of records per week. We only allow one record per day.

We include_case_type data for both the given location and the sublocations.

Args:

variable: variable_id

location: location id number_per_week: expected number per week

argument weekend, specify exclude_case_type as a string None

weekend: specified weekend days in a comma separated string 0=Mon.

Returns:

completness data: {score: score, timeline: timeline, clinic_score: clinic:score, clinic_yearly_score: clinic:yearly_score, dates_not_reported: dated_not_reported, yearly_score: yearly_score}
GET /aggregate_latest_category/(category)/(identifier_id)/(location_id)/(weeks)/(year)
GET /aggregate_latest_category/(category)/(identifier_id)/(location_id)/(weeks)
GET /aggregate_latest_category/(category)/(identifier_id)/(location_id)

Get total and weekly aggregate for a year for all variables with a given category. Only aggregate over the given location.

Args:

category: category

location: location_id

year: year

lim_variable: limit results to those with this variable

Returns:

result_dict: {variable_id: AggregateYear result_dict}
GET /aggregate_latest_level/(variable_id)/(identifier_id)/(level)/(weekly)/(location_id)
GET /aggregate_latest_level/(variable_id)/(identifier_id)/(level)/(weekly)
GET /aggregate_latest_level/(variable_id)/(identifier_id)/(level)

Get total and weekly aggregate for the current year for the given variable and location. Can get data for other years by useing the year keyword argument.

Args:

variable: variable_id

location: location_id

year: year (defaults to current year)

Reutrns:

result_dict: {“weeks”:{1:0….}, “year”:0}
GET /aggregate_latest_year/(variable_id)/(identifier_id)/(location_id)/(weeks)/(year)
GET /aggregate_latest_year/(variable_id)/(identifier_id)/(location_id)/(weeks)
GET /aggregate_latest_year/(variable_id)/(identifier_id)/(location_id)

Get total and weekly aggregate for the current year for the given variable and location. Can get data for other years by useing the year keyword argument.

Args:

variable: variable_id

location: location_id

year: year (defaults to current year)

Reutrns:

result_dict: {“weeks”:{1:0….}, “year”:0}
GET /incidence_rate/(variable_id)/(level)/(mult_factor)/(year)/(monthly)
GET /incidence_rate/(variable_id)/(level)/(mult_factor)/(year)
GET /incidence_rate/(variable_id)/(level)/(mult_factor)
GET /incidence_rate/(variable_id)/(level)

Calculate the incidence rate for level and variable id

Args:

variable: variable_id

level: clinic,district or region

Returns:

result: {“value”: value}
GET /query_category/(group_by1)/(group_by2)/(start_date)/(end_date)/(only_loc)
GET /query_category/(group_by1)/(group_by2)/(start_date)/(end_date)
GET /query_category/(group_by1)/(group_by2)/(only_loc)
GET /query_category/(group_by1)/(group_by2)

Create a contingency table with category1 x category2. Start and end data gives option to specifiy time period.

We first construct the conditions for our database query. Need to take special care if any of the categories are locations locations as they need to be handeld differently. We then do the db-query and then assemble the return dictionary

Args:

variable: the variable all records need to fulfill

group_by: category to group by

start_date: start date

end_date: end_date

only_loc: restrict data to only this location

Returns:

data: {variable_11: {variable_21: number, variable_22: number …},
variable_12: {….
GET /indicators/(flags)/(variables)/(location)/(start_date)/(end_date)
GET /indicators/(flags)/(variables)/(location)

Return a value and a timeline of an indicator specified by a list of variables and flags.

Args:

flags: A list containings char flags defining operations on variables.
d - denominator of an indicator, n - nominator, v - additional variable to restrict query. r - restrict ` count_over_count` query if set to 1

variables: A list of variables id to which flags correspond

location: location id

Returns:

indicator_data:
{cummulative: cummulative, timeline: timeline, current: current}
GET /export/category/(form_name)/(category)/(download_name)/(data_type)
GET /export/category/(form_name)/(category)/(download_name)

Export cases from case form that matches a category

Starts generation of data file Args:

category: category to match

variables: variable dictionary

Returns:

uuid
GET /aggregate_category_sum/(category)/(location_id)/(year)/(lim_variables)
GET /aggregate_category_sum/(category)/(location_id)/(year)
GET /aggregate_category_sum/(category)/(location_id)

This function does the same as AggregateCategory. Get total and weekly aggregate for a year for all variables with a given category. Only aggregate over the given location. It gives the same output as AggregateCategory() and is better suited if variables within a category are overlapping.

Args:

category: category

location: location_id

year: year

lim_variable: limit results to those with this variable

Returns:

result_dict: {variable_id: AggregateYear result_dict}
GET /aggregate_category/(category)/(location_id)/(year)/(lim_variables)
GET /aggregate_category/(category)/(location_id)/(year)
GET /aggregate_category/(category)/(location_id)

Get total and weekly aggregate for a year for all variables with a given category. Only aggregate over the given location. It is faster than AggregateCategorySum() if each variable in the categories are mutually exclusive (for instance for gender) but gives exactly the same output. Args:

category: category

location: location_id

year: year

lim_variables: limit results to those with this variable

Returns:

result_dict: {variable_id: AggregateYear result_dict}
GET /weekly_incidence/(variable_id)/(loc_id)/(year)/(mult_factor)
GET /weekly_incidence/(variable_id)/(loc_id)/(year)
GET /weekly_incidence/(variable_id)/(loc_id)

Calculate the incidence rate for level and variable id

Args:

variable: variable_id
X
level: clinic,district or region

Returns:

result: {“value”: value}
GET /query_variable/(variable)/(group_by)/(start_date)/(end_date)
GET /query_variable/(variable)/(group_by)

Create a table where all records have the variable, and is broken down by group_by. Start and end data gives option to specifiy time period

We first construct the conditions for our database query. Need to take special care if the variable or the group_by is given in terms of locations as they need to be handeld differently. We then do the db-query and then assemble the return dictionary

Args:

variable: the variable all records need to fulfill

group_by: category to group by

start_date: start date

end_date: end_date

only_loc: If given retricts the data to that location

use_ids: If use_ids is true we use variable_ids and not the
name as keys for the return
additional_variables: a list of variable string id’s to
include in the filter conditions

Returns:

data: {variable_1: {total: X, weeks: {12:X,13:X}}….}
GET /reports/refugee_public_health/(location)/(end_date)/(start_date)
GET /reports/refugee_public_health/(location)/(end_date)
GET /reports/refugee_public_health/(location)

Refugee Public Health Profile Report

This reports gives an overview summary over the refugee data from the project Including NCD, Mental Health, CD, Injuries, reporting locations and demographics.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/cd_public_health_mad/(location)/(end_date)/(start_date)
GET /reports/cd_public_health_mad/(location)/(end_date)
GET /reports/cd_public_health_mad/(location)

Public Health Profile Report for Communicable Diseases

This reports gives an overview summary over the CD data from the project Including disease brekdowns reporting locations and demographics

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/cd_public_health_som/(location)/(end_date)/(start_date)
GET /reports/cd_public_health_som/(location)/(end_date)
GET /reports/cd_public_health_som/(location)

Public Health Profile Report for Communicable Diseases

This reports gives an overview summary over the CD data from the project Including disease brekdowns reporting locations and demographics

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/foreigner_screening/(location)/(end_date)/(start_date)
GET /reports/foreigner_screening/(location)/(end_date)
GET /reports/foreigner_screening/(location)

Foreigner Screening Report

Provides breakdown of positive test results for specified screening of foreigners intending to stay in the country.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/ncd_public_health/(location)/(end_date)/(start_date)
GET /reports/ncd_public_health/(location)/(end_date)
GET /reports/ncd_public_health/(location)

Public Health Profile Report for Non-Communicable Diseases

This reports gives an overview summary over the NCD data from the project Including disease brekdowns reporting locations and demographics

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/cd_public_health/(location)/(end_date)/(start_date)
GET /reports/cd_public_health/(location)/(end_date)
GET /reports/cd_public_health/(location)

Public Health Profile Report for Communicable Diseases

This reports gives an overview summary over the CD data from the project Including disease brekdowns reporting locations and demographics

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/refugee_detail/(location)/(end_date)/(start_date)
GET /reports/refugee_detail/(location)/(end_date)
GET /reports/refugee_detail/(location)

Refugee Detailed Report

This reports gives detailed tables on all aspects of the refugee data

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/epi_monitoring/(location)/(end_date)/(start_date)
GET /reports/epi_monitoring/(location)/(end_date)
GET /reports/epi_monitoring/(location)

Weekly Epi Monitoring or “Rapport de Surveillance Epidémiologique Hebdomadaire”

This reports gives detailed tables on all aspects the epidiemiological data. As requested by Madagascar.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/public_health/(location)/(end_date)/(start_date)
GET /reports/public_health/(location)/(end_date)
GET /reports/public_health/(location)

Public Health Profile Report

This reports gives an overview summary over the data from the project Including NCD, Mental Health, CD, Injuries, reporting locations and demographics

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/vaccination/(location)/(end_date)/(start_date)
GET /reports/vaccination/(location)/(end_date)
GET /reports/vaccination/(location)

Vaccination Report or “Vaccination de Routine”

This reports gives detailed tables on aspects concerning vaccination sessions. As requested by Madagascar.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/refugee_cd/(location)/(end_date)/(start_date)
GET /reports/refugee_cd/(location)/(end_date)
GET /reports/refugee_cd/(location)

Refugee CD Report

Gives timelines for the refugee CD cases

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/cd_report/(location)/(end_date)/(start_date)
GET /reports/cd_report/(location)/(end_date)
GET /reports/cd_report/(location)

Communicable Disease Report

This report includes data on all disease that generate alerts. For each of these diseases we generate a timeline of the number of cases per week. We split these cases into supected and confrimed cases and only show data for disease where there at least one case.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/mh_report/(location)/(end_date)/(start_date)
GET /reports/mh_report/(location)/(end_date)
GET /reports/mh_report/(location)

Mental Health Report to show data on all mental health related diseases and visits.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/malaria/(location)/(end_date)/(start_date)
GET /reports/malaria/(location)/(end_date)
GET /reports/malaria/(location)

Malaria Report or “Rapport de Surveillance Epidemiologique Hebdomadaire du Paludisme”

This reports gives detailed tables on aspects concerning Malaria. As requested by Madagascar.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/plague/(location)/(end_date)/(start_date)
GET /reports/plague/(location)/(end_date)
GET /reports/plague/(location)

PlagueReport

This reports gives a summary of the plague situation

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/afro/(location)/(end_date)/(start_date)
GET /reports/afro/(location)/(end_date)
GET /reports/afro/(location)

AFRO Bulletin

This reports gives a comple summary of the state of the system.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/pip/(location)/(end_date)/(start_date)
GET /reports/pip/(location)/(end_date)
GET /reports/pip/(location)

Pandemic Influenza Preparedness (PIP) Report

This report shows data on the patients with severe acute respiratory infections (SARI). We include data on their treatmend and on lab data to confirm the type of Influenza.

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/ebs/(location)/(end_date)/(start_date)
GET /reports/ebs/(location)/(end_date)
GET /reports/ebs/(location)

EBSReport

This reports gives a summary of the plague situation

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/ctc/(location)/(end_date)/(start_date)
GET /reports/ctc/(location)/(end_date)
GET /reports/ctc/(location)

CTCReport

This reports gives a summary of the Cholera Treatment Centre surveillance

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /reports/sc/(location)/(end_date)/(start_date)
GET /reports/sc/(location)/(end_date)
GET /reports/sc/(location)

SCReport

This reports gives a summary of the Stabilisation Centre surveillance

Args:

location: Location to generate report for

start_date: Start date of report

end_date: End date of report

Returns:

report_data
GET /map/(variable_id)/(location)/(end_date)/(start_date)
GET /map/(variable_id)/(location)/(end_date)
GET /map/(variable_id)/(location)
GET /map/(variable_id)

Want to map a variable id by clinic (only include case reporting clinics)

Args:

variable_id: variable to map

interval: the time interval to aggregate over (default=year)

location: If we should restrict on location

include_all_clinics: If true we include all clinics even with no cases

Returns:

map_data: [{value:0, geolocation: .., clinic:name},…]
GET /aggregate_latest/(variable_id)/(identifier_id)/(location_id)

Get total and weekly aggregate for the current year for the given variable and location. Can get data for other years by useing the year keyword argument.

Args:

variable: variable_id

location: location_id

year: year (defaults to current year)

Reutrns:

result_dict: {“weeks”:{1:0….}, “year”:0}
GET /aggregate_year/(variable_id)/(location_id)/(year)
GET /aggregate_year/(variable_id)/(location_id)

Get total and weekly aggregate for the current year for the given variable and location. Can get data for other years by useing the year keyword argument.

Args:

variable: variable_id

location: location_id

year: year (defaults to current year)

Reutrns:

result_dict: {“weeks”:{1:0….}, “year”:0}
GET /prescriptions/(location)/(end_date)/(start_date)
GET /prescriptions/(location)/(end_date)
GET /prescriptions/(location)

Return medicine prescription data based on scanned barcodes

Args:

location: location id
Returns:
GET /clinics/(location_id)/(clinic_type)/(require_case_report)
GET /clinics/(location_id)/(clinic_type)
GET /clinics/(location_id)

Geojson for all clinics that are sublocation of location.

Args:

location_id: location that all other locations should be under

clinic_type: If we should only get a specific clinic type (default=None)

Returns:

points: A geojson FeatureCollection of points
GET /export/data_table/(download_name)/(restrict_by)

Export data table with aggregated data from db

Starts generation of data file

Args:
use_loc_ids: If we use names are location ids

Returns:

uuid
GET /device/(device_id)/submissions/(variable_id)

Resource handling device submissions api for a single device and selected variable id. Results can be filtered by url param filter in format filter=data_column_name:comparator:value, where:

data_column_name: model.Data sqlalchemy field name. comparator: eq =, ne !=, ge >=, le <=, gt >, lt < value: value to filter results by

Result is returned in json: {

“deviceId”: <device_id>, “variable”: <variable_id>, “submissionsCount”: <caluclated_submissions_count>

}

GET /epi_week_start/(year)/(epi_week)

Return the start date of an epi week in the given year

Args:

epi-week: epi week

year: year

Returns:
start-date: start-date
GET /aggregate/(variable_id)/(location_id)

Count (or add up) all the records with variable and location over all time.

Args:

variable: variable_id

location: location_id

Returns:

result: {“value”: value}
GET /devices/submissions/(variable_id)

Resource handling device submissions api for a all devices grouped by clinics under given parent location Requires providing parameter ‘location` with parent location id. e.g. http://host/api/devices/submissions/tot_1?location=1 Results can be filtered by url param filter in format filter=data_column_name:comparator:value, where:

data_column_name: model.Data sqlalchemy field name. comparator: eq =, ne !=, ge >=, le <=, gt >, lt < value: value to filter results by

Result is returned in json: {

“parentLocationId”: <passed_location_id>, “clinicCount”: <number_of_descendant_clinics_under_parent>, “clinicSubmissions”: [

“clinicId”: <clinic_id> “deviceSubmissions”: [

“deviceId”: <device_id>, “variable”: <variable_id>, “submissionsCount”: <caluclated_submissions_count> …

]

]

}

GET /records/(variable)/(location_id)

Return the records with a given variable and location

Args:

variable: variable_id

location: location

Returns:

list_of_records
GET /export/get_status/(uid)

Checks the current status of the generation

Args:
uuid: uuid to check status for
GET /export/getcsv/(uid)

serves a pregenerated csv file

Args:
uuid: uuid of download
GET /export/getxls/(uid)

Serves a pregenerated xls file

Args:
uuid: uuid of download
GET /export/form/(form)

Export a form. If fields is in the request variable we only include those fields.

Starts background export

Args:

form: the form to export
GET /incidence_map/(variable_id)

Want to map a variable id by clinic (only include case reporting clinics)

Args:

variable_id: variable to map

interval: the time interval to aggregate over (default=year)

location: If we should restrict on location

include_all_clinics: If true we include all clinics even with no cases

Returns:

map_data: [{value:0, geolocation: .., clinic:name},…]
GET /tot_clinics/(location_id)

Returns the number of clinics below location_id in the location tree Args:

location_id
Returns:
number of clinics
GET /geo_shapes/(level)

Returns the shapes for the given level

Args:

level: region, district or clinic
GET /variables/(category)

Return variables. If category=all we return all variables. If cateogry=locations or locations: we return locations. If category=alert we return variables which triggers alerts.

Args:

category: category of variables
GET /location/(location_id)

Location by location_id

Args:

location_id: id of location

Returns:

location: location
GET /variable/(variable_id)

Returns a variable

Args:

variable_id: id of variable to be returned
GET /device/(device_id)

=== Deprecated === Use Locations with “/locations?deviceId=<device_id> instead. Location by device_id

Args:

device_id: id of a device

Returns:

location: location
GET /alert/(alert_id)

Get alert with alert_id

Args:

alert_id

Returns:

alert

Testing

When new features for the API are developed they should be properly tested. The test are done using the python unittest library. All the tests are in the meerkat_api/test directory. For tests of indivudal function we use data inserted into the database for that specific test. The db_util.py file contains utilities for inserting data from data test_data directory. See the documentation below. We also have some general tests in the __init__.py file. We test that all urls return a 200 status code and that the authentication is set up properly. When adding new url endpoints it is important to make sure that these tests pass. Any arugments to these function needs to be given values that make sense (not nesccesary that all the functions return real results, but all urls should return status code 200). As some endpoints return csv format instead of json we need to handle them differently. Any new endpoints that return a csv format needs to be added to the csv_representations in need_csv_representations.

We also test that authentication is set up properly. We assume that all urls need authentication and the few urls that do not need authentication have to be specified in the urls_without_authentication list in the test_authentication function in __init__.py.

Functions that are used to test all urls

DB Util

Utility Functions

The most important utility function is thi query_sum function. It counts adds up the value of the variables submitted to it between the start_date and end_date. It can be used to get either an overall total, a weekly breakdown or breakdown by location level. The variables keyword is a list of variables that are required. For the variables that have values other than just 1 or 0, we sum up the values of the first variable in the list. Setting weeks=True gives a breakdown by weeks and setting level=region,district or clinic gives a breakdown by this level.

meerkat_api.util.data_query.latest_query(db, var_id, identifier_id, start_date, end_date, location, allowed_location=1, level=None, weeks=False, date_variable=None, week_offset=0)

To query register like data where we want to get the latest value.

I.e If the value of the number of beds is updated each week and we want the latest number. We take the latest value per clinic.

Parameters:
  • var_id – Variable id to get last of
  • identifier_id – Id to identify which records we should use
  • start_date – Start date
  • end_date – End date
  • location – Location to restrict to
  • date_variable – if None we use date from data otherwise we use the variable indicated
  • weeks – True if we want a breakdwon by weeks.
Returns:

Dictionary with results. Always has total key, and if

level was given there is a level key with the data breakdown

Return type:

result(dict)

meerkat_api.util.data_query.query_sum(db, var_ids, start_date, end_date, location, group_by_category=None, allowed_location=1, level=None, weeks=False, date_variable=None, exclude_variables=None)

Calculates the total number of records with every variable in var_ids. If var_ids is only one variable it can also be used to sum up the numbers of var_id.

If level is not None the data will be broken down by location level.

Parameters:
  • var_ids – list(or just a string) with variable ids
  • start_date – Start date
  • end_date – End date
  • location – Location to restrict to
  • level – Level to brea down the total by
  • weeks – True if we want a breakdwon by weeks.
  • date_variable – if None we use date from data otherwise we use the variable indicated
  • exclude_variables – list with variables to be excluded
Returns:

Dictionary with results. Always has total key, and if

level was given there is a level key with the data breakdown

Return type:

result(dict)

Other util functions:

meerkat_api util functions

meerkat_api.util.find_level(location, sublevel, locations)

Returns the isntance of level that location is a child of

Parameters:
  • location – location
  • sublevel – the sublevel we are interested in
  • locations – all locations in dict
Returns:

id of the mathcing location

Return type:

location_id(int)

meerkat_api.util.fix_dates(start_date, end_date)

We parse the start and end date and remove any timezone information

Parameters:
  • start_date – start date
  • end_date – end_date
Returns:

(start_date, end_date)

Return type:

dates(tuple)

meerkat_api.util.get_children(parent, locations, clinic_type=None, require_case_report=True, case_type=None)

Return all clinics that are children of parent

Parameters:
  • parent – parent_id
  • locations – all locations in dict
Returns:

list of location ids

meerkat_api.util.row_to_dict(row)

Translate sql alchemy row to dict

Args: row: SQL alchemy class

Returns:data as dictionary
Return type:data_dict(dict)
meerkat_api.util.rows_to_dicts(rows, dict_id=None)

Translate sql alchemy rows to dicts

Parameters:
  • rows – List of SQL alchemy rows
  • dict_id – If True we return a dict with the dict_id column as index
Returns:

data as dictionary

Return type:

data_dicts(dict)

meerkat_api.util.series_to_json_dict(series)

Takes pandas series and turns into a dict with string keys

Parameters:series – pandas series
Returns:dict
Return type:dict

Report Helper Functions

Resource for Reports.

The Reports are specified collections of data that can easily be visualised in a html or pdf report.

This large file includes the following reports:

NCD Report CD Report Public Health Profile NCD Profile CD Profile Refugee Profile Refugee CD Report Refugee Detailed Report Vaccination Report

meerkat_api.resources.reports.fix_dates(start_date, end_date)

We parse the start and end date and remove any timezone information

Parameters:
  • start_date – start date
  • end_date – end_date
Returns:

(start_date, end_date)

Return type:

dates(tuple)

meerkat_api.resources.reports.get_disease_types(category, start_date, end_date, location, conn, additional_variables=[])

Get and return top five disease of a type

Parameters:
  • category – the category to get the top five disease from
  • start_date – the start date for the aggregation
  • end_date – the end_date for the aggregation
  • location – the location to incldue
  • conn – db.connection
Returns:

ordered list of top five disease with percentage

Return type:

top_five_disease(list)

meerkat_api.resources.reports.make_dict(title, quantity, percent)

Small utility to create dictionary with title, quantity and percent

Parameters:
  • title – The title
  • quantity – quantity
  • percent – percent
Returns:

Dictionary

Return type:

dict(dict)

meerkat_api.resources.reports.top(values, number=5)

Return the dict containg the top number(defaults to 5) values. If we ask for the top 2 and the data looks like {“A”: 5, “B”: 5, “C”: 5} we will sort on the keys and take A and B.

Parameters:
  • values – the dict with data
  • number – how many we include (default=5)
Returns:

dict with the number highest values

Return type:

top_x(dict)

meerkat_api.resources.reports.get_variables_category(category, start_date, end_date, location, conn, use_ids=False, additional_variables=[])

Aggregate category between dates and with location

Parameters:
  • category – the category to get the top five disease from
  • start_date – the start date for the aggregation
  • end_date – the end_date for the aggregation
  • location – the location to incldue
  • conn – db.connection
  • use_ids – we use ids instead of names as keys for the return dict
Returns:

dict with {variable: number, variable2: number3, …}

Return type:

aggregate_category(dict)

meerkat_api.resources.reports.disease_breakdown(diseases)

Calculate the age and gender breakdown of dieases with codes of the following format: “Disease, Gender AgeGroup”. This is to deal with the refugee data that is submitted in an aggregated format instead of by cases.

Parameters:diseases – dict with Variable Name: value
Returns:formatted disease dict with dieases and age and gender breakdown
Return type:diseases(dict)
meerkat_api.resources.reports.get_latest_category(category, clinic, start_date, end_date)

To deal with data submitted in an aggregated way. We have e.g Population data that is submitted as the number of males <5, males 5-14 etc. These indicators are also not cumulative, we just want to find the latest record where any of the population data(in this example) has been submitted. Once that record is found we sort out the variable names that are of this format “Category, Gender AgeGroup” into a structured dict of demographics.

Args:get_variables_category(category, start_date, end_date, location, conn, use_ids=False):
category: the category to get the top five disease from clinic: the clinic we are looking at start_date: the start date for the aggregation end_date: the end_date for the aggregation
Returns:the demographics from the latest record
Return type:latest_demo(dict)
meerkat_api.resources.reports.refugee_disease(disease_demo)

From a dict of Variable Name: value where variable name includes gender and age information we want to just find the total numbers for each diseases.

Parameters:disease_demo – dict with disease data that includes demographics in the variable name
Returns:diseases with their aggregated value over all demographics
Return type:diseases(dict)