Created
January 8, 2014 22:13
-
-
Save wraithan/8325429 to your computer and use it in GitHub Desktop.
Stab at moving to CSV
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import calendar | |
import json | |
from collections import defaultdict | |
from django.http.response import (HttpResponse, HttpResponseBadRequest, | |
HttpResponseForbidden) | |
from django.db.models import Avg, Min, Max, Sum | |
from django.views.generic.base import View | |
from ordereddict import OrderedDict | |
from apps.survey.models import GridAnswer | |
from .forms import GridStandardDeviationForm | |
from .utils import CustomJSONEncoder, SlugCSVWriter | |
class BaseGraphView(View): | |
def dispatch(self, request, **kwargs): | |
renderer = getattr(self, 'render_to_{0}'.format(self.output), None) | |
if renderer is None: | |
return HttpResponseBadRequest() | |
if (not request.user.is_authenticated() or | |
not (request.user.is_staff or request.user.is_superuser)): | |
return HttpResponseForbidden() | |
self.form = self.form_class(request.GET) | |
if not self.form.is_valid(): | |
return self.error(self.form.errors) | |
self.rows, self.labels = self.get_rows(form_data=self.form.cleaned_data, | |
**kwargs) | |
self.filename = self.filename_template.format(**kwargs) | |
return renderer() | |
def build_filter(self, form_data): | |
filters = {} | |
for key, value in form_data.iteritems(): | |
if value is not None: | |
filters[self.model_filter[key]] = value | |
return filters | |
def get_rows(self): | |
raise NotImplementedError | |
def process_data_for_json(self): | |
pass | |
def render_to_json(self): | |
self.process_data_for_json() | |
return HttpResponse(json.dumps({ | |
'success': True, | |
'graph_data': self.rows, | |
'labels': self.labels, | |
}, cls=CustomJSONEncoder), content_type='application/json') | |
def process_data_for_csv(self): | |
pass | |
def render_to_csv(self): | |
self.process_data_for_csv() | |
response = HttpResponse(content_type='text/csv') | |
response['Content-Disposition'] = ('attachment; filename="{0}"' | |
.format(self.csv_filename)) | |
writer = SlugCSVWriter(response, self.field_names) | |
writer.writeheader() | |
writer.writerows(self.rows) | |
return response | |
class GridStandardDeviationView(BaseGraphView): | |
form_class = GridStandardDeviationForm | |
model_filter = { | |
'row': 'row_label', | |
'col': 'col_label', | |
'market': 'response__respondant__survey_site', | |
'status': 'response__respondant__review_status', | |
'start_date': 'response__respondant__ts__gte', | |
'end_date': 'response__respondant__ts__lt' | |
} | |
field_names = OrderedDict(( | |
('row_text', 'Type'), | |
('date', 'Date'), | |
('minimum', 'Minimum'), | |
('average', 'Average'), | |
('maximum', 'Maximum'), | |
('total', 'Total') | |
)) | |
filename_template = 'grid_standard_deviation_{question_slug}_{inteval}.csv' | |
def get_rows(self, question_slug, interval, form_data): | |
rows = (GridAnswer.objects.filter(response__question__slug=question_slug) | |
.extra(select={'date': "date_trunc(%s, survey_response.ts)"}, | |
select_params=(interval,), | |
tables=('survey_response',)) | |
.filter(**self.build_filter(form_data))) | |
labels = list(rows.values_list('row_label', flat=True).distinct()) | |
rows = (rows.values('row_text', 'row_label', 'date') | |
.order_by('date') | |
.annotate(minimum=Min('answer_number'), | |
average=Avg('answer_number'), | |
maximum=Max('answer_number'), | |
total=Sum('answer_number'))) | |
return rows, labels | |
def process_data_for_json(self): | |
graph_data = defaultdict(list) | |
for row in self.rows: | |
row['date'] = calendar.timegm(row['date'].utctimetuple()) * 1000 | |
graph_data[row['row_text']].append(row) | |
self.rows = graph_data | |
self.labels = list(self.labels) | |
def process_data_for_csv(self): | |
for row in self.rows: | |
row.pop('row_label') | |
row['date'] = str(row['date']) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment