Skip to content

Instantly share code, notes, and snippets.

@Rustem
Created April 24, 2014 10:02
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Rustem/11248949 to your computer and use it in GitHub Desktop.
Save Rustem/11248949 to your computer and use it in GitHub Desktop.
Ex: filtering in django.
# -*- coding: utf-8 -*-
from synergy.forms import SearchForm
from synergy.models import add_look, SynergyBook
from synergy.synergy_backend import synergy
from synergy.dictionaries import *
from synergy.utils import synergy_data
from django.conf import settings
from django.http import HttpResponse, HttpResponseRedirect
from django.views.generic.base import TemplateView
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
from django.core.urlresolvers import reverse
from django.core.exceptions import ImproperlyConfigured
from django.shortcuts import render
from django.contrib import messages
from django.utils.translation import ugettext_lazy as _
PUB_YEAR = '210d'
FROM_PUB_YEAR = '210d_0'
TO_PUB_YEAR = '210d_1'
MAIN_TEXT_LANG = '101a'
ERESOURCE_ADDR = '8562'
SEARCH_PARAM = 'search'
COLLECTIVE_AUTHOR = '701b'
PARALLEL_TITLE = '200d'
COMMON_NOTES = '300a'
KEYWORD = '610a'
INITIAL_ELEMENT_BBK = '907a'
ISBN = '010a'
PUBLISHING_PLACE = '210a'
PUBLICATION_OFFICE = '210c'
class SynergySearchBackend(object):
FILTER_PARAMS = {
FROM_PUB_YEAR: 'pub_year',
MAIN_TEXT_LANG: '',
ERESOURCE_ADDR: '',
SEARCH_PARAM: 'search',
COLLECTIVE_AUTHOR: '',
PARALLEL_TITLE: '',
PUB_YEAR: '',
COMMON_NOTES: '',
KEYWORD: '',
INITIAL_ELEMENT_BBK: '',
ISBN: '',
PUBLISHING_PLACE: '',
PUBLICATION_OFFICE: ''
}
SEARCH_TYPES = (PARTIAL, EXACT) = ('partial', 'exact')
DEFAULT_POSTS_PER_PAGE = 15
def __init__(self, request):
self.request = request
self.idx = None
def search(self, **kwargs):
r"""Makes Synergy search by applying:
#. set search param
#. all required filters
Finally returns django view context.
Kwargs parameters
-----------------
posts_per_page::int - determines how much books
is visible on single page
"""
form_uuids = self.request.GET.getlist('formUUID', [])
if not form_uuids:
raise ImproperlyConfigured(_("No formUUID provided."))
posts_per_page = kwargs.get(
'posts_per_page', self.DEFAULT_POSTS_PER_PAGE)
default_req_id = form_uuids and form_uuids[0] or None
req_id = self.request.GET.get('req_id', default_req_id)
books, current_data_uuids, registries = [], [], {}
for form_uuid, catalog_name in settings.FORM_BIG:
registries[form_uuid] = {
'formUUID': form_uuid,
'name': catalog_name,
'amount': 0
}
global_params = {
'username': settings.SYNERGY_ADMIN,
'password': settings.SYNERGY_ADMIN_PASSWORD
}
for form_uuid in form_uuids:
request_data = dict(global_params.items() + self.apply_filters(
form_uuid).items())
found_data_uuids = synergy.search(**request_data)
registries[form_uuid].update({
'amount': len(found_data_uuids)
})
if form_uuid == req_id:
current_data_uuids = found_data_uuids
self.reset_search()
offset_pages = int(self.request.GET.get('page', '1'))
from_page = (offset_pages - 1) * posts_per_page + 1
st, fn = from_page - 1, from_page + posts_per_page - 1
for uuid in current_data_uuids[st:fn]:
try:
doc = SynergyBook.get(uuid)
except SynergyBook.DoesNotExist:
doc = synergy.get_form_data(
fuckin_bullshit_id=uuid,
dataUUID=uuid,
username=settings.SYNERGY_ADMIN,
password=settings.SYNERGY_ADMIN_PASSWORD)
doc = SynergyBook.save_from_synergy(doc)
books.append(doc)
paginator = Paginator(current_data_uuids, posts_per_page)
try:
current_data_uuids = paginator.page(offset_pages)
except PageNotAnInteger:
current_data_uuids = paginator.page(1)
from_page = 1
except EmptyPage:
current_data_uuids = paginator.page(paginator.num_pages)
from_page = (paginator.num_pages - 1) * posts_per_page + 1
return {
"registries": registries.values(),
"books": books,
"paginator": paginator,
"from_page": from_page,
"req_id": req_id,
"current_data_uuids": current_data_uuids}
def apply_filters(self, form_uuid):
r"""Applies all possible filters that are required
according to talk with Arta Synergy. Returns dictionary of
parameters that is ready to be used by ~`synergy_backend`."""
request_data = {}
for k in self.request.GET:
if not (k in self.FILTER_PARAMS and self.request.GET.get(k, None)):
continue
fn_name = 'by_{}'.format(self.FILTER_PARAMS.get(k))
if hasattr(self, fn_name):
fn = getattr(self, fn_name)
request_data.update(fn(
form_uuid, self.request.GET.get(k, None)))
else:
request_data.update(self.search_param(
self.request.GET.get(k, None),
k, form_uuid, search_tp='exact'))
return request_data
def search_param(self, search, field, formUUID, **kwargs):
r"""According to synergy search protocol, applies param
set for search by particular field."""
search_tp = kwargs.get('search_tp', 'exact')
cur_idx = self.idx and str(self.idx) or ''
rv = {
'search{}': search,
'field{}': field,
'formUUID{}': formUUID,
'type{}': search_tp
}
self.idx = 1 if not self.idx else self.idx + 1
return {k.format(cur_idx): v for k, v in rv.items()}
def reset_search(self):
self.idx = None
def by_search(self, formUUID, data):
if not data:
raise ImproperlyConfigured(_("Provide search string."))
field_ids = list(
field_id for field_id, _ in settings.SYNERGY_SEARCH_FIELDS)
return self.search_param(data, field_ids,
formUUID, search_tp='partial')
def by_pub_year(self, formUUID, data):
from_year, to_year = (
self.request.GET.get(FROM_PUB_YEAR, None),
self.request.GET.get(TO_PUB_YEAR, None))
if not from_year and to_year:
from_year = 1950
if from_year and not to_year:
to_year = 2022
if from_year and to_year:
from_year, to_year = int(from_year), int(to_year)
if from_year and to_year and from_year > to_year:
raise ImproperlyConfigured(
_('date ranges must be from begin to end'))
if not (from_year and to_year):
return {}
return self.search_param(data, PUB_YEAR, formUUID, search_tp='exact')
def search(request, template_name='', **kwargs):
template_name = template_name or 'synergy/search_res.html'
ssb = SynergySearchBackend(request)
search_form = SearchForm(
data=dict(((k, request.GET.get(k, '')) for k in request.GET)),
user=request.user)
try:
view_context = ssb.search()
except ImproperlyConfigured, e:
messages.error(request, e.message)
return render(request, template_name, {
'registries': [],
'books': [],
'search_form': SearchForm(data=request.GET)
})
else:
view_context.update({
'search_form': search_form
})
return render(request, template_name, view_context)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment