Skip to content

Commit

Permalink
Merge pull request #956 from onaio/charts-group-by
Browse files Browse the repository at this point in the history
support group by multiple fields
  • Loading branch information
denniswambua authored Mar 16, 2017
2 parents 17d6128 + 6dfa687 commit e287565
Show file tree
Hide file tree
Showing 4 changed files with 359 additions and 186 deletions.
58 changes: 57 additions & 1 deletion docs/charts.rst
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,62 @@ Response
- ``html`` format response is a html, javascript and css to the chart
- ``json`` format response is the ``JSON`` data that can be passed to a charting library

Get a chart for field grouped by another field in the form
----------------------------------------------------------

- ``field_name`` - a field name in the form, for group by multiple fields
requires this to be a numeric field.
- ``group_by`` - a field name in the form to group by, if it is a comma
separated field list then the field_name will be grouped by all the fields in
the list.
- ``format`` - can be ``html`` or ``json``

.. raw:: html

<pre class="prettyprint">
<b>GET</b> /api/v1/charts/<code>{formid}</code>.<code>{format}</code>?field_name=<code>field_name</code>&group_by=<code>field1,field2</code></pre>

Example
^^^^^^^
::

curl -X GET https://api.ona.io/api/v1/charts/4240.json?field_name=age&group_by=year
curl -X GET https://api.ona.io/api/v1/charts/4240.json?field_name=age&group_by=sex,year

Response
^^^^^^^^

- ``html`` format response is a html, javascript and css to the chart
- ``json`` format response is the ``JSON`` data that can be passed to a charting library

.. raw:: json
{
"field_type": "integer",
"data_type": "numeric",
"field_xpath": "age",
"data": [
{
"mean": 45.0,
"sum": 855.0,
"year": "1880",
"sex": [
"Female"
]
},
{
"mean": 45.0,
"sum": 855.0,
"year": "1850",
"sex": [
"Female"
]
},
"field_label": "Age",
"field_name": "age",
"xform": 4240
}
Get a chart data for all fields in a form
------------------------------------------

Expand All @@ -103,4 +159,4 @@ Response

- `json` format response is the `JSON` data for each field that can be passed to a charting library


31 changes: 26 additions & 5 deletions onadata/libs/data/query.py
Original file line number Diff line number Diff line change
Expand Up @@ -101,12 +101,25 @@ def _postgres_aggregate_group_by(field, name, xform, group_by, data_view=None):
if data_view:
additional_filters = _additional_data_view_filters(data_view)

query = "SELECT %(group_by)s AS \"%(group_name)s\","\
group_by_select = ""
group_by_group_by = ""
if isinstance(group_by, list):
group_by_group_by = []
for i, v in enumerate(group_by):
group_by_select += "%(group_by" + str(i) + \
")s AS \"%(group_name" + str(i) + ")s\", "
group_by_group_by.append("%(group_by" + str(i) + ")s")
group_by_group_by = ",".join(group_by_group_by)
else:
group_by_select = "%(group_by)s AS \"%(group_name)s\","
group_by_group_by = "%(group_by)s"

query = "SELECT " + group_by_select + \
"SUM((%(json)s)::numeric) AS sum, " \
"AVG((%(json)s)::numeric) AS mean " \
"FROM %(table)s WHERE %(restrict_field)s=%(restrict_value)s " \
"AND deleted_at IS NULL " + additional_filters + \
" GROUP BY %(group_by)s"
" GROUP BY " + group_by_group_by

query = query % string_args

Expand All @@ -122,15 +135,23 @@ def _postgres_select_key(field, name, xform):


def _query_args(field, name, xform, group_by=None):
return {
qargs = {
'table': 'logger_instance',
'json': _json_query(field),
'name': name,
'group_name': group_by,
'group_by': _json_query(group_by),
'restrict_field': 'xform_id',
'restrict_value': xform.pk}

if isinstance(group_by, list):
for i, v in enumerate(group_by):
qargs['group_name%d' % i] = v
qargs['group_by%d' % i] = _json_query(v)
else:
qargs['group_name'] = group_by
qargs['group_by'] = _json_query(group_by)

return qargs


def _select_key(field, name, xform):
if using_postgres:
Expand Down
Loading

0 comments on commit e287565

Please sign in to comment.