From cae951766530d6ada5240f9f3d9653b017a30a98 Mon Sep 17 00:00:00 2001 From: Étienne Loks Date: Wed, 12 Apr 2017 18:55:58 +0200 Subject: Treament dashboard: add filter form (refs #3381) --- ishtar_common/views.py | 23 +++++++++++++++-------- 1 file changed, 15 insertions(+), 8 deletions(-) (limited to 'ishtar_common/views.py') diff --git a/ishtar_common/views.py b/ishtar_common/views.py index e8a2c9e12..4aa452641 100644 --- a/ishtar_common/views.py +++ b/ishtar_common/views.py @@ -63,6 +63,7 @@ from archaeological_finds.models import Find, Treatment, TreatmentFile, \ from archaeological_operations.forms import DashboardForm as DashboardFormOpe from archaeological_files.forms import DashboardForm as DashboardFormFile +from archaeological_finds.forms import DashboardTreatmentForm from ishtar_common.forms import FinalForm, FinalDeleteForm from ishtar_common.widgets import JQueryAutoComplete @@ -1458,7 +1459,10 @@ def dashboard_main(request, dct, obj_id=None, *args, **kwargs): return render_to_response('ishtar/dashboards/dashboard_main.html', dct, context_instance=RequestContext(request)) -DASHBOARD_FORMS = {'files': DashboardFormFile, 'operations': DashboardFormOpe} +DASHBOARD_FORMS = { + 'files': DashboardFormFile, 'operations': DashboardFormOpe, + 'treatments': DashboardTreatmentForm +} def dashboard_main_detail(request, item_name): @@ -1473,8 +1477,11 @@ def dashboard_main_detail(request, item_name): form = None slicing, date_source, fltr, show_detail = 'year', None, {}, False profile = models.get_current_profile() - if (item_name == 'files' and profile.files) \ - or item_name == 'operations': + has_form = (item_name == 'files' and profile.files) \ + or item_name == 'operations' \ + or (item_name in ('treatmentfiles', 'treatments') + and profile.warehouse) + if has_form: slicing = 'month' if item_name in DASHBOARD_FORMS: if request.method == 'POST': @@ -1490,8 +1497,7 @@ def dashboard_main_detail(request, item_name): form = DASHBOARD_FORMS[item_name]() lbl, dashboard = None, None dashboard_kwargs = {} - if (item_name == 'files' and profile.files) \ - or item_name == 'operations': + if has_form: dashboard_kwargs = {'slice': slicing, 'fltr': fltr, 'show_detail': show_detail} # date_source is only relevant when the form has set one @@ -1515,12 +1521,13 @@ def dashboard_main_detail(request, item_name): elif item_name == 'treatmentfiles' and profile.warehouse: lbl, dashboard = ( _(u"Treatment requests"), - models.Dashboard(TreatmentFile, slice=slicing, fltr=fltr)) + models.Dashboard(TreatmentFile, **dashboard_kwargs)) elif item_name == 'treatments' and profile.warehouse: + if 'date_source' not in dashboard_kwargs: + dashboard_kwargs['date_source'] = 'start' lbl, dashboard = ( _(u"Treatments"), - models.Dashboard(Treatment, slice=slicing, fltr=fltr, - date_source='start')) + models.Dashboard(Treatment, **dashboard_kwargs)) if not lbl: raise Http404 dct = {'lbl': lbl, 'dashboard': dashboard, -- cgit v1.2.3 From 4e245d53cbba5afd595b2a4effc79800270bba8d Mon Sep 17 00:00:00 2001 From: Étienne Loks Date: Wed, 12 Apr 2017 22:38:09 +0200 Subject: Treament file dashboard: add filter form (refs #3381) --- archaeological_finds/forms.py | 4 +- archaeological_finds/forms_treatments.py | 51 +++++++++++++++++++--- .../ishtar/dashboards/dashboard_main_detail.html | 2 +- ishtar_common/views.py | 12 ++--- 4 files changed, 57 insertions(+), 12 deletions(-) (limited to 'ishtar_common/views.py') diff --git a/archaeological_finds/forms.py b/archaeological_finds/forms.py index c0f44423d..ee010094b 100644 --- a/archaeological_finds/forms.py +++ b/archaeological_finds/forms.py @@ -61,7 +61,8 @@ from archaeological_finds.forms_treatments import TreatmentSelect, \ AdministrativeActTreatmentFileFormSelection, \ AdministrativeActTreatmentFileModifForm, SourceTreatmentFormSelection, \ SourceTreatmentFileFormSelection, TreatmentSourceFormSelection, \ - TreatmentFileSourceFormSelection, DashboardForm as DashboardTreatmentForm + TreatmentFileSourceFormSelection, DashboardForm as DashboardTreatmentForm, \ + DashboardTreatmentFileForm __all__ = [ 'TreatmentSelect', 'TreatmentFormSelection', 'BaseTreatmentForm', @@ -76,6 +77,7 @@ __all__ = [ 'AdministrativeActTreatmentFileModifForm', 'SourceTreatmentFormSelection', 'SourceTreatmentFileFormSelection', 'TreatmentSourceFormSelection', 'TreatmentFileSourceFormSelection', 'DashboardTreatmentForm', + 'DashboardTreatmentFileForm', 'RecordFormSelection', 'FindForm', 'DateForm', 'DatingFormSet', 'FindSelect', 'FindFormSelection', 'FindFormSelectionWarehouseModule', 'MultipleFindFormSelection', 'MultipleFindFormSelectionWarehouseModule', diff --git a/archaeological_finds/forms_treatments.py b/archaeological_finds/forms_treatments.py index be62fc1d0..58429f4c9 100644 --- a/archaeological_finds/forms_treatments.py +++ b/archaeological_finds/forms_treatments.py @@ -279,10 +279,6 @@ class TreatmentDeletionForm(FinalForm): SLICING = (("month", _(u"months")), ('year', _(u"years")),) -PREVENTIVE_RESARCH = (('all', _('All')), - ('preventive', _(u"Preventive")), - ('research', _(u"Research")),) - DATE_SOURCE = (("start", _(u"Start date")), ("end", _(u"Closing date")),) @@ -306,7 +302,7 @@ class DashboardForm(forms.Form): models.TreatmentType.get_types() def get_date_source(self): - date_source = 'history' + date_source = 'start' if hasattr(self, 'cleaned_data') and \ self.cleaned_data.get('date_source'): date_source = self.cleaned_data['date_source'] @@ -532,6 +528,51 @@ class TreatmentFileDeletionForm(FinalForm): confirm_msg = _(u"Are you sure you want to delete this treatment request?") confirm_end_msg = _(u"Would you like to delete this treatment request?") +DATE_SOURCE_FILE = ( + ("creation", _(u"Creation date")), + ("reception", _(u"Reception date")), + ("end", _(u"Closing date")),) + + +class DashboardTreatmentFileForm(forms.Form): + slicing = forms.ChoiceField(label=_("Slicing"), choices=SLICING, + required=False) + date_source = forms.ChoiceField( + label=_("Date get from"), choices=DATE_SOURCE_FILE, required=False) + treatmentfile_type = forms.ChoiceField(label=_("Treatment request type"), + choices=[], required=False) + after = forms.DateField(label=_(u"Date after"), + widget=widgets.JQueryDate, required=False) + before = forms.DateField(label=_(u"Date before"), + widget=widgets.JQueryDate, required=False) + + def __init__(self, *args, **kwargs): + if 'prefix' not in kwargs: + kwargs['prefix'] = 'treatmentfiles' + super(DashboardTreatmentFileForm, self).__init__(*args, **kwargs) + self.fields['treatmentfile_type'].choices = \ + models.TreatmentFileType.get_types() + + def get_date_source(self): + date_source = 'creation' + if hasattr(self, 'cleaned_data') and \ + self.cleaned_data.get('date_source'): + date_source = self.cleaned_data['date_source'] + return date_source + + def get_filter(self): + if not hasattr(self, 'cleaned_data') or not self.cleaned_data: + return {} + fltr = {} + date_source = self.get_date_source() + if self.cleaned_data.get('treatmentfile_type'): + fltr['type__pk'] = self.cleaned_data['treatmentfile_type'] + if self.cleaned_data.get('after'): + fltr[date_source + '_date__gte'] = self.cleaned_data['after'] + if self.cleaned_data.get('before'): + fltr[date_source + '_date__lte'] = self.cleaned_data['before'] + return fltr + class AdministrativeActTreatmentFileSelect(TableSelect): year = forms.IntegerField(label=_("Year")) diff --git a/ishtar_common/templates/ishtar/dashboards/dashboard_main_detail.html b/ishtar_common/templates/ishtar/dashboards/dashboard_main_detail.html index c3a8a58a8..2650282ca 100644 --- a/ishtar_common/templates/ishtar/dashboards/dashboard_main_detail.html +++ b/ishtar_common/templates/ishtar/dashboards/dashboard_main_detail.html @@ -178,7 +178,7 @@ $('#search_{{unique_id}}').click(function (){ return false; }); -{% if item_name == 'files' or item_name == "operations" or item_name == "treatments" or item_name == "treatment_types" %} +{% if item_name == 'files' or item_name == "operations" or item_name == "treatments" or item_name == "treatmentfiles" %} load_jquerydate_{{item_name}}_after(); load_jquerydate_{{item_name}}_before(); {% endif %} diff --git a/ishtar_common/views.py b/ishtar_common/views.py index 4aa452641..94e4c1582 100644 --- a/ishtar_common/views.py +++ b/ishtar_common/views.py @@ -63,7 +63,8 @@ from archaeological_finds.models import Find, Treatment, TreatmentFile, \ from archaeological_operations.forms import DashboardForm as DashboardFormOpe from archaeological_files.forms import DashboardForm as DashboardFormFile -from archaeological_finds.forms import DashboardTreatmentForm +from archaeological_finds.forms import DashboardTreatmentForm, \ + DashboardTreatmentFileForm from ishtar_common.forms import FinalForm, FinalDeleteForm from ishtar_common.widgets import JQueryAutoComplete @@ -1461,7 +1462,8 @@ def dashboard_main(request, dct, obj_id=None, *args, **kwargs): DASHBOARD_FORMS = { 'files': DashboardFormFile, 'operations': DashboardFormOpe, - 'treatments': DashboardTreatmentForm + 'treatments': DashboardTreatmentForm, + 'treatmentfiles': DashboardTreatmentFileForm } @@ -1478,9 +1480,9 @@ def dashboard_main_detail(request, item_name): slicing, date_source, fltr, show_detail = 'year', None, {}, False profile = models.get_current_profile() has_form = (item_name == 'files' and profile.files) \ - or item_name == 'operations' \ - or (item_name in ('treatmentfiles', 'treatments') - and profile.warehouse) + or item_name == 'operations' \ + or (item_name in ('treatmentfiles', 'treatments') + and profile.warehouse) if has_form: slicing = 'month' if item_name in DASHBOARD_FORMS: -- cgit v1.2.3 From d5664fbc9754e987f124444f9dcc02e46d20e0ad Mon Sep 17 00:00:00 2001 From: Étienne Loks Date: Thu, 13 Apr 2017 12:23:27 +0200 Subject: get_item: refactoting of access control check --- ishtar_common/models.py | 38 ++++++++++++++++++++++++++++++++++++++ ishtar_common/views.py | 31 +++++-------------------------- 2 files changed, 43 insertions(+), 26 deletions(-) (limited to 'ishtar_common/views.py') diff --git a/ishtar_common/models.py b/ishtar_common/models.py index 44bc138eb..77b4ed335 100644 --- a/ishtar_common/models.py +++ b/ishtar_common/models.py @@ -90,6 +90,44 @@ def post_save_user(sender, **kwargs): post_save.connect(post_save_user, sender=User) +def check_model_access_control(request, model, available_perms=None): + """ + Check access control to a model for a specific request + + :param request: the current request + :param model: the concerned model + :param available_perms: specific permissions to check if not specified + "view" and "view_own" will be checked + :return: (allowed, own) tuple + """ + own = True # more restrictive by default + allowed = False + if not request.user.is_authenticated(): + return allowed, own + + if not available_perms: + available_perms = ['view_' + model.__name__.lower(), + 'view_own_' + model.__name__.lower()] + if request.user.ishtaruser.has_right('administrator', + session=request.session): + allowed = True + own = False + return allowed, own + for perm, lbl in model._meta.permissions: + if perm not in available_perms: + continue + cperm = model._meta.app_label + '.' + perm + if request.user.has_perm(cperm) \ + or cperm in request.user.get_all_permissions() \ + or request.user.ishtaruser.has_right( + perm, session=request.session): + allowed = True + if "_own_" not in perm: + own = False + break # max right reach + return allowed, own + + class Imported(models.Model): imports = models.ManyToManyField( 'Import', blank=True, null=True, diff --git a/ishtar_common/views.py b/ishtar_common/views.py index 94e4c1582..3cd00a6a6 100644 --- a/ishtar_common/views.py +++ b/ishtar_common/views.py @@ -586,47 +586,26 @@ def get_item(model, func_name, default_name, extra_request_keys=[], """ def func(request, data_type='json', full=False, force_own=False, col_names=None, **dct): - # check rights - own = True # more restrictive by default - allowed = False + available_perms = [] if specific_perms: available_perms = specific_perms[:] - else: - available_perms = ['view_' + model.__name__.lower(), - 'view_own_' + model.__name__.lower()] EMPTY = '' if 'type' in dct: data_type = dct.pop('type') if not data_type: EMPTY = '[]' data_type = 'json' - if not request.user.is_authenticated(): + + allowed, own = models.check_model_access_control(request, model, + available_perms) + if not allowed: return HttpResponse(EMPTY, mimetype='text/plain') - if request.user.ishtaruser.has_right('administrator', - session=request.session): - allowed = True - own = False - else: - for perm, lbl in model._meta.permissions: - if perm not in available_perms: - continue - cperm = model._meta.app_label + '.' + perm - if request.user.has_perm(cperm) \ - or cperm in request.user.get_all_permissions() \ - or request.user.ishtaruser.has_right( - perm, session=request.session): - allowed = True - if "_own_" not in perm: - own = False - break # max right reach if force_own: own = True if full == 'shortcut' and 'SHORTCUT_SEARCH' in request.session and \ request.session['SHORTCUT_SEARCH'] == 'own': own = True - if not allowed: - return HttpResponse(EMPTY, mimetype='text/plain') # get defaults from model if not extra_request_keys and hasattr(model, 'EXTRA_REQUEST_KEYS'): -- cgit v1.2.3 From 1b642d737b55c20ea2b83afbf63d701acd25fc00 Mon Sep 17 00:00:00 2001 From: Étienne Loks Date: Thu, 13 Apr 2017 12:52:12 +0200 Subject: Access control: fix show own item (not *all* items) (refs #3593) --- ishtar_common/models.py | 2 +- ishtar_common/views.py | 12 ++++++++++-- 2 files changed, 11 insertions(+), 3 deletions(-) (limited to 'ishtar_common/views.py') diff --git a/ishtar_common/models.py b/ishtar_common/models.py index 77b4ed335..f1de8c60a 100644 --- a/ishtar_common/models.py +++ b/ishtar_common/models.py @@ -125,7 +125,7 @@ def check_model_access_control(request, model, available_perms=None): if "_own_" not in perm: own = False break # max right reach - return allowed, own + return allowed, own class Imported(models.Model): diff --git a/ishtar_common/views.py b/ishtar_common/views.py index 3cd00a6a6..f185576ea 100644 --- a/ishtar_common/views.py +++ b/ishtar_common/views.py @@ -1192,10 +1192,18 @@ def display_item(model, extra_dct=None, show_url=None): def show_item(model, name, extra_dct=None): def func(request, pk, **dct): + allowed, own = models.check_model_access_control(request, model) + if not allowed: + return HttpResponse('', content_type="application/xhtml") + q = model.objects + if own: + query_own = model.get_query_owns(request.user) + if query_own: + q = q.filter(query_own) try: - item = model.objects.get(pk=pk) + item = q.get(pk=pk) except ObjectDoesNotExist: - return HttpResponse(None) + return HttpResponse('NOK') doc_type = 'type' in dct and dct.pop('type') url_name = u"/".join(reverse('show-' + name, args=['0', ''] ).split('/')[:-2]) + u"/" -- cgit v1.2.3