def edit_role(request, event_url_name, role_pk=None): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_EDIT): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # get BadgePermission role = None if role_pk: role = get_object_or_404(BadgeRole, pk=role_pk, badge_settings__event=event) # form form = BadgeRoleForm(request.POST or None, instance=role, settings=event.badge_settings) if form.is_valid(): form.save() return HttpResponseRedirect( reverse('badges:settings', args=[ event.url_name, ])) context = {'event': event, 'form': form} return render(request, 'badges/edit_role.html', context)
def register(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_GENERATE): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) if event.badge_settings.barcodes: form = BadgeBarcodeForm(request.POST or None, event=event) if form.is_valid(): if form.badge.printed: # duplicate -> error messages.error( request, _("Badge already printed: %(name)s") % {'name': form.badge.name()}) else: # mark as printed form.badge.printed = True form.badge.save() messages.success( request, _("Badge registered: %(name)s") % {'name': form.badge.name()}) else: form = None context = {'event': event, 'form': form} return render(request, 'badges/register.html', context)
def failed(request, event_url_name, task_id): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_GENERATE): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # get result result = AsyncResult(task_id) error = None latex_output = None if result.failed(): error = _("Internal Server Error. The admins were notified.") mail_admins("Badge generation error", str(result.result), fail_silently=True) elif result.state == "CREATOR_ERROR": error = result.info['error'] latex_output = result.info['latex_output'] # return error message context = {'event': event, 'error': error, 'latex_output': latex_output} return render(request, 'badges/failed.html', context)
def view_helpers_prerequisite(request, event_url_name, prerequisite_pk): event = get_object_or_404(Event, url_name=event_url_name) # check if feature is active if not event.prerequisites: return notactive(request) # check permission if not has_access(request.user, event, ACCESS_PREREQUISITES_VIEW): return nopermission(request) prerequisite = get_object_or_404(Prerequisite, pk=prerequisite_pk) if prerequisite.event != event: raise Http404 # find all helpers that need this prerequisite helpers = Helper.objects.filter( shifts__job__prerequisites=prerequisite).distinct() # render page context = { 'event': event, 'prerequisite': prerequisite, 'helpers': helpers } return render(request, 'prerequisites/view_helpers_prerequisite.html', context)
def edit_specialbadges(request, event_url_name, specialbadges_pk=None): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_EDIT_SPECIAL): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # get special badges specialbadges = None if specialbadges_pk: specialbadges = get_object_or_404(SpecialBadges, pk=specialbadges_pk, event=event) # form form = SpecialBadgesForm(request.POST or None, instance=specialbadges, event=event) if form.is_valid(): instance = form.save() return redirect('badges:edit_specialbadges_template', event_url_name=event.url_name, specialbadges_pk=instance.pk) context = {'event': event, 'form': form} return render(request, 'badges/edit_specialbadges.html', context)
def settings_advanced(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_EDIT): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # form for settings form = BadgeSettingsForm(request.POST or None, request.FILES or None, instance=event.badge_settings) # for for permissions permissions = event.badge_settings.badgepermission_set.all() if form.is_valid(): form.save() return HttpResponseRedirect(reverse('badges:settings_advanced', args=[event.url_name, ])) # render context = {'event': event, 'form': form, 'permissions': permissions} return render(request, 'badges/settings_advanced.html', context)
def edit_specialbadges_template(request, event_url_name, specialbadges_pk): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_EDIT_SPECIAL): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # get special badges specialbadges = get_object_or_404(SpecialBadges, pk=specialbadges_pk, event=event) # form form = BadgeForm(request.POST or None, request.FILES or None, instance=specialbadges.template_badge) if form.is_valid(): form.save() specialbadges.save() # sync changes to other badges return redirect('badges:list_specialbadges', event_url_name=event.url_name) context = {'event': event, 'form': form} return render(request, 'badges/edit_badge.html', context)
def delete_specialbadges(request, event_url_name, specialbadges_pk): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_EDIT_SPECIAL): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # get special badges specialbadges = get_object_or_404(SpecialBadges, pk=specialbadges_pk, event=event) form = SpecialBadgesDeleteForm(request.POST or None, instance=specialbadges) if form.is_valid(): form.delete() return redirect('badges:list_specialbadges', event_url_name=event.url_name) context = {'event': event, 'form': form, 'specialbadges': specialbadges} return render(request, 'badges/delete_specialbadges.html', context)
def take_back_direct(request, event_url_name, item_pk): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_INVENTORY_HANDLE): return nopermission(request) # check if badge system is active if not event.inventory: return notactive(request) item = Item.objects.get(pk=item_pk) try: helper = item.get_exclusive_user(event) item.remove_from_helper(helper) request.session['inventory_helper_pk'] = str(helper.pk) return redirect('inventory:take_back', event_url_name) except InvalidMultipleAssignment: error = 'multiple' except NotAssigned: error = 'noassignment' context = {'event': event, 'error': error} return render(request, 'inventory/take_back_error.html', context)
def list_shirts(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_GIFTS_VIEW_SUMMARY): return nopermission(request) # check if active if not event.gifts: return notactive(request) if event.ask_shirt: helpers = event.helper_set.filter(gifts__buy_shirt=True) num_shirts = OrderedDict() shirts = helpers.values('shirt').annotate(num=Count('shirt')) for size, name in event.get_shirt_choices(): num = 0 try: num = shirts.get(shirt=size)['num'] except Helper.DoesNotExist: pass num_shirts.update({name: num}) else: helpers = None num_shirts = None context = {'event': event, 'helpers': helpers, 'num_shirts': num_shirts, 'shirts_not_active': not event.ask_shirt} return render(request, 'gifts/list_shirts.html', context)
def list(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_GIFTS_EDIT): return nopermission(request) # check if active if not event.gifts: return notactive(request) # manage gift settings settings_form = GiftSettingsForm(request.POST or None, instance=event.giftsettings) if settings_form.is_valid(): settings_form.save() log_msg = "giftsettings changed" logger.info(log_msg, extra={ 'user': request.user, 'event': event, }) return redirect("gifts:list", event_url_name=event.url_name) # grab gifts and giftsets gifts = Gift.objects.filter(event=event) gift_sets = GiftSet.objects.filter(event=event) context = {'event': event, 'gifts': gifts, 'gift_sets': gift_sets, 'settings_form': settings_form} return render(request, 'gifts/list.html', context)
def set_present(request, event_url_name, shift_pk): event, job, shift, helper = get_or_404(event_url_name, shift_pk=shift_pk) # check permission if not has_access(request.user, event, ACCESS_GIFTS_HANDLE_PRESENCE): return nopermission(request) # check if active if not event.gifts: return notactive(request) form = PresentForm(request.POST or None, shift=shift, user=request.user) if form.is_valid(): form.save() messages.success(request, _("Presence was saved")) return HttpResponseRedirect(reverse('gifts:set_present', args=[event.url_name, shift.pk, ])) context = {'event': event, 'shift': shift, 'form': form} return render(request, 'gifts/set_present.html', context)
def delete_permission(request, event_url_name, permission_pk): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_EDIT): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # get BadgePermission permission = get_object_or_404(BadgePermission, pk=permission_pk, badge_settings__event=event) # form form = BadgePermissionDeleteForm(request.POST or None, instance=permission) if form.is_valid(): form.delete() return HttpResponseRedirect(reverse('badges:settings_advanced', args=[event.url_name, ])) context = {'event': event, 'form': form, 'permission': permission} return render(request, 'badges/delete_permission.html', context)
def overview(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # permission if not has_access(request.user, event, ACCESS_STATISTICS_VIEW): return nopermission(request) num_helpers = event.helper_set.count() num_coordinators = event.all_coordinators.count() num_vegetarians = event.helper_set.filter(vegetarian=True).count() num_shift_slots = Shift.objects.filter(job__event=event).aggregate( Sum('number'))['number__sum'] empty_slots_expr = ExpressionWrapper(F('number') - F('num_helpers'), output_field=fields.IntegerField()) num_empty_shift_slots = Shift.objects.filter(job__event=event) \ .annotate(num_helpers=Count('helper')) \ .annotate(empty_slots=empty_slots_expr) \ .aggregate(Sum('empty_slots'))['empty_slots__sum'] total_duration = ExpressionWrapper((F('end') - F('begin')) * F('number'), output_field=fields.DurationField()) try: hours_total = Shift.objects.filter(job__event=event) \ .annotate(duration=total_duration) \ .aggregate(Sum('duration'))['duration__sum'] except (OperationalError, OverflowError): hours_total = None except Exception as e: # handle psycopg2.DataError without importing psycopg2 # happens on overflow with postgresql if 'DataError' in str(e.__class__): hours_total = None else: raise e if event.badges: num_specialbadges = SpecialBadges.objects.filter( event=event).aggregate(Sum('number'))['number__sum'] or 0 else: num_specialbadges = 0 # render context = { 'event': event, 'num_helpers': num_helpers, 'num_coordinators': num_coordinators, 'num_vegetarians': num_vegetarians, 'num_shift_slots': num_shift_slots, 'num_empty_shift_slots': num_empty_shift_slots, 'num_specialbadges': num_specialbadges, 'hours_total': hours_total } return render(request, 'statistic/overview.html', context)
def chart_timeline(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # permission if not has_access(request.user, event, ACCESS_STATISTICS_VIEW): return JsonResponse({}) # collect data timeline = {} for helper in event.helper_set.all(): if not helper.is_coordinator: day = helper.timestamp.strftime('%Y-%m-%d') if day in timeline: timeline[day] += 1 else: timeline[day] = 1 # abort if no data found if len(timeline) == 0: return JsonResponse({}) # sum up timeline timeline_sum_data = [] days = sorted(timeline.keys()) cur_sum = 0 for day in days: cur_sum += timeline[day] timeline_sum_data.append({ "x": day, "y": cur_sum, }) # output format output = { "type": "line", "data": { 'datasets': [ { "label": _("Number of helpers"), "data": timeline_sum_data, "lineTension": 0.2, }, ] }, "options": { "scales": { "xAxes": [{ "type": 'time', }], }, }, } return JsonResponse(output)
def event_list(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_INVENTORY_HANDLE): return nopermission(request) # check if badge system is active if not event.inventory: return notactive(request) used_items = UsedItem.objects.filter(helper__event=event) context = {'event': event, 'used_items': used_items} return render(request, 'inventory/list.html', context)
def view_prerequisites(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check if feature is active if not event.prerequisites: return notactive(request) # check permission if not has_access(request.user, event, ACCESS_PREREQUISITES_VIEW): return nopermission(request) prerequisites = Prerequisite.objects.filter(event=event) context = {'event': event, 'prerequisites': prerequisites} return render(request, 'prerequisites/view_prerequisites.html', context)
def can_see_mail(self, user): # not involved at all -> no if not has_access(user, self.event, ACCESS_INVOLVED): return False # can view all mails -> yes if has_access(user, self.event, ACCESS_MAILS_VIEW): return True # involved and mail sent to everybody -> yes if self.all_helpers_and_coordinators: return True # mails to all coordinators are only visible for admins for job in self.jobs_all.all(): if has_access(user, job, ACCESS_JOB_VIEW_MAILS): return True for job in self.jobs_only_coordinators.all(): if has_access(user, job, ACCESS_JOB_VIEW_MAILS): return True return False
def list_specialbadges(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_EDIT_SPECIAL): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # get special badges (=badges without helper object) specialbadges = SpecialBadges.objects.filter(event=event) context = {'event': event, 'specialbadges': specialbadges} return render(request, 'badges/list_specialbadges.html', context)
def download(request, event_url_name, task_id): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_GENERATE): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # remove from list if 'badge_tasks' not in request.session: request.session['badge_tasks'] = [] del_task = None for task in request.session['badge_tasks']: if task['id'] == task_id: del_task = task break if del_task: request.session['badge_tasks'].remove(del_task) request.session.modified = True # TODO: files can be deleted also, happens through celery at the moment # get result badge_task = BadgeTaskResult(task_id) if badge_task.finished and not badge_task.expired: # output filename = escape_filename("%s.pdf" % badge_task.dl_filename) response = HttpResponse(content_type='application/pdf') response['Content-Disposition'] = 'attachment; filename="%s"' % \ filename # send file with open(badge_task.pdf, 'rb') as f: response.write(f.read()) return response else: # return error message context = {'event': event} return render(request, 'badges/download.html', context)
def edit_prerequisite(request, event_url_name, prerequisite_pk=None): event = get_object_or_404(Event, url_name=event_url_name) # check if feature is active if not event.prerequisites: return notactive(request) # check permission if not has_access(request.user, event, ACCESS_PREREQUISITES_EDIT): return nopermission(request) # get prerequisite, if available prerequisite = None if prerequisite_pk: prerequisite = get_object_or_404(Prerequisite, pk=prerequisite_pk) if prerequisite.event != event: raise Http404 # handle form form = PrerequisiteForm(request.POST or None, instance=prerequisite, event=event) if form.is_valid(): prerequisite = form.save() log_msg = "prerequisite created" if prerequisite_pk: log_msg = "prerequisite changed" logger.info(log_msg, extra={ 'user': request.user, 'event': event, 'prerequisite': prerequisite.name, 'prerequisite_pk': prerequisite.pk, }) # redirect to prerequisite overview return redirect('prerequisites:view_prerequisites', event_url_name=event.url_name) # render page context = {'event': event, 'prerequisite': prerequisite, 'form': form} return render(request, 'prerequisites/edit_prerequisite.html', context)
def warnings(request, event_url_name, job_pk): event, job, shift, helper = get_or_404(event_url_name, job_pk) # check permission if not has_access(request.user, event, ACCESS_BADGES_GENERATE): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # TODO: check if possible helpers = warnings_for_job(job) # render context = {'event': event, 'helpers': helpers} return render(request, 'badges/warnings.html', context)
def event_settings(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_INVENTORY_EDIT): return nopermission(request) # check if badge system is active if not event.inventory: return notactive(request) form = InventorySettingsForm(request.POST or None, instance=event.inventory_settings) if form.is_valid(): form.save() return redirect('inventory:event_settings', event_url_name) context = {'event': event, 'form': form} return render(request, 'inventory/event_settings.html', context)
def default_template(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_EDIT): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # output response = HttpResponse(content_type='application/x-tex') response['Content-Disposition'] = 'attachment; filename="template.tex"' # send file with open(django_settings.BADGE_DEFAULT_TEMPLATE, 'rb') as f: response.write(f.read()) return response
def delete_gift(request, event_url_name, gift_pk): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_GIFTS_EDIT): return nopermission(request) # check if active if not event.gifts: return notactive(request) gift = _validate_gift(event, gift_pk) # gift sets that use this gift gift_sets = GiftSet.objects.filter(gifts__id=gift.id).all() # form form = GiftDeleteForm(request.POST or None, instance=gift) if form.is_valid(): form.delete() messages.success(request, _("Gift deleted: %(name)s") % {'name': gift.name}) logger.info("gift deleted", extra={ 'user': request.user, 'event': event, 'gift_pk': gift_pk, 'gift': gift.name, }) # redirect to shift return HttpResponseRedirect(reverse('gifts:list', args=[event.url_name, ])) # render page context = {'gift': gift, 'gift_sets': gift_sets, 'form': form, 'event': event} return render(request, 'gifts/delete_gift.html', context)
def take_back_badge(request, event_url_name, item_pk): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_INVENTORY_HANDLE): return nopermission(request) # check if badge system is active if not event.inventory: return notactive(request) wrong_helper = False item = None try: item = Item.objects.get(pk=item_pk) form = BadgeBarcodeForm(request.POST or None, event=event) if form.is_valid(): if form.badge.helper: item.remove_from_helper(form.badge.helper) request.session['inventory_helper_pk'] = \ str(form.badge.helper.pk) return redirect('inventory:take_back', event_url_name) else: # special badge -> just show wrong helper message wrong_helper = True except (KeyError, Item.DoesNotExist): form = None except WrongHelper: wrong_helper = True context = { 'event': event, 'form': form, 'item': item, 'wrong_helper': wrong_helper } return render(request, 'inventory/take_back_badge.html', context)
def index(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_BADGES_GENERATE): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # check if all necessary settings are done possible = event.badge_settings.creation_possible() # number for warnings for each job jobs = event.job_set.all() for job in jobs: job.num_warnings = len(warnings_for_job(job)) context = {'event': event, 'jobs': jobs, 'possible': possible} return render(request, 'badges/index.html', context)
def delete_prerequisite(request, event_url_name, prerequisite_pk): event = get_object_or_404(Event, url_name=event_url_name) # check if feature is active if not event.prerequisites: return notactive(request) # check permission if not has_access(request.user, event, ACCESS_PREREQUISITES_EDIT): return nopermission(request) prerequisite = get_object_or_404(Prerequisite, pk=prerequisite_pk) if prerequisite.event != event: raise Http404 # form form = PrerequisiteDeleteForm(request.POST or None, instance=prerequisite) if form.is_valid(): form.delete() messages.success( request, _("Prerequisite deleted: %(name)s") % {'name': prerequisite.name}) logger.info("prerequisite deleted", extra={ 'user': request.user, 'event': event, 'prerequisite': prerequisite.name, 'prerequisite_pk': prerequisite.pk, }) # redirect to prerequisite overview return redirect('prerequisites:view_prerequisites', event_url_name=event.url_name) # render page context = {'event': event, 'prerequisite': prerequisite, 'form': form} return render(request, 'prerequisites/delete_prerequisite.html', context)
def take_back_item(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # check permission if not has_access(request.user, event, ACCESS_INVENTORY_HANDLE): return nopermission(request) # check if badge system is active if not event.inventory: return notactive(request) last_helper_pk = request.session.pop('inventory_helper_pk', None) try: last_helper = Helper.objects.get(pk=last_helper_pk) last_helper_items = UsedItem.objects.filter(helper=last_helper, timestamp_returned=None) except Helper.DoesNotExist: last_helper = None last_helper_items = None form = InventoryBarcodeForm(request.POST or None, event=event) not_in_use = False if form.is_valid(): if form.item.is_in_use(event): return redirect('inventory:take_back_badge', event_url_name, form.item.pk) else: not_in_use = True context = { 'event': event, 'form': form, 'not_in_use': not_in_use, 'last_helper': last_helper, 'last_helper_items': last_helper_items } return render(request, 'inventory/take_back_item.html', context)
def tasklist(request, event_url_name): event = get_object_or_404(Event, url_name=event_url_name) # do not return data if user is not authenticated if not request.user.is_authenticated: context = {'event': event, 'tasks': None, 'no_login': True} return render(request, 'badges/tasklist.html', context) # check permission if not has_access(request.user, event, ACCESS_BADGES_GENERATE): return nopermission(request) # check if badge system is active if not event.badges: return notactive(request) # recently started tasks if 'badge_tasks' not in request.session: request.session['badge_tasks'] = [] task_results = [] task_list_del = [] for task in request.session['badge_tasks']: tmp = BadgeTaskResult(task['id'], task['name']) # filter expired tasks if tmp.expired: task_list_del.append(task) elif task['event'] == event.pk: task_results.append(tmp) # remove expired filtered tasks for task in task_list_del: request.session['badge_tasks'].remove(task) request.session.modified = True context = {'event': event, 'tasks': task_results, 'no_login': False} return render(request, 'badges/tasklist.html', context)