From 95c0e7461ded0f0e3ef201f234c6be97fa249853 Mon Sep 17 00:00:00 2001 From: Harish Krishna Date: Tue, 21 Jul 2015 18:46:22 -0400 Subject: [PATCH] TESTS! --- query/search.js | 20 ++-- test/unit/helper/query_parser.js | 168 +++++++++++++++++++++++++++++++ test/unit/run.js | 1 + test/unit/sanitiser/_input.js | 29 ++++++ test/unit/sanitiser/coarse.js | 14 +-- test/unit/sanitiser/search.js | 10 +- 6 files changed, 221 insertions(+), 21 deletions(-) create mode 100644 test/unit/helper/query_parser.js create mode 100644 test/unit/sanitiser/_input.js diff --git a/query/search.js b/query/search.js index a0f4bc4b..8e34b404 100644 --- a/query/search.js +++ b/query/search.js @@ -30,10 +30,11 @@ function generate( params ){ query.query.filtered.query.bool.should = []; - var admin_fields = []; - var qb = function(admin_fields, value) { + var unmatched_admin_fields = []; + // qb stands for query builder + var qb = function(unmatched_admin_fields, value) { if (value) { - admin_fields.forEach(function(admin_field) { + unmatched_admin_fields.forEach(function(admin_field) { var match = {}; match[admin_field] = value; query.query.filtered.query.bool.should.push({ @@ -67,7 +68,7 @@ function generate( params ){ if (params.parsed_input.city) { qb(['admin2'], params.parsed_input.admin2); } else { - admin_fields.push('admin2'); + unmatched_admin_fields.push('admin2'); } // state @@ -75,7 +76,7 @@ function generate( params ){ if (params.parsed_input.state) { qb(['admin1_abbr'], params.parsed_input.state); } else { - admin_fields.push('admin1', 'admin1_abbr'); + unmatched_admin_fields.push('admin1', 'admin1_abbr'); } // country @@ -83,15 +84,16 @@ function generate( params ){ if (params.parsed_input.country) { qb(['alpha3'], params.parsed_input.country); } else { - admin_fields.push('admin0', 'alpha3'); + unmatched_admin_fields.push('admin0', 'alpha3'); } var input_regions = params.parsed_input.regions ? params.parsed_input.regions.join(' ') : undefined; - if (admin_fields.length === 5 && input_regions !== params.input) { + // if no address was identified and input suggests some admin info in it + if (unmatched_admin_fields.length === 5 && input_regions !== params.input) { if (params.parsed_input.admin_parts) { - qb(admin_fields, params.parsed_input.admin_parts); + qb(unmatched_admin_fields, params.parsed_input.admin_parts); } else { - qb(admin_fields, input_regions); + qb(unmatched_admin_fields, input_regions); } } diff --git a/test/unit/helper/query_parser.js b/test/unit/helper/query_parser.js new file mode 100644 index 00000000..2d697a4f --- /dev/null +++ b/test/unit/helper/query_parser.js @@ -0,0 +1,168 @@ + +var parser = require('../../../helper/query_parser'); +var get_layers = require('../../../helper/layers'); + +module.exports.tests = {}; + +module.exports.tests.interface = function(test, common) { + test('interface', function(t) { + t.equal(typeof parser, 'function', 'valid function'); + t.end(); + }); +}; + +module.exports.tests.split_on_comma = function(test, common) { + var queries = ['soho, new york', 'chelsea, london', '123 main, new york']; + var delim = ','; + + var testParse = function(query) { + test('naive parsing ' + query, function(t) { + var address = parser(query); + var delimIndex = query.indexOf(delim); + var name = query.substring(0, delimIndex); + var admin_parts = query.substring(delimIndex + 1).trim(); + + t.equal(typeof address, 'object', 'valid object'); + t.equal(address.name, name, 'name set correctly to ' + address.name); + t.equal(address.admin_parts, admin_parts, 'admin_parts set correctly to ' + address.admin_parts); + t.end(); + }); + }; + + for (var keys in queries) { + testParse( queries[keys] ); + } +}; + +module.exports.tests.parse_three_chars_or_less = function(test, common) { + var chars_queries = ['a', 'bb', 'ccc']; + var num_queries = ['1', '12', '123']; + var alphanum_q = ['a1', '1a2', '12c']; + + var testParse = function(query) { + test('query length < 3 (' + query + ')', function(t) { + var address = parser(query); + var target_layer = get_layers(['admin']); + + t.equal(typeof address, 'object', 'valid object'); + t.deepEqual(address.target_layer, target_layer, 'admin_parts set correctly to ' + target_layer.join(', ')); + t.end(); + }); + }; + + var queries = chars_queries.concat(num_queries).concat(alphanum_q); + for (var keys in queries) { + testParse( queries[keys] ); + } +}; + +module.exports.tests.parse_one_or_more_tokens = function(test, common) { + var one_token_queries = ['hyderbad', 'yugoslavia', 'somethingreallybigbutjustonetokenstill']; + var two_tokens_nonum = ['small town', 'biggg city', 'another empire']; + var two_tokens_withnum= ['123 main', 'sixty 1', '123-980 house']; + + var testParse = function(query, parse_address) { + test('query with one or more tokens (' + query + ')', function(t) { + var address = parser(query); + var target_layer = get_layers(['admin', 'poi']); + + t.equal(typeof address, 'object', 'valid object'); + + if (parse_address) { + t.deepEqual(address.regions.join(''), query, 'since query contained a number, it went through address parsing'); + } else { + t.deepEqual(address.target_layer, target_layer, 'admin_parts set correctly to ' + target_layer.join(', ')); + } + + t.end(); + }); + }; + + var queries = one_token_queries.concat(two_tokens_nonum); + for (var keys in queries) { + testParse( queries[keys] ); + } + for (keys in two_tokens_withnum) { + testParse( two_tokens_withnum[keys], true ); + } +}; + +module.exports.tests.parse_address = function(test, common) { + var addresses_nonum = [{ non_street: 'main particle', city: 'new york'}, + { non_street: 'biggg city block' }, + { non_street: 'the empire state building' } + ]; + var address_with_num = [{ number: 123, street: 'main st', city: 'new york', state: 'ny'}, + { number: 456, street: 'pine ave', city: 'san francisco', state: 'CA'}, + { number: 1980, street: 'house st', city: 'hoboken', state: 'NY'} + ]; + var address_with_zip = [{ number: 1, street: 'main st', city: 'new york', state: 'ny', zip: 10010}, + { number: 4, street: 'ape ave', city: 'san diego', state: 'CA', zip: 98970}, + { number: 19, street: 'house dr', city: 'houston', state: 'TX', zip: 79089} + ]; + + var testParse = function(query, hasNumber, hasZip) { + var testcase = 'parse query with ' + (hasNumber ? 'a house number ': 'no house number '); + testcase += 'and ' + (hasZip ? 'a zip ' : 'no zip '); + + test(testcase, function(t) { + var query_string = ''; + for (var k in query) { + query_string += ' ' + query[k]; + } + + // remove leading whitespace + query_string = query_string.substring(1); + + var address = parser(query_string); + var non_address_layer = get_layers(['admin', 'poi']); + + t.equal(typeof address, 'object', 'valid object for the address ('+query_string+')'); + + if (!hasNumber && !hasZip && query.non_street) { + t.equal(address.regions.join(''), query_string, 'expected parsing result'); + } else { + t.equal(address.regions.join(''), query.city, 'city in regions (' + query.city +')'); + } + + if ((hasNumber || hasZip) && query.street) { + t.equal(typeof address.number, 'number', 'valid house number format (' + address.number + ')'); + t.equal(address.number, query.number, 'correct house number (' + query.number + ')'); + t.equal(typeof address.street, 'string', 'valid street name format (' + address.street + ')'); + t.equal(address.street, query.street, 'correct street name (' + query.street + ')'); + } + + if (hasZip) { + t.equal(typeof address.postalcode, 'number', 'valid zip (' + address.postalcode + ')'); + t.equal(address.postalcode, query.zip, 'correct postal code (' + query.zip + ')'); + } + + if (address.text === address.regions.join(' ')) { + t.deepEqual(address.target_layer, query.target_layer, 'admin_parts set correctly to ' + query.target_layer.join(', ')); + } + + t.end(); + }); + }; + + for (var keys in addresses_nonum) { + testParse( addresses_nonum[keys] ); + } + for (keys in address_with_num) { + testParse( address_with_num[keys], true ); + } + for (keys in address_with_zip) { + testParse( address_with_zip[keys], true, true ); + } +}; + +module.exports.all = function (tape, common) { + + function test(name, testFunction) { + return tape('QUERY PARSING: ' + name, testFunction); + } + + for( var testCase in module.exports.tests ){ + module.exports.tests[testCase](test, common); + } +}; \ No newline at end of file diff --git a/test/unit/run.js b/test/unit/run.js index f28d7306..eb7cad06 100644 --- a/test/unit/run.js +++ b/test/unit/run.js @@ -17,6 +17,7 @@ var tests = [ require('./query/sort'), require('./query/search'), require('./query/reverse'), + require('./helper/query_parser'), require('./helper/geojsonify'), require('./helper/outputSchema') ]; diff --git a/test/unit/sanitiser/_input.js b/test/unit/sanitiser/_input.js new file mode 100644 index 00000000..98eab084 --- /dev/null +++ b/test/unit/sanitiser/_input.js @@ -0,0 +1,29 @@ + +var input = require('../../../sanitiser/_input'), + parser = require('../../../helper/query_parser'), + delim = ',', + defaultError = 'invalid param \'input\': text length, must be >0', + allLayers = [ 'geoname', 'osmnode', 'osmway', 'admin0', 'admin1', 'admin2', 'neighborhood', + 'locality', 'local_admin', 'osmaddress', 'openaddresses' ], + nonAddressLayers = [ 'geoname', 'osmnode', 'osmway', 'admin0', 'admin1', 'admin2', 'neighborhood', + 'locality', 'local_admin' ], + defaultParsed= { target_layer: nonAddressLayers }, + defaultClean = { input: 'test', + layers: allLayers, + size: 10, + details: true, + parsed_input: defaultParsed, + lat:0, + lon:0 + }, + getTargetLayers = function(query) { + var address = parser(query); + return address.target_layer; + }; + + +module.exports = { + defaultParsed: defaultParsed, + defaultClean : defaultClean, + getTargetLayers: getTargetLayers +}; \ No newline at end of file diff --git a/test/unit/sanitiser/coarse.js b/test/unit/sanitiser/coarse.js index a1fd69ab..13eca7c2 100644 --- a/test/unit/sanitiser/coarse.js +++ b/test/unit/sanitiser/coarse.js @@ -3,6 +3,7 @@ var coarse = require('../../../sanitiser/coarse'), _sanitize = coarse.sanitize, middleware = coarse.middleware, valid_layers = [ 'admin0', 'admin1', 'admin2', 'neighborhood', 'locality', 'local_admin' ], + defaultClean = require('../sanitiser/_input').defaultClean, sanitize = function(query, cb) { _sanitize({'query':query}, cb); }; module.exports.tests = {}; @@ -47,17 +48,12 @@ module.exports.tests.middleware_failure = function(test, common) { module.exports.tests.middleware_success = function(test, common) { test('middleware success', function(t) { var req = { query: { input: 'test', lat: 0, lon: 0 }}; + var clean = defaultClean; + clean.layers = valid_layers; + var next = function( message ){ - var defaultClean = { - input: 'test', - size: 10, - layers: [ 'admin0', 'admin1', 'admin2', 'neighborhood', 'locality', 'local_admin' ], - lat: 0, - lon: 0, - details: true - }; t.equal(message, undefined, 'no error message set'); - // t.deepEqual(req.clean, defaultClean); + t.deepEqual(req.clean, clean); t.end(); }; middleware( req, undefined, next ); diff --git a/test/unit/sanitiser/search.js b/test/unit/sanitiser/search.js index a06f7da5..ed1c0b6d 100644 --- a/test/unit/sanitiser/search.js +++ b/test/unit/sanitiser/search.js @@ -1,6 +1,7 @@ var search = require('../../../sanitiser/search'), - defaultParsed = require('../sanitiser/_input').defaultParsed, + _input = require('../sanitiser/_input'), + defaultParsed = _input.defaultParsed, _sanitize = search.sanitize, middleware = search.middleware, delim = ',', @@ -10,7 +11,8 @@ var search = require('../../../sanitiser/search'), 'locality', 'local_admin', 'osmaddress', 'openaddresses' ], size: 10, details: true, - parsed_input: defaultParsed + parsed_input: defaultParsed, + default_layers_set: true }, sanitize = function(query, cb) { _sanitize({'query':query}, cb); }; @@ -48,8 +50,10 @@ module.exports.tests.sanitize_input = function(test, common) { sanitize({ input: input }, function( err, clean ){ var expected = JSON.parse(JSON.stringify( defaultClean )); expected.input = input; + expected.parsed_input.target_layer = _input.getTargetLayers(input); + t.equal(err, undefined, 'no error'); - // t.deepEqual(clean, expected, 'clean set correctly (' + input + ')'); + t.deepEqual(clean, expected, 'clean set correctly (' + input + ')'); }); }); t.end();