maps: require all words to match when querying layer features (#26268)

This commit is contained in:
Frédéric Péters 2018-09-14 12:16:33 +02:00
parent 299c3d2dcd
commit f872cafd75
2 changed files with 31 additions and 8 deletions

View File

@ -203,21 +203,26 @@ class MapLayer(models.Model):
features = [x for x in features if match(x)]
if request and request.GET.get('q'):
query = slugify(request.GET['q'])
# all words must match
query_words = [slugify(x) for x in request.GET['q'].split()]
additional_strings = []
if multiple_layers: # also match on layer name
additional_strings = [self.label]
def match(feature):
for geo_property in feature['properties'].values():
matching_query_words = set()
for geo_property in feature['properties'].values() + additional_strings:
if not isinstance(geo_property, six.string_types):
continue
if query in slugify(geo_property):
for word in query_words:
if word in slugify(geo_property):
matching_query_words.add(word)
if len(matching_query_words) == len(query_words):
return True
return False
if multiple_layers and query in slugify(self.label):
# also match on layer name, get them all
pass
else:
features = [x for x in features if match(x)]
features = [x for x in features if match(x)]
for feature in features:
feature['properties']['layer'] = {

View File

@ -280,6 +280,18 @@ def test_get_geojson(app, layer, user):
resp = app.get(reverse('mapcell-geojson', kwargs={'cell_id': cell.id}) + '?lng=2.54&lat=48.84&distance=100')
assert len(json.loads(resp.content)['features']) == 0
# check on multiple words
with mock.patch('combo.utils.requests_wrapper.RequestsSession.request') as requests_get:
requests_get.return_value = mock.Mock(
content=SAMPLE_GEOJSON_CONTENT,
json=lambda: json.loads(SAMPLE_GEOJSON_CONTENT),
status_code=200)
resp = app.get(reverse('mapcell-geojson', kwargs={'cell_id': cell.id}) + '?q=bar baz')
assert len(json.loads(resp.content)['features']) == 1
resp = app.get(reverse('mapcell-geojson', kwargs={'cell_id': cell.id}) + '?q=quux baz')
assert len(json.loads(resp.content)['features']) == 0
# add a second layer
layer2 = MapLayer()
layer2.label = 'xxx'
@ -305,6 +317,12 @@ def test_get_geojson(app, layer, user):
resp = app.get(reverse('mapcell-geojson', kwargs={'cell_id': cell.id}) + '?q=bicycle')
assert len(json.loads(resp.content)['features']) == 2
resp = app.get(reverse('mapcell-geojson', kwargs={'cell_id': cell.id}) + '?q=bar bicycle')
assert len(json.loads(resp.content)['features']) == 1
resp = app.get(reverse('mapcell-geojson', kwargs={'cell_id': cell.id}) + '?q=quux bicycle')
assert len(json.loads(resp.content)['features']) == 0
def test_get_geojson_properties(app, layer, user):
page = Page(title='xxx', slug='new', template_name='standard')