Commit 1e152bf2b70a24f0c925dc52f66230e897c72ed5

Authored by Zambom
1 parent e6de6131

Adding goals history report

amadeus/static/js/goals_reports.js
... ... @@ -46,6 +46,9 @@ function getAnswered() {
46 46 container.find('.unanswered_link').removeClass('active');
47 47 container.find('.unanswered').hide();
48 48  
  49 + container.find('.history_link').removeClass('active');
  50 + container.find('.history').hide();
  51 +
49 52 setBreadcrumb(answeredBread);
50 53 }
51 54  
... ... @@ -106,9 +109,62 @@ function getUnanswered() {
106 109 container.find('.unanswered_link').addClass('active');
107 110 container.find('.unanswered').show();
108 111  
  112 + container.find('.history_link').removeClass('active');
  113 + container.find('.history').hide();
  114 +
109 115 setBreadcrumb(unansweredBread);
110 116 }
111 117  
  118 +function getHistory() {
  119 + var container = $("#reports"),
  120 + list = container.find('.history_data');
  121 +
  122 + if (list.children().length == 0) {
  123 + var url = list.parent().data('url');
  124 +
  125 + $.ajax({
  126 + url: url,
  127 + success: function (data) {
  128 + list.html(data);
  129 +
  130 + $('#history_table').DataTable({
  131 + "dom": "Bfrtip",
  132 + "language": dataTablei18n,
  133 + buttons: {
  134 + dom: {
  135 + container: {
  136 + className: 'col-md-3'
  137 + },
  138 + buttonContainer: {
  139 + tag: 'h4',
  140 + className: 'history-header'
  141 + },
  142 + },
  143 + buttons: [
  144 + {
  145 + extend: 'csv',
  146 + text: csvBtnLabeli18n,
  147 + filename: 'report-history'
  148 + }
  149 + ],
  150 + },
  151 + });
  152 + }
  153 + });
  154 + }
  155 +
  156 + container.find('.answered_link').removeClass('active');
  157 + container.find('.answered').hide();
  158 +
  159 + container.find('.unanswered_link').removeClass('active');
  160 + container.find('.unanswered').hide();
  161 +
  162 + container.find('.history_link').addClass('active');
  163 + container.find('.history').show();
  164 +
  165 + setBreadcrumb(historyBread);
  166 +}
  167 +
112 168 function setBreadcrumb(text) {
113 169 var breadcrumb = $(".breadcrumb")[0],
114 170 li = $(breadcrumb).find('li:last-child');
... ...
goals/templates/goals/_history.html 0 → 100644
... ... @@ -0,0 +1,40 @@
  1 +{% load i18n goals_filters %}
  2 +
  3 +<div class="row">
  4 + <div class="col-md-12">
  5 + <table id="history_table" class="table table-striped table-bordered">
  6 + <thead>
  7 + <th>
  8 + {% trans 'Date/Hour' %}
  9 + </th>
  10 + <th>
  11 + {% trans 'Student' %}
  12 + </th>
  13 + <th>
  14 + {% trans 'Group' %}
  15 + </th>
  16 + <th>
  17 + {% trans 'Action' %}
  18 + </th>
  19 + <th>
  20 + {% trans 'Object' %}
  21 + </th>
  22 + <th>
  23 + {% trans 'Resource' %}
  24 + </th>
  25 + </thead>
  26 + <tbody>
  27 + {% for row in records %}
  28 + <tr>
  29 + <td>{{ row.datetime }}</td>
  30 + <td>{{ row.user }}</td>
  31 + <td>{{ row.user_id|log_groups }}</td>
  32 + <td>{{ row.action|log_action }}</td>
  33 + <td>{{ row|log_object }}</td>
  34 + <td>{{ row.context.goals_name }}</td>
  35 + </tr>
  36 + {% endfor %}
  37 + </tbody>
  38 + </table>
  39 + </div>
  40 +</div>
0 41 \ No newline at end of file
... ...
goals/templates/goals/reports.html
... ... @@ -56,22 +56,20 @@
56 56 <ul class="core-subjects-options">
57 57 <a href="javascript:getAnswered()"><li class="answered_link active">{% trans "Answered" %} ({{ totals.answered }})</li></a>
58 58 <a href="javascript:getUnanswered()"><li class="unanswered_link">{% trans "Unanswered" %} ({{ totals.unanswered }})</li></a>
59   - <a href=""><li class="">{% trans "Resource History" %}</li></a>
  59 + <a href="javascript:getHistory()"><li class="history_link">{% trans "Resource History" %}</li></a>
60 60 </ul>
61 61 </div>
62 62  
63 63 <div class="answered" data-url="{% url 'goals:answered_report' goal.slug %}">
64 64 <div class="answered_data"></div>
65   - <div class="text-center">
66   - <div class="holder"></div>
67   - </div>
68 65 </div>
69 66  
70 67 <div class="unanswered" data-url="{% url 'goals:unanswered_report' goal.slug %}">
71 68 <div class="unanswered_data"></div>
72   - <div class="text-center">
73   - <div class="holder"></div>
74   - </div>
  69 + </div>
  70 +
  71 + <div class="history" data-url="{% url 'goals:history_report' goal.slug %}">
  72 + <div class="history_data"></div>
75 73 </div>
76 74 </div>
77 75 </div>
... ... @@ -104,7 +102,8 @@
104 102  
105 103 var csvBtnLabeli18n = "<i class='fa fa-download'></i> {% trans 'Download .csv file' %}",
106 104 answeredBread = "{% trans 'Reports: Answered' %}",
107   - unansweredBread = "{% trans 'Reports: Unanswered' %}";
  105 + unansweredBread = "{% trans 'Reports: Unanswered' %}",
  106 + historyBread = "{% trans 'Reports: History' %}";
108 107 </script>
109 108 <script type="text/javascript" src="{% static 'js/goals_reports.js' %}"></script>
110 109 {% endblock %}
111 110 \ No newline at end of file
... ...
goals/templatetags/goals_filters.py
... ... @@ -3,6 +3,7 @@ from django.utils.translation import ugettext_lazy as _
3 3  
4 4 from goals.models import MyGoals
5 5 from log.models import Log
  6 +from students_group.models import StudentsGroup
6 7  
7 8 register = template.Library()
8 9  
... ... @@ -17,6 +18,17 @@ def groups(user):
17 18 else:
18 19 return "---"
19 20  
  21 +@register.filter(name = 'log_groups')
  22 +def log_groups(user_id):
  23 + groups = StudentsGroup.objects.filter(participants__id = user_id).values_list('name', flat = True)
  24 +
  25 + if groups.count() > 0:
  26 + groups = list(groups)
  27 +
  28 + return ", ".join(groups)
  29 + else:
  30 + return "---"
  31 +
20 32 @register.filter(name = 'creation_date')
21 33 def creation_date(user, goal):
22 34 log = Log.objects.filter(user_id = user.id, action = 'submit', resource = 'goals', context__contains = {"goals_id": goal.id})
... ... @@ -39,4 +51,26 @@ def update_date(user, goal):
39 51 def my_goals(user, goal):
40 52 mine = list(MyGoals.objects.filter(user = user, item__goal = goal).values_list('value', flat = True))
41 53  
42   - return ', '.join(str(x) for x in mine)
43 54 \ No newline at end of file
  55 + return ', '.join(str(x) for x in mine)
  56 +
  57 +@register.filter(name = 'log_action')
  58 +def log_action(action):
  59 + if action == 'view':
  60 + return _('Visualized')
  61 + elif action == 'create':
  62 + return _('Added')
  63 + elif action == 'update':
  64 + return _('Updated')
  65 + elif action == 'submit':
  66 + return _('Submitted')
  67 +
  68 + return '---'
  69 +
  70 +@register.filter(name = 'log_object')
  71 +def log_object(log):
  72 + if log.resource == 'my_goals':
  73 + return _('My Goals')
  74 +
  75 + name = log.context['goals_name']
  76 +
  77 + return _("%s Instance")%(name)
44 78 \ No newline at end of file
... ...
goals/urls.py
... ... @@ -14,4 +14,5 @@ urlpatterns = [
14 14 url(r'^reports/(?P<slug>[\w_-]+)/$', views.Reports.as_view(), name = 'reports'),
15 15 url(r'^answered_report/(?P<slug>[\w_-]+)/$', views.AnsweredReport.as_view(), name = 'answered_report'),
16 16 url(r'^unanswered_report/(?P<slug>[\w_-]+)/$', views.UnansweredReport.as_view(), name = 'unanswered_report'),
  17 + url(r'^history_report/(?P<slug>[\w_-]+)/$', views.HistoryReport.as_view(), name = 'history_report'),
17 18 ]
... ...
goals/views.py
... ... @@ -71,7 +71,6 @@ class AnsweredReport(LoginRequiredMixin, generic.ListView):
71 71 redirect_field_name = 'next'
72 72  
73 73 template_name = 'goals/_answered.html'
74   - model = MyGoals
75 74 context_object_name = 'students'
76 75  
77 76 def get_queryset(self):
... ... @@ -110,7 +109,6 @@ class UnansweredReport(LoginRequiredMixin, generic.ListView):
110 109 redirect_field_name = 'next'
111 110  
112 111 template_name = 'goals/_unanswered.html'
113   - model = MyGoals
114 112 context_object_name = 'students'
115 113  
116 114 def get_queryset(self):
... ... @@ -146,6 +144,40 @@ class UnansweredReport(LoginRequiredMixin, generic.ListView):
146 144  
147 145 return context
148 146  
  147 +class HistoryReport(LoginRequiredMixin, generic.ListView):
  148 + login_url = reverse_lazy("users:login")
  149 + redirect_field_name = 'next'
  150 +
  151 + template_name = 'goals/_history.html'
  152 + context_object_name = 'records'
  153 +
  154 + def get_queryset(self):
  155 + slug = self.kwargs.get('slug', '')
  156 + goal = get_object_or_404(Goals, slug = slug)
  157 +
  158 + rows = Log.objects.filter(context__contains = {"goals_id": goal.id})
  159 +
  160 + return rows
  161 +
  162 + def dispatch(self, request, *args, **kwargs):
  163 + slug = self.kwargs.get('slug', '')
  164 + goals = get_object_or_404(Goals, slug = slug)
  165 +
  166 + if not has_resource_permissions(request.user, goals):
  167 + return redirect(reverse_lazy('subjects:home'))
  168 +
  169 + return super(HistoryReport, self).dispatch(request, *args, **kwargs)
  170 +
  171 + def get_context_data(self, **kwargs):
  172 + context = super(HistoryReport, self).get_context_data(**kwargs)
  173 +
  174 + slug = self.kwargs.get('slug', '')
  175 + goals = get_object_or_404(Goals, slug = slug)
  176 +
  177 + context['goal'] = goals
  178 +
  179 + return context
  180 +
149 181 class InsideView(LoginRequiredMixin, LogMixin, generic.ListView):
150 182 log_component = "resources"
151 183 log_action = "view"
... ...