Merge branch 'stage5' of bitbucket.org:Bonus_05/expomap into stage5

remotes/origin/stage5
ya_dim4ik 10 years ago
commit 6273ba1f03
  1. 2
      conference/search_indexes.py
  2. 227
      events/forms.py
  3. 3
      events/views.py
  4. 2
      exposition/search_indexes.py
  5. 4
      functions/custom_views.py
  6. 6
      functions/search_mixin.py
  7. 215
      schema_22.08.2016.xml
  8. 4
      schema_new.xml
  9. 1
      templates/client/blank.html

@ -27,6 +27,8 @@ class ConferenceIndex(indexes.SearchIndex, indexes.Indexable, ExpoSearchMixin):
members_choice = indexes.IntegerField()
visitors_choice = indexes.IntegerField()
price_choice = indexes.IntegerField()
expohit = indexes.BooleanField(model_attr='expohit')
rating = indexes.MultiValueField()
def prepare_form_name(self, obj):
return None

@ -1,6 +1,7 @@
# -*- coding: utf-8 -*-
import re
from itertools import chain
import operator
from itertools import chain, combinations
from collections import namedtuple
from datetime import datetime
from datetime import timedelta
@ -47,7 +48,7 @@ class FilterCheckboxSelectMultiple(forms.CheckboxSelectMultiple):
if value is None: value = []
has_id = attrs and 'id' in attrs
final_attrs = self.build_attrs(attrs, name=name)
output = ['<ul>']
output = ['<ul>' if not self.is_hidden else '<ul style="display: none;">']
# Normalize to strings
str_values = set([force_text(v) for v in value])
for i, (option_value, option_label) in enumerate(chain(self.choices, choices)):
@ -165,12 +166,20 @@ values_mapping = {
}
RATING = (
(1, _(u'Топовые (HIT)')),
(2, _(u'Члены РСВЯ')),
(3, _(u'Члены UFI')),
(4, _(u'ExpoRating')),
('r1', _(u'Топовые (HIT)')),
('r2', _(u'Члены РСВЯ')),
('r3', _(u'Члены UFI')),
('r4', _(u'ExpoRating')),
)
rating_mapping = [
{'value': 'r1', 'db_value': 1, 'label': _(u'Топовые (HIT)'), 'field': 'expohit'},
{'value': 'r2', 'db_value': int(Exposition.quality_label.ufi), 'label': _(u'Члены РСВЯ'), 'field': 'quality_label'},
{'value': 'r3', 'db_value': int(Exposition.quality_label.rsva), 'label': _(u'Члены UFI'), 'field': 'quality_label'},
{'value': 'r4', 'db_value': int(Exposition.quality_label.exporating), 'label': _(u'ExpoRating'), 'field': 'quality_label'},
]
monthes_abr_to_num = {v.lower(): k for k, v in enumerate(calendar.month_abbr)}
monthes_num_to_abr = {v: k for k, v in monthes_abr_to_num.iteritems()}
year_month_regex = re.compile(r'^((?P<year>\d{4})(?P<month>\w{3}))|((?P<month_>\d{1,2})/(?P<year_>\d{4}))$')
@ -248,10 +257,11 @@ class FilterForm(forms.Form):
choices=VISITORS,
required=False, widget=FilterCheckboxSelectMultiple())
rating = FilterTypedMultipleChoiceField(
label=_(u'Рейтинги'), coerce=int,
label=_(u'Рейтинги'), coerce=str,
choices=RATING,
required=False, widget=FilterCheckboxSelectMultiple())
query = forms.CharField(required=False, widget=forms.HiddenInput())
where_query = forms.CharField(required=False, widget=forms.HiddenInput())
def __init__(self, *args, **kwargs):
super(FilterForm, self).__init__(*args, **kwargs)
@ -314,7 +324,7 @@ class FilterForm(forms.Form):
return year
def clean_default_month(self):
v = self.cleaned_data.get('default_month')
v = self.cleaned_data.get('default_month')
if v and v in settings.MONTHES.keys():
self.fields['month'].default_month = v
return v
@ -353,19 +363,32 @@ class FilterForm(forms.Form):
# print(new_values, self.data)
return new_values
def clean_rating(self):
types = self.cleaned_data.get('event_type')
if TYPES.CONF in types and not TYPES.EXPO in types:
self.fields['rating'].widget.input_type = 'hidden'
self.fields['rating'].widget.is_hidden = True
# self.fields['rating'].widget = forms.HiddenInput()
return []
return self.cleaned_data.get('rating')
def clean_visitors(self):
types = self.cleaned_data.get('event_type')
if TYPES.CONF in types and not TYPES.EXPO in types:
self.fields['visitors'].widget.input_type = 'hidden'
self.fields['visitors'].widget.is_hidden = True
# self.fields['visitors'].widget = forms.HiddenInput()
return []
return self.cleaned_data.get('visitors')
def _post_clean(self):
# нужно для того, чтобы год зашел в поле month
# print(self.get_date_begin_periods())
if not self.cleaned_data.get('default_month') and self.fields['month'].default_month:
self.data['default_month'] = self.fields['month'].default_month
year = self.cleaned_data.get('year')
# if year:
# for val, name in self.fields['month'].additional_choices:
# self.
# additional_choices
# year = self.cleaned_data.get('year')
def is_valid(self):
# if getattr(self, '_is_valid', None) is None:
self._is_valid = super(FilterForm, self).is_valid()
# нам нужно сбрасывать сохраненный выбор моделей,
@ -383,7 +406,18 @@ class FilterForm(forms.Form):
self._models.append(Exposition)
if TYPES.CONF in val:
self._models.append(Conference)
return self._models or [Exposition, Conference]
if not self._models:
self._models = [Exposition, Conference]
if self.cleaned_data.get('query') or self.cleaned_data.get('where_query'):
exclude_models = []
for model in self._models:
values = self.filter(load_all=False, models=[model]).values_list('pk', flat=True)
if values:
setattr(self, 'query_{model}_ids'.format(model=model.__name__), map(int, values))
else:
exclude_models.append(model)
self._models = list(filter(lambda x: x not in exclude_models, self._models))
return self._models
@property
def lookup_kwargs(self):
@ -415,10 +449,10 @@ class FilterForm(forms.Form):
self._lookup_kwargs['price_choice__in'] = d.get('price')
return self._lookup_kwargs
def filter(self, qs=None):
qs = qs or self.default_filter()
def filter(self, qs=None, load_all=True, models=None):
qs = qs or self.default_filter(load_all=load_all, _models=models)
# lookup_kwargs = dict(ChainMap({}, *(lookup_kwargs or self.lookup_kwargs).values()))
qs = self.make_data_begin_filter(qs)
qs = self.make_cleaned_sqs_filter(qs)
return qs.filter(**self.lookup_kwargs).order_by('data_begin')
def default_filter(self, load_all=True, _models=None):
@ -432,10 +466,19 @@ class FilterForm(forms.Form):
qs = qs.filter(data_begin__gte=datetime.now().date())
return qs
def make_data_begin_filter(self, qs):
params = self.make_date_begin_sqs_params()
if params is not None:
qs = qs.filter(params)
def make_cleaned_sqs_filter(self, qs):
date_params = self.make_date_begin_sqs_params()
if date_params is not None:
qs = qs.filter(date_params)
rating_params = self.make_rating_sqs_params()
if rating_params is not None:
qs = qs.filter(rating_params)
query = self.cleaned_data.get('query')
if query:
qs = qs.autocomplete(content_auto=query)
where_query = self.cleaned_data.get('where_query')
if where_query:
qs = qs.filter(where__contains=where_query)
return qs
def recalculate_choices(self):
@ -470,26 +513,27 @@ class FilterForm(forms.Form):
# для того чтобы взяло чойсы из новых результатов
self.fields[field].cache_choices = False
self.fields[field].choice_cache = None
print(self.fields[field].queryset.query)
# print(self.fields[field].queryset.query)
for field in ['members', 'visitors', 'price']:
self.fields[field].choices = self.make_local_field_count(field) or self.fields[field].choices
self.fields['month'].choices = self.make_date_begin_counts()
self.fields['rating'].choices = self.make_rating_counts()
self.make_event_type_choices_count()
# self.fields['month'].choices = self.month_choices()
# for field in self.fields:
# field = self.fields[field]
# if hasattr(field, 'queryset'):
# field.queryset = field.queryset[:15]
for field in self.fields:
field = self.fields[field]
if hasattr(field, 'queryset'):
field.queryset = field.queryset[:150]
def make_event_type_choices_count(self):
types = {1: Exposition, 2: Conference}
choices = []
for _type, label in TYPES:
qs = self.default_filter(load_all=False, _models=[types.get(_type)])
qs = self.make_data_begin_filter(qs)
qs = self.make_cleaned_sqs_filter(qs)
count = qs.filter(**self.lookup_kwargs).count()
choices.append((_type, label + ' <i>({count})</i>'.format(count=count)))
self.fields['event_type'].choices = choices
@ -548,6 +592,16 @@ class FilterForm(forms.Form):
'''`{db_table}`.`{attname}` IN {val}'''\
.format(**_format_kwargs))
# if self.cleaned_data.get('query') or self.cleaned_data.get('where_query'):
values = getattr(self, 'query_{model}_ids'.format(model=model.__name__), [])
# values = self.filter(load_all=False, models=[model]).values_list('pk', flat=True)
if values:
where.append(
'''`{db_table}`.`id` IN {val}'''\
.format(
db_table=model._meta.db_table,
val=self.make_ids_in_sql_format(values))
)
return joins, where
def make_local_field_count(self, field):
@ -583,10 +637,11 @@ class FilterForm(forms.Form):
)
_joins, _where = self.make_joins_from_selected(field, model)
joins.extend(_joins)
where.extend(_where)
joins.extend(_joins or [])
where.extend(_where or [])
where.append(self.make_default_where(db_table=model._meta.db_table))
self.make_date_begin_where(where, db_table=model._meta.db_table)
self.make_rating_where(where, db_table=model._meta.db_table)
selects.append(select + ''.join(joins) + ' where ' + ' and '.join(where) + group_by)
@ -669,9 +724,10 @@ class FilterForm(forms.Form):
)
_joins, _where = self.make_joins_from_selected('data_begin', model)
joins.extend(_joins)
where.extend(_where)
joins.extend(_joins or [])
where.extend(_where or [])
where.append(self.make_default_where(db_table=model._meta.db_table))
self.make_rating_where(where, db_table=model._meta.db_table)
selects.append(select + ''.join(joins) + ' where ' + ' and '.join(where) + group_by)
@ -693,6 +749,64 @@ class FilterForm(forms.Form):
# with connection.cursor() as c:
return choices
def make_rating_counts(self):
choices = []
sql = ''
selects = []
for model in self.models:
joins = []
where = []
group_by = ''
format_kwargs = {
'db_table': model._meta.db_table,
'lang': self.lang,
}
cases = []
for case in filter(lambda x: x['field'] == 'expohit', rating_mapping):
cases.append(
''' sum(case when (`{db_table}`.`{field}` = {db_value}) then 1 else 0 end) as '{value}' '''\
.format(value=case['value'], field=case['field'], db_value=case['db_value'], **format_kwargs)
)
for case in filter(lambda x: x['field'] != 'expohit', rating_mapping):
cases.append(
''' sum(case when (`{db_table}`.`{field}` = `{db_table}`.`{field}` | {db_value}) then 1 else 0 end) as '{value}' '''\
.format(value=case['value'], field=case['field'], db_value=case['db_value'], **format_kwargs)
)
select = \
''' SELECT {cases} FROM `{db_table}_translation` INNER JOIN `{db_table}` ON (`{db_table}_translation`.`master_id` = `{db_table}`.`id`) '''\
.format(cases=', '.join(cases), **format_kwargs)
where.append(
''' `{db_table}_translation`.`language_code` = '{lang}' '''\
.format(**format_kwargs)
)
_joins, _where = self.make_joins_from_selected('rating', model)
joins.extend(_joins or [])
where.extend(_where or [])
where.append(self.make_default_where(db_table=model._meta.db_table))
self.make_date_begin_where(where, db_table=model._meta.db_table)
selects.append(select + ''.join(joins) + ' where ' + ' and '.join(where) + group_by)
sql = ' union '.join(selects)
choices = []
if sql:
c = connection.cursor()
try:
c.execute(sql)
mapper = namedtuple('Result', [col[0] for col in c.description])
data = [mapper(*raw) for raw in c.fetchall()]
for value, label in RATING:
count = sum([getattr(x, value, 0) or 0 for x in data])
choices.append((value, label + ' <i>({count})</i>'.format(count=count)))
finally:
c.close()
# some bug with these! AttributeError: __exit__
# with connection.cursor() as c:
return choices
def get_date_begin_periods(self):
periods = getattr(self, '_periods', None)
if periods is None:
@ -751,7 +865,7 @@ class FilterForm(forms.Form):
return None
def make_date_begin_where(self, where, db_table):
key = '_where_date_begin_where_{}'.format(db_table)
key = '_make_date_begin_where_{}'.format(db_table)
_where = getattr(self, key, None)
if _where is None:
_where = []
@ -791,9 +905,34 @@ class FilterForm(forms.Form):
_where = [''' ({}) '''.format(' OR '.join(_where))]
setattr(self, key, _where)
# print(_where)
where.extend(_where)
where.extend(_where or [])
return
def make_rating_where(self, where, db_table):
key = '_make_rating_where_{}'.format(db_table)
_where = getattr(self, key, None)
if _where is None:
cleaned = self.cleaned_data.get('rating', [])
_where = []
# choices = filter(lambda x: x['value'] in cleaned and x['field'] == 'expohit', rating_mapping)
for choice in filter(lambda x: x['field'] == 'expohit' and x['value'] in cleaned, rating_mapping):
_where.append(
''' `{db_table}`.`{field}` = {db_value} '''\
.format(field=choice['field'], db_value=choice['db_value'], db_table=db_table)
)
quality_label = []
for choice in filter(lambda x: x['field'] == 'quality_label' and x['value'] in cleaned, rating_mapping):
quality_label.append(choice['db_value'])
if quality_label:
_where.append(
''' `{db_table}`.`{field}` = `{db_table}`.`{field}` | {computed} '''\
.format(field=choice['field'], computed=reduce(operator.or_, quality_label), db_table=db_table)
)
if len(_where) > 1:
_where = [''' ({}) '''.format(' OR '.join(_where))]
setattr(self, key, _where)
where.extend(_where or [])
return
# def get_prev_month(self, date):
# year = date.year
# month = date.month
@ -894,6 +1033,19 @@ class FilterForm(forms.Form):
params |= SQ(**lookup)
return params
def make_rating_sqs_params(self):
params = None
if self.cleaned_data.get('rating'):
for choice in filter(lambda x: x['field'] == 'expohit' and x['value'] in self.cleaned_data.get('rating'), rating_mapping):
params = SQ(**{choice['field']: choice['db_value']})
quality_label = [x['db_value'] for x in filter(lambda x: x['field'] != 'expohit' and x['value'] in self.cleaned_data.get('rating'), rating_mapping)]
if quality_label:
if params is None:
params = SQ(**{'rating__in': quality_label})
else:
params |= SQ(**{'rating__in': quality_label})
return params
def make_count_select(self, field):
selects = []
case = None
@ -953,10 +1105,11 @@ class FilterForm(forms.Form):
# FILTER current by other values
_joins, _where = self.make_joins_from_selected(field, model)
joins.extend(_joins)
where.extend(_where)
joins.extend(_joins or [])
where.extend(_where or [])
where.append(self.make_default_where(db_table=model._meta.db_table))
self.make_date_begin_where(where, db_table=model._meta.db_table)
self.make_rating_where(where, db_table=model._meta.db_table)
selects.append(select + ''.join(joins) + ' where ' + ' and '.join(where) + group_by)
if len(selects) == 2:

@ -32,11 +32,12 @@ class FilterListView(ContextMixin, FormMixin, ListView):
def get_queryset(self):
if self.form.is_valid():
qs = self.form.filter()
# import pdb; pdb.set_trace()
else:
qs = self.form.default_filter()
if self.kwargs.get('with_form', True):
self.form.recalculate_choices()
print(self.form.data, self.form.cleaned_data, self.form.get_date_begin_periods())
# print(self.form.data, self.form.cleaned_data, self.form.get_date_begin_periods())
# import pdb; pdb.set_trace()
return qs

@ -28,6 +28,8 @@ class ExpositionIndex(indexes.SearchIndex, indexes.Indexable, ExpoSearchMixin):
members_choice = indexes.IntegerField()
visitors_choice = indexes.IntegerField()
price_choice = indexes.IntegerField()
expohit = indexes.BooleanField(model_attr='expohit')
rating = indexes.MultiValueField()
def prepare_form_name(self, obj):
return None

@ -413,7 +413,9 @@ class ExpoSearchView(ListView):
if form.cleaned_data.get('to'):
context['date_to'] = form.cleaned_data.get('to').strftime('%d.%m.%Y')
if form.cleaned_data.get('q'):
context['query'] = self.cleaned_data.get('q', '').strip()
context['query'] = form.cleaned_data.get('q', '').strip()
if form.cleaned_data.get('w'):
context['where_query'] = form.cleaned_data.get('w', '').strip()
else:
form = self.search_form()

@ -5,7 +5,6 @@ class ExpoSearchMixin(object):
"""
"""
def prepare_where(self, obj):
if obj.country:
country = [tr.name for tr in obj.country.translations.all()]
@ -24,7 +23,6 @@ class ExpoSearchMixin(object):
"""
return obj.get_index_text()
def prepare_area_id(self, obj):
if obj.country:
return obj.country.area.id
@ -46,7 +44,6 @@ class ExpoSearchMixin(object):
def prepare_tag(self, obj):
return [th.id for th in obj.tag.filter()]
def prepare_url(self, obj):
return obj.get_permanent_url()
@ -71,3 +68,6 @@ class ExpoSearchMixin(object):
def prepare_price_choice(self, obj):
return obj.price_choice or 0
def prepare_rating(self, obj):
q = obj.quality_label
return [x.mask for x in filter(lambda x: x.is_set == True, [getattr(q, key) for key in q.iterkeys()])]

@ -0,0 +1,215 @@
<?xml version="1.0" ?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<schema name="default" version="1.5">
<types>
<fieldtype name="string" class="solr.StrField" sortMissingLast="true" omitNorms="true"/>
<fieldType name="boolean" class="solr.BoolField" sortMissingLast="true" omitNorms="true"/>
<fieldtype name="binary" class="solr.BinaryField"/>
<!-- Numeric field types that manipulate the value into
a string value that isn't human-readable in its internal form,
but with a lexicographic ordering the same as the numeric ordering,
so that range queries work correctly. -->
<fieldType name="int" class="solr.TrieIntField" precisionStep="0" omitNorms="true" sortMissingLast="true" positionIncrementGap="0"/>
<fieldType name="float" class="solr.TrieFloatField" precisionStep="0" omitNorms="true" sortMissingLast="true" positionIncrementGap="0"/>
<fieldType name="long" class="solr.TrieLongField" precisionStep="0" omitNorms="true" sortMissingLast="true" positionIncrementGap="0"/>
<fieldType name="double" class="solr.TrieDoubleField" precisionStep="0" omitNorms="true" sortMissingLast="true" positionIncrementGap="0"/>
<fieldType name="sint" class="solr.SortableIntField" sortMissingLast="true" omitNorms="true"/>
<fieldType name="slong" class="solr.SortableLongField" sortMissingLast="true" omitNorms="true"/>
<fieldType name="sfloat" class="solr.SortableFloatField" sortMissingLast="true" omitNorms="true"/>
<fieldType name="sdouble" class="solr.SortableDoubleField" sortMissingLast="true" omitNorms="true"/>
<fieldType name="tint" class="solr.TrieIntField" precisionStep="8" omitNorms="true" positionIncrementGap="0"/>
<fieldType name="tfloat" class="solr.TrieFloatField" precisionStep="8" omitNorms="true" positionIncrementGap="0"/>
<fieldType name="tlong" class="solr.TrieLongField" precisionStep="8" omitNorms="true" positionIncrementGap="0"/>
<fieldType name="tdouble" class="solr.TrieDoubleField" precisionStep="8" omitNorms="true" positionIncrementGap="0"/>
<fieldType name="date" class="solr.TrieDateField" omitNorms="true" precisionStep="0" positionIncrementGap="0"/>
<!-- A Trie based date field for faster date range queries and date faceting. -->
<fieldType name="tdate" class="solr.TrieDateField" omitNorms="true" precisionStep="6" positionIncrementGap="0"/>
<fieldType name="point" class="solr.PointType" dimension="2" subFieldSuffix="_d"/>
<fieldType name="location" class="solr.LatLonType" subFieldSuffix="_coordinate"/>
<fieldtype name="geohash" class="solr.GeoHashField"/>
<fieldType name="text_general" class="solr.TextField" positionIncrementGap="100">
<analyzer type="index">
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.StopFilterFactory" ignoreCase="true" words="stopwords.txt" enablePositionIncrements="true" />
<!-- in this example, we will only use synonyms at query time
<filter class="solr.SynonymFilterFactory" synonyms="index_synonyms.txt" ignoreCase="true" expand="false"/>
-->
<filter class="solr.LowerCaseFilterFactory"/>
</analyzer>
<analyzer type="query">
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.StopFilterFactory" ignoreCase="true" words="stopwords.txt" enablePositionIncrements="true" />
<filter class="solr.SynonymFilterFactory" synonyms="synonyms.txt" ignoreCase="true" expand="true"/>
<filter class="solr.LowerCaseFilterFactory"/>
</analyzer>
</fieldType>
<fieldType name="text_en" class="solr.TextField" positionIncrementGap="100">
<analyzer type="index">
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.StopFilterFactory"
ignoreCase="true"
words="lang/stopwords_en.txt"
enablePositionIncrements="true"
/>
<filter class="solr.LowerCaseFilterFactory"/>
<filter class="solr.EnglishPossessiveFilterFactory"/>
<filter class="solr.KeywordMarkerFilterFactory" protected="protwords.txt"/>
<!-- Optionally you may want to use this less aggressive stemmer instead of PorterStemFilterFactory:
<filter class="solr.EnglishMinimalStemFilterFactory"/>
-->
<filter class="solr.PorterStemFilterFactory"/>
</analyzer>
<analyzer type="query">
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.SynonymFilterFactory" synonyms="synonyms.txt" ignoreCase="true" expand="true"/>
<filter class="solr.StopFilterFactory"
ignoreCase="true"
words="lang/stopwords_en.txt"
enablePositionIncrements="true"
/>
<filter class="solr.LowerCaseFilterFactory"/>
<filter class="solr.EnglishPossessiveFilterFactory"/>
<filter class="solr.KeywordMarkerFilterFactory" protected="protwords.txt"/>
<!-- Optionally you may want to use this less aggressive stemmer instead of PorterStemFilterFactory:
<filter class="solr.EnglishMinimalStemFilterFactory"/>
-->
<filter class="solr.PorterStemFilterFactory"/>
</analyzer>
</fieldType>
<fieldType name="text_ws" class="solr.TextField" positionIncrementGap="100">
<analyzer>
<tokenizer class="solr.WhitespaceTokenizerFactory"/>
</analyzer>
</fieldType>
<fieldType name="ngram" class="solr.TextField" >
<analyzer type="index">
<tokenizer class="solr.KeywordTokenizerFactory"/>
<filter class="solr.LowerCaseFilterFactory"/>
<filter class="solr.NGramFilterFactory" minGramSize="3" maxGramSize="15" />
</analyzer>
<analyzer type="query">
<tokenizer class="solr.KeywordTokenizerFactory"/>
<filter class="solr.LowerCaseFilterFactory"/>
</analyzer>
</fieldType>
<fieldType name="edge_ngram" class="solr.TextField" positionIncrementGap="1">
<analyzer type="index">
<tokenizer class="solr.WhitespaceTokenizerFactory" />
<filter class="solr.LowerCaseFilterFactory" />
<filter class="solr.WordDelimiterFilterFactory" generateWordParts="1" generateNumberParts="1" catenateWords="0" catenateNumbers="0" catenateAll="0" splitOnCaseChange="1"/>
<filter class="solr.EdgeNGramFilterFactory" minGramSize="2" maxGramSize="15" side="front" />
</analyzer>
<analyzer type="query">
<tokenizer class="solr.WhitespaceTokenizerFactory" />
<filter class="solr.LowerCaseFilterFactory" />
<filter class="solr.WordDelimiterFilterFactory" generateWordParts="1" generateNumberParts="1" catenateWords="0" catenateNumbers="0" catenateAll="0" splitOnCaseChange="1"/>
</analyzer>
</fieldType>
</types>
<fields>
<!-- general -->
<field name="id" type="string" indexed="true" stored="true" multiValued="false" required="true"/>
<field name="django_ct" type="string" indexed="true" stored="true" multiValued="false"/>
<field name="django_id" type="string" indexed="true" stored="true" multiValued="false"/>
<field name="_version_" type="long" indexed="true" stored ="true"/>
<dynamicField name="*_i" type="int" indexed="true" stored="true"/>
<dynamicField name="*_s" type="string" indexed="true" stored="true"/>
<dynamicField name="*_l" type="long" indexed="true" stored="true"/>
<dynamicField name="*_t" type="text_en" indexed="true" stored="true"/>
<dynamicField name="*_b" type="boolean" indexed="true" stored="true"/>
<dynamicField name="*_f" type="float" indexed="true" stored="true"/>
<dynamicField name="*_d" type="double" indexed="true" stored="true"/>
<dynamicField name="*_dt" type="date" indexed="true" stored="true"/>
<dynamicField name="*_p" type="location" indexed="true" stored="true"/>
<dynamicField name="*_coordinate" type="tdouble" indexed="true" stored="false"/>
<field name="name_ru" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="url" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="text" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="catalog_name_ru" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="catalog_name_en" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="content_auto" type="edge_ngram" indexed="true" stored="true" multiValued="false" />
<field name="form_name" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="name_en" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="area_id" type="long" indexed="true" stored="true" multiValued="false" />
<field name="city_id" type="long" indexed="true" stored="true" multiValued="false" />
<field name="country_id" type="long" indexed="true" stored="true" multiValued="false" />
<field name="theme" type="text_en" indexed="true" stored="true" multiValued="true" />
<field name="tag" type="text_en" indexed="true" stored="true" multiValued="true" />
<field name="where" type="text_en" indexed="true" stored="true" multiValued="true" />
<field name="rating" type="text_en" indexed="true" stored="true" multiValued="true" />
<field name="data_end" type="date" indexed="true" stored="true" multiValued="false" />
<field name="members_choice" type="long" indexed="true" stored="true" multiValued="false" />
<field name="data_begin" type="date" indexed="true" stored="true" multiValued="false" />
<field name="visitors_choice" type="long" indexed="true" stored="true" multiValued="false" />
<field name="expohit" type="boolean" indexed="true" stored="true" multiValued="false" />
<field name="price_choice" type="long" indexed="true" stored="true" multiValued="false" />
<field name="city" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="country" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="parent_en" type="text_en" indexed="true" stored="true" multiValued="false" />
<field name="parent_ru" type="text_en" indexed="true" stored="true" multiValued="false" />
</fields>
<!-- field to use to determine and enforce document uniqueness. -->
<uniqueKey>id</uniqueKey>
<!-- field for the QueryParser to use when an explicit fieldname is absent -->
<defaultSearchField>text</defaultSearchField>
<!-- SolrQueryParser configuration: defaultOperator="AND|OR" -->
<solrQueryParser defaultOperator="AND"/>
</schema>

@ -175,6 +175,8 @@
<field name="where" type="text_en" indexed="true" stored="true" multiValued="true" />
<field name="rating" type="text_en" indexed="true" stored="true" multiValued="true" />
<field name="data_end" type="date" indexed="true" stored="true" multiValued="false" />
<field name="members_choice" type="long" indexed="true" stored="true" multiValued="false" />
@ -183,6 +185,8 @@
<field name="visitors_choice" type="long" indexed="true" stored="true" multiValued="false" />
<field name="expohit" type="boolean" indexed="true" stored="true" multiValued="false" />
<field name="price_choice" type="long" indexed="true" stored="true" multiValued="false" />
<field name="city" type="text_en" indexed="true" stored="true" multiValued="false" />

@ -65,6 +65,7 @@ This template include basic anf main styles and js files,
"date_from": "{{ date_from }}",
"date_to": "{{ date_to }}",
"query": "{{ query }}",
"where_query": "{{ where_query }}",
};
</script>
{% if not NO_BANNERS %}

Loading…
Cancel
Save