Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

autocomplete: extend additional name fields used in multimatch queries #1620

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@
"pelias-microservice-wrapper": "^1.10.0",
"pelias-model": "^9.0.0",
"pelias-parser": "2.2.0",
"pelias-query": "^11.0.0",
"pelias-query": "github:pelias/query#additional-name-fields",
"pelias-sorting": "^1.2.0",
"predicates": "^2.0.0",
"regenerate": "^1.4.0",
Expand Down
9 changes: 6 additions & 3 deletions query/search_pelias_parser.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,10 @@ const textParser = require('./text_parser_pelias');
const config = require('pelias-config').generate().api;

var placeTypes = require('../helper/placeTypes');
var views = { custom_boosts: require('./view/boost_sources_and_layers') };
var views = {
custom_boosts: require('./view/boost_sources_and_layers'),
query_multi_match: require('./view/query_multi_match')
};

// region_a is also an admin field which can be identified by
// the pelias_parser. this functionality was inherited from the
Expand All @@ -18,10 +21,10 @@ var adminFields = placeTypes.concat(['region_a']);
var query = new peliasQuery.layout.FilteredBooleanQuery();

// mandatory matches
query.score( peliasQuery.view.leaf.match('main'), 'must' );
query.score( views.query_multi_match('match', 'main'), 'must' );

// scoring boost
const phrase_view = peliasQuery.view.leaf.match_phrase('main');
const phrase_view = views.query_multi_match('match_phrase', 'main', 'phrase');

query.score( phrase_view );
query.score( peliasQuery.view.focus( peliasQuery.view.leaf.match_all ) );
Expand Down
21 changes: 18 additions & 3 deletions query/view/helper.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,12 @@
function toMultiFields(baseField, suffix) {
return [baseField, toSingleField(baseField, suffix)];
const _ = require('lodash');

function toMultiFields(baseField, ...suffix) {
return [
baseField,
...suffix
.filter(e => _.isString(e) && !_.isEmpty(e))
.map(suffix => toSingleField(baseField, suffix))
];
}

function toSingleField(baseField, suffix) {
Expand All @@ -9,4 +16,12 @@ function toSingleField(baseField, suffix) {
return parts.join('.');
}

module.exports = { toMultiFields, toSingleField };
function toMultiFieldsWithWildcards(baseField, ...suffix) {
const result = [];
toMultiFields(baseField, ...suffix).forEach(field => {
result.push(field, `${field}_*`);
});
return result;
}

module.exports = { toMultiFields, toSingleField, toMultiFieldsWithWildcards };
7 changes: 5 additions & 2 deletions query/view/ngrams_strict.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
const peliasQuery = require('pelias-query');
const toMultiFields = require('./helper').toMultiFields;
const toMultiFieldsWithWildcards = require('./helper').toMultiFieldsWithWildcards;

/**
Ngrams view with the additional properties to enable:
Expand All @@ -16,7 +16,10 @@ module.exports = function( vs ){
}

vs.var('multi_match:ngrams_strict:input', vs.var('input:name').get());
vs.var('multi_match:ngrams_strict:fields', toMultiFields(vs.var('ngram:field').get(), vs.var('lang').get()));
vs.var('multi_match:ngrams_strict:fields', toMultiFieldsWithWildcards(
vs.var('ngram:field').get(),
vs.var('lang').get(),
));

vs.var('multi_match:ngrams_strict:analyzer', vs.var('ngram:analyzer').get());
vs.var('multi_match:ngrams_strict:slop', vs.var('phrase:slop').get());
Expand Down
7 changes: 5 additions & 2 deletions query/view/phrase_first_tokens_only.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
const peliasQuery = require('pelias-query');
const toMultiFields = require('./helper').toMultiFields;
const toMultiFieldsWithWildcards = require('./helper').toMultiFieldsWithWildcards;

/**
Phrase view which trims the 'input:name' and uses ALL BUT the last token.
Expand All @@ -18,7 +18,10 @@ module.exports = function( vs ){

// set the 'input' variable to all but the last token
vs.var(`multi_match:${view_name}:input`).set( tokens.join(' ') );
vs.var(`multi_match:${view_name}:fields`).set(toMultiFields(vs.var('phrase:field').get(), vs.var('lang').get()));
vs.var(`multi_match:${view_name}:fields`, toMultiFieldsWithWildcards(
vs.var('phrase:field').get(),
vs.var('lang').get(),
));

vs.var(`multi_match:${view_name}:analyzer`).set(vs.var('phrase:analyzer').get());
vs.var(`multi_match:${view_name}:boost`).set(vs.var('phrase:boost').get());
Expand Down
52 changes: 52 additions & 0 deletions query/view/query_multi_match.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
const _ = require('lodash');
const toMultiFieldsWithWildcards = require('./helper').toMultiFieldsWithWildcards;

const optional_params = [
'boost',
'slop',
'operator',
'analyzer',
'cutoff_frequency',
'fuzziness',
'max_expansions',
'prefix_length',
'fuzzy_transpositions',
'minimum_should_match',
'zero_terms_query'
];

module.exports = (namespace, prefix, type) => {
return (vs) => {
const input_variable = `${namespace}:${prefix}:input`;
const field_variable = `${namespace}:${prefix}:field`;

if (!vs.isset(input_variable) || !vs.isset(field_variable)) {
return null;
}

const query = {
multi_match: {
query: vs.var(input_variable),
fields: toMultiFieldsWithWildcards(
vs.var(field_variable).get(),
vs.var('lang').get(),
)
}
};

// optional 'type'
if (_.isString(type)) {
query.multi_match.type = type;
}

// other optional params
optional_params.forEach((param) => {
const variable_name = `${namespace}:${prefix}:${param}`;
if (vs.isset(variable_name)) {
query.multi_match[param] = vs.var(variable_name);
}
});

return query;
};
};
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_boundary_country.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'test',
'boost': 100,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_boundary_gid.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'test',
'boost': 100,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_custom_boosts.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,12 @@
"must": [
{
"multi_match": {
"fields": ["phrase.default", "phrase.en"],
"fields": [
"phrase.default",
"phrase.default_*",
"phrase.en",
"phrase.en_*"
],
"analyzer": "peliasQuery",
"query": "foo",
"boost": 1,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'test',
'boost': 100,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'test',
'boost': 100,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_linguistic_final_token.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,12 @@ module.exports = {
'bool': {
'must': [{
'multi_match': {
'fields': ['phrase.default', 'phrase.en'],
'fields': [
'phrase.default',
'phrase.default_*',
'phrase.en',
'phrase.en_*'
],
'analyzer': 'peliasQuery',
'query': 'one',
'boost': 1,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_linguistic_focus.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'test',
'boost': 100,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'test',
'boost': 100,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_linguistic_multiple_tokens.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,12 @@ module.exports = {
'bool': {
'must': [{
'multi_match': {
'fields': ['phrase.default', 'phrase.en'],
'fields': [
'phrase.default',
'phrase.default_*',
'phrase.en',
'phrase.en_*'
],
'analyzer': 'peliasQuery',
'query': 'one two',
'boost': 1,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,12 @@ module.exports = {
'bool': {
'must': [{
'multi_match': {
'fields': ['phrase.default', 'phrase.en'],
'fields': [
'phrase.default',
'phrase.default_*',
'phrase.en',
'phrase.en_*'
],
'analyzer': 'peliasQuery',
'type': 'phrase',
'slop': 3,
Expand All @@ -15,7 +20,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'three',
'boost': 100,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_linguistic_one_char_token.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 't',
'boost': 100,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_linguistic_only.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'test',
'boost': 100,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'tes',
'boost': 100,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_linguistic_two_char_token.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ module.exports = {
'constant_score': {
'filter': {
'multi_match': {
'fields': ['name.default', 'name.en'],
'fields': [
'name.default',
'name.default_*',
'name.en',
'name.en_*'
],
'analyzer': 'peliasQuery',
'query': 'te',
'boost': 100,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_linguistic_with_admin.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,12 @@ module.exports = {
'must': [
{
'multi_match': {
'fields': ['phrase.default', 'phrase.en'],
'fields': [
'phrase.default',
'phrase.default_*',
'phrase.en',
'phrase.en_*'
],
'analyzer': 'peliasQuery',
'type': 'phrase',
'slop': 3,
Expand Down
7 changes: 6 additions & 1 deletion test/unit/fixture/autocomplete_single_character_street.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,12 @@ module.exports = {
'bool': {
'must': [{
'multi_match': {
'fields': ['phrase.default', 'phrase.en'],
'fields': [
'phrase.default',
'phrase.default_*',
'phrase.en',
'phrase.en_*'
],
'analyzer': 'peliasQuery',
'query': 'k road',
'boost': 1,
Expand Down
Loading