diff options
Diffstat (limited to 'ishtar_common')
-rw-r--r-- | ishtar_common/static/js/ishtar.js | 32 | ||||
-rw-r--r-- | ishtar_common/templates/base.html | 1 | ||||
-rw-r--r-- | ishtar_common/templates/blocks/DataTables.html | 20 | ||||
-rw-r--r-- | ishtar_common/templates/ishtar/blocks/base_shortcut_menu.html | 4 | ||||
-rw-r--r-- | ishtar_common/templates/ishtar/wizard/search.html | 8 | ||||
-rw-r--r-- | ishtar_common/urls.py | 6 | ||||
-rw-r--r-- | ishtar_common/utils.py | 3 | ||||
-rw-r--r-- | ishtar_common/views.py | 50 | ||||
-rw-r--r-- | ishtar_common/views_item.py | 17 | ||||
-rw-r--r-- | ishtar_common/wizards.py | 22 |
10 files changed, 149 insertions, 14 deletions
diff --git a/ishtar_common/static/js/ishtar.js b/ishtar_common/static/js/ishtar.js index a71450fab..60840bcf8 100644 --- a/ishtar_common/static/js/ishtar.js +++ b/ishtar_common/static/js/ishtar.js @@ -38,7 +38,10 @@ function manage_async_link(event){ function get_next_table_id(){} function get_previous_table_id(){} +var datatable_submit_search = function() {}; + var shortcut_url = ''; +var alert_url = ''; var datatables_i18n; var current_modal; @@ -222,6 +225,7 @@ function load_shortcut_menu(opened){ cache: false, success:function(html){ init_shortcut_menu(html); + load_alerts(); if(opened){ $("#dropdown-toggle-shortcut-menu").click(); } @@ -232,6 +236,34 @@ function load_shortcut_menu(opened){ }); } +var load_alerts = function(){ + if (!alert_url) return; + $('.modal-progress').modal('show'); + $.ajax({ + url: alert_url, + cache: false, + success:function(json){ + $('.modal-progress').modal('hide'); + var html = ""; + for (idx in json["alerts"]){ + var b = json["alerts"][idx]; + var url = "/bookmark/" + b["query_id"] + "/" ; + html += '<a class="badge badge-secondary" href="' + url + '">'; + html += b["label"]; + html += ' <span class="badge badge-light">'; + html += b["number"]; + html += '</span>'; + html += '</a> '; + } + $("#alert-list").html(html); + }, + error:function(XMLHttpRequest, textStatus, errorThrows){ + close_wait(); + }, + dataType: 'json' + }); +} + function dynamic_load(url, target){ $.ajax({ url: url, diff --git a/ishtar_common/templates/base.html b/ishtar_common/templates/base.html index 40e30706c..72c6a9b65 100644 --- a/ishtar_common/templates/base.html +++ b/ishtar_common/templates/base.html @@ -30,6 +30,7 @@ {{EXTRA_JS|safe}} <script type='text/javascript'> var shortcut_url = '{% url "shortcut-menu" %}'; + var alert_url = '{% url "alert-list" %}'; var get_file_url = '{% url "get-file-shortcut" %}'; var get_operation_url = '{% url "get-operation-shortcut" %}'; var get_contextrecord_url = '{% url "get-contextrecord-shortcut" %}'; diff --git a/ishtar_common/templates/blocks/DataTables.html b/ishtar_common/templates/blocks/DataTables.html index 0ae6ba7d0..c3ca16395 100644 --- a/ishtar_common/templates/blocks/DataTables.html +++ b/ishtar_common/templates/blocks/DataTables.html @@ -99,8 +99,9 @@ $('#modal_grid_{{name}}').on('hide.bs.modal', function (e) { var query_vars = new Array({{col_idx|safe}}); var selItems_{{sname}} = new Array(); -jQuery(document).ready(function(){ - jQuery("#search_{{name}}").click(function (){ + + +datatable_submit_search = function(){ $("#id_search_vector").removeClass('input-progress'); if ($('.modal-progress').length > 0){ $('.modal-progress').modal('show'); @@ -137,11 +138,22 @@ jQuery(document).ready(function(){ $('.modal-progress').modal('hide'); } return false; - }); +}; + + + +jQuery(document).ready(function(){ + jQuery("#search_{{name}}").click(datatable_submit_search); + + var base_source = "{{source}}"; + + if (default_search_vector){ + base_source += "?search_vector=" + default_search_vector; + } datatable_options = { "ajax": { - "url": "{{source}}", + "url": base_source, "dataSrc": function (json) { manage_pinned_search("{{name}}", json); return json.rows; diff --git a/ishtar_common/templates/ishtar/blocks/base_shortcut_menu.html b/ishtar_common/templates/ishtar/blocks/base_shortcut_menu.html index 6faf37670..77ef9804b 100644 --- a/ishtar_common/templates/ishtar/blocks/base_shortcut_menu.html +++ b/ishtar_common/templates/ishtar/blocks/base_shortcut_menu.html @@ -8,7 +8,9 @@ <span class="navbar-toggler-icon"></span> </button> {% endcomment %} -<div class="navbar-collapse collapse justify-content-end"> +<div class="navbar-collapse collapse justify-content-between"> + <span id="alert-list"> + </span> <ul class="navbar-nav" id="navbar-shortcut"> <li class="nav-item"> <ol class="breadcrumb"> diff --git a/ishtar_common/templates/ishtar/wizard/search.html b/ishtar_common/templates/ishtar/wizard/search.html index eebd58d89..a7a6faec7 100644 --- a/ishtar_common/templates/ishtar/wizard/search.html +++ b/ishtar_common/templates/ishtar/wizard/search.html @@ -5,6 +5,14 @@ {% endblock %} {% block content %} <h3>{{wizard_label}}</h3> +{% if default_search_vector %} +<script type="text/javascript"> + var default_search_vector = "{{default_search_vector|safe}}".replace(/''/g, '"'); + $(document).ready(function() { + $("#id_search_vector").val(default_search_vector.replace(/''/g, '"')); + }); +</script> +{% endif %} {% comment %} <nav aria-label="breadcrumb" role="navigation"> diff --git a/ishtar_common/urls.py b/ishtar_common/urls.py index 44ebd0f93..ee1b3805e 100644 --- a/ishtar_common/urls.py +++ b/ishtar_common/urls.py @@ -128,8 +128,10 @@ urlpatterns = [ views.SearchQueryEdit.as_view(), name='save-search-query'), url(r'^bookmarks/(?P<app_label>[a-z-]+)/(?P<model>[a-z-]+)/$', - views.BookmarkList.as_view(), - name='bookmark-list'), + views.BookmarkList.as_view(), name='bookmark-list'), + url(r'^bookmark/(?P<pk>[0-9]+)/$', + views.get_bookmark, name='bookmark'), + url(r'^alerts/$', views.AlertList.as_view(), name='alert-list'), url(r'^success(?:/(?P<context>[a-z-]+))?/$', TemplateView.as_view(template_name="ishtar/forms/success.html"), name='success'), diff --git a/ishtar_common/utils.py b/ishtar_common/utils.py index 34d170892..0e5dd286a 100644 --- a/ishtar_common/utils.py +++ b/ishtar_common/utils.py @@ -794,7 +794,8 @@ def create_default_json_fields(model): ) -def get_urls_for_model(model, views, own=False, autocomplete=False): +def get_urls_for_model(model, views, own=False, autocomplete=False, + ): """ Generate get and show url for a model """ diff --git a/ishtar_common/views.py b/ishtar_common/views.py index 1f8b46fd6..c713b9972 100644 --- a/ishtar_common/views.py +++ b/ishtar_common/views.py @@ -21,6 +21,7 @@ import csv import datetime import json import logging +import importlib import unicodedata import unicodecsv @@ -1676,6 +1677,19 @@ document_deletion_wizard = wizards.DocumentDeletionWizard.as_view( url_name='document_deletion',) +def get_bookmark(request, pk): + try: + sq = models.SearchQuery.objects.get( + pk=pk, + profile__person__ishtaruser__user_ptr=request.user) + except models.SearchQuery.DoesNotExist: + raise Http404() + slug = sq.content_type.model_class().SLUG + return redirect( + reverse(slug + '_search') + "?bookmark={}".format(sq.pk) + ) + + class SearchQueryMixin(object): """ Manage content type and profile init @@ -1736,3 +1750,39 @@ class BookmarkList(SearchQueryMixin, JSONResponseMixin, LoginRequiredMixin, 'bookmarks': [ {'label': sq.label, 'query': sq.query} for sq in q.all()] } + + +class AlertList(JSONResponseMixin, LoginRequiredMixin, + TemplateView): + def dispatch(self, request, *args, **kwargs): + if not request.user.pk: + raise Http404() + try: + self.profile = models.UserProfile.objects.get( + current=True, person__ishtaruser__user_ptr=request.user) + except models.UserProfile.DoesNotExist: + # no current profile + raise Http404() + return super(AlertList, self).dispatch(request, *args, **kwargs) + + def get_data(self, context): + q = models.SearchQuery.objects.filter( + profile=self.profile, + is_alert=True + ) + alerts = [] + for sq in q.all(): + model = sq.content_type.model_class() + module = model.__module__.split('.')[0] + views = importlib.import_module(module + '.views') + get_view = getattr(views, "get_" + model.SLUG) + nb = get_view( + self.request, + query={'search_vector': sq.query}, + count=True + ) + alerts.append( + {'label': sq.label, 'query_id': sq.pk, + 'number': nb} + ) + return {'alerts': alerts} diff --git a/ishtar_common/views_item.py b/ishtar_common/views_item.py index 854c91ce5..85ef5339a 100644 --- a/ishtar_common/views_item.py +++ b/ishtar_common/views_item.py @@ -12,7 +12,6 @@ from tempfile import NamedTemporaryFile from django.conf import settings from django.contrib.gis.geos import GEOSException -from django.contrib.postgres.search import SearchQuery from django.contrib.staticfiles.templatetags.staticfiles import static from django.core.exceptions import ObjectDoesNotExist from django.core.urlresolvers import reverse, NoReverseMatch @@ -821,14 +820,22 @@ def get_item(model, func_name, default_name, extra_request_keys=[], (hasattr(field, 'rel') and field.rel and '__pk' or '')) for field in associated_fields])) request_keys.update(my_extra_request_keys) - request_items = request.method == 'POST' and request.POST \ - or request.GET + + if "query" in dct: + request_items = dct["query"] + elif request.method == 'POST': + request_items = request.POST + else: + request_items = request.GET + + count = dct.get('count', False) # pager try: row_nb = int(request_items.get('length')) except (ValueError, TypeError): row_nb = DEFAULT_ROW_NUMBER + dct_request_items = {} # filter requested fields @@ -839,6 +846,7 @@ def get_item(model, func_name, default_name, extra_request_keys=[], if key.startswith('searchprefix_'): key = key[len('searchprefix_'):] dct_request_items[key] = request_items[k] + request_items = dct_request_items dct = my_base_request @@ -985,6 +993,9 @@ def get_item(model, func_name, default_name, extra_request_keys=[], items = items.extra(**extra) items = items.distinct() + + if count: + return items.count() # print(items.query) if search_vector: # for serialization diff --git a/ishtar_common/wizards.py b/ishtar_common/wizards.py index 4a55345d2..b1e0c7fd2 100644 --- a/ishtar_common/wizards.py +++ b/ishtar_common/wizards.py @@ -1413,9 +1413,25 @@ class SearchWizard(IshtarWizard): context = super(SearchWizard, self).get_context_data(form) self.request.session['CURRENT_ACTION'] = self.get_wizard_name() current_step = self.steps.current - context.update({'current_step': self.form_list[current_step], - 'is_search': True, - 'wizard_label': self.get_label()}) + bookmark = self.request.GET.get('bookmark', None) + default_search_vector = None + if bookmark: + try: + app_label = self.model.__module__.split('.')[0] + sq = models.SearchQuery.objects.get( + pk=bookmark, + content_type__app_label=app_label, + content_type__model=self.model.SLUG, + profile__person__ishtaruser__user_ptr=self.request.user + ) + default_search_vector = sq.query.replace('"', "''") + except models.SearchQuery.DoesNotExist: + pass + context.update({ + 'current_step': self.form_list[current_step], + 'is_search': True, 'wizard_label': self.get_label(), + 'default_search_vector': default_search_vector + }) return context |