From b6896f142150dfd0d431ae76551ed4b9e70ab413 Mon Sep 17 00:00:00 2001 From: Doug Turnbull Date: Wed, 23 Sep 2015 13:10:42 -0400 Subject: [PATCH] Enable jshint validation, cleanup jshint errors Previously the Gruntfile had jshint settings encoded in it instead of using the more standard .jshintrc. Many editors pick up on jshintrc and will warn you when you have errors, which mine does. I made jshintrc pretty much consistent with Quepid and cleaned up associated errors. --- .jshintrc | 7 ++- Gruntfile.js | 46 ++++--------------- factories/esDocFactory.js | 6 +-- factories/settingsValidatorFactory.js | 10 ++--- services/esSearcherPreprocessorSvc.js | 2 +- services/esUrlSvc.js | 6 +-- services/fieldSpecSvc.js | 8 ++-- services/simExplainSvc.js | 8 ++-- services/solrUrlSvc.js | 17 ------- services/stringPatch.js | 4 +- services/vectorSvc.js | 3 +- splainer-search.js | 64 ++++++++++----------------- 12 files changed, 60 insertions(+), 121 deletions(-) diff --git a/.jshintrc b/.jshintrc index 6ba9e06..0fbc069 100644 --- a/.jshintrc +++ b/.jshintrc @@ -7,7 +7,6 @@ "curly": true, "eqeqeq": true, "immed": true, - "indent": 2, "latedef": "nofunc", "newcap": true, "noarg": true, @@ -18,7 +17,11 @@ "strict": true, "trailing": true, "smarttabs": true, + "validthis": true, "globals": { - "angular": false + "angular": false, + "inject": false, + "Promise": false, + "URI": false } } diff --git a/Gruntfile.js b/Gruntfile.js index c5db946..b0fca9f 100644 --- a/Gruntfile.js +++ b/Gruntfile.js @@ -32,42 +32,14 @@ module.exports = function(grunt) { */ grunt.initConfig({ jshint: { - options: { - //force: true, - globalstrict: true, - //sub: true, - node: true, - loopfunc: true, - browser: true, - devel: true, - globals: { - angular: true, - $: true, - moment: false, - Pikaday: false, - module: false, - forge: false - } - }, - beforeconcat: { - options: { - force: false, - ignores: ['**.min.js'] - }, - files: { - src: ['services/*.js', 'factories/*.js', 'values/*.js'] - } - }, - //quick version - will not fail entire grunt process if there are lint errors - beforeconcatQ: { - options: { - force: true, - ignores: ['**.min.js'] - }, - files: { - src: ['module.js, services/*.js', 'factories/*.js', 'values/*.js'] - } - } + options: { + force: true, + ignores: ['**.min.js'], + jshintrc: '.jshintrc' + }, + all: { + src: ['module.js', 'services/*.js', 'factories/*.js', 'values/*.js'] + } }, concat: { dist: { @@ -105,7 +77,7 @@ module.exports = function(grunt) { @toc 6. */ // Default task(s). - grunt.registerTask('default', ['jshint:beforeconcatQ', 'karma:unit', 'concat:dist']); + grunt.registerTask('default', ['jshint', 'karma:unit', 'concat:dist']); } init({}); //initialize here for defaults (init may be called again later within a task) diff --git a/factories/esDocFactory.js b/factories/esDocFactory.js index 4213ffa..4683763 100644 --- a/factories/esDocFactory.js +++ b/factories/esDocFactory.js @@ -58,7 +58,7 @@ /*jslint validthis:true*/ var self = this; - if (self.doc.hasOwnProperty("highlight")) { + if (self.doc.hasOwnProperty('highlight')) { var docHls = self.doc.highlight; if (docHls.hasOwnProperty(fieldName)) { return docHls[fieldName]; @@ -87,9 +87,9 @@ angular.forEach(fieldValue, function (value) { // Doing the naive thing and assuming that the highlight tags // were not overridden in the query DSL. - var preRegex = new RegExp("", 'g'); + var preRegex = new RegExp('', 'g'); var hlPre = value.replace(preRegex, preText); - var postRegex = new RegExp("", 'g'); + var postRegex = new RegExp('', 'g'); newValue.push(hlPre.replace(postRegex, postText)); }); diff --git a/factories/settingsValidatorFactory.js b/factories/settingsValidatorFactory.js index da6914c..9396d32 100644 --- a/factories/settingsValidatorFactory.js +++ b/factories/settingsValidatorFactory.js @@ -28,9 +28,9 @@ var args = { }; var fields = '*'; - if ( self.searchEngine == 'solr' ) { + if ( self.searchEngine === 'solr' ) { args = { q: ['*:*'] }; - } else if ( self.searchEngine == 'es' ) { + } else if ( self.searchEngine === 'es' ) { fields = null; } @@ -51,7 +51,7 @@ // the entire list of fields possible. // This is not perfect as the top 10 results might not include // a comprehensive list, but it's the best we can do. - if ( self.searchEngine == 'solr' ) { + if ( self.searchEngine === 'solr' ) { angular.forEach(self.searcher.docs, function(doc) { var attributes = Object.keys(doc.doc); @@ -59,8 +59,8 @@ return self.fields.indexOf(attribute) < 0; })); }); - } else if ( self.searchEngine == 'es' ) { - self.fields.push("_id"); + } else if ( self.searchEngine === 'es' ) { + self.fields.push('_id'); angular.forEach(self.searcher.docs, function(doc) { var attributes = Object.keys(doc.doc._source); diff --git a/services/esSearcherPreprocessorSvc.js b/services/esSearcherPreprocessorSvc.js index 07dad16..4cca6cf 100644 --- a/services/esSearcherPreprocessorSvc.js +++ b/services/esSearcherPreprocessorSvc.js @@ -7,7 +7,7 @@ angular.module('o19s.splainer-search') var replaceQuery = function(args, queryText) { if (queryText) { - queryText = queryText.replace(/\\/g, "\\\\");; + queryText = queryText.replace(/\\/g, '\\\\'); queryText = queryText.replace(/"/g, '\\\"'); } diff --git a/services/esUrlSvc.js b/services/esUrlSvc.js index 2e475b0..88f9962 100644 --- a/services/esUrlSvc.js +++ b/services/esUrlSvc.js @@ -52,7 +52,7 @@ angular.module('o19s.splainer-search') self.password = a.password(); self.parsed = true; - }; + } /** * @@ -116,7 +116,7 @@ angular.module('o19s.splainer-search') var url = self.protocol + '://' + self.host; - return url + return url; } function setParams (params) { @@ -126,7 +126,7 @@ angular.module('o19s.splainer-search') function UrlNotParseException() { var self = this; - self.message = "URL not parsed. Must call the parse() function first."; + self.message = 'URL not parsed. Must call the parse() function first.'; self.toString = function() { return self.message; }; diff --git a/services/fieldSpecSvc.js b/services/fieldSpecSvc.js index 5b320ac..59948ec 100644 --- a/services/fieldSpecSvc.js +++ b/services/fieldSpecSvc.js @@ -3,7 +3,7 @@ angular.module('o19s.splainer-search') .service('fieldSpecSvc', function fieldSpecSvc() { // AngularJS will instantiate a singleton by calling 'new' on this function - + var addFieldOfType = function(fieldSpec, fieldType, fieldName) { if (fieldType === 'sub') { if (!fieldSpec.hasOwnProperty('subs')) { @@ -11,7 +11,7 @@ angular.module('o19s.splainer-search') } if (fieldSpec.subs !== '*') { fieldSpec.subs.push(fieldName); - } + } if (fieldName === '*') { fieldSpec.subs = '*'; } @@ -47,8 +47,8 @@ angular.module('o19s.splainer-search') } }); }; - - + + var FieldSpec = function(fieldSpecStr) { this.fields = []; this.fieldSpecStr = fieldSpecStr; diff --git a/services/simExplainSvc.js b/services/simExplainSvc.js index 50e0ed4..2860c7e 100644 --- a/services/simExplainSvc.js +++ b/services/simExplainSvc.js @@ -25,7 +25,7 @@ angular.module('o19s.splainer-search') }); this.formulaStr = function() { - return 'TF=' + this.fieldWeight.tf().contribution() + + return 'TF=' + this.fieldWeight.tf().contribution() + ' * IDF=' + this.fieldWeight.idf().contribution(); }; }; @@ -44,7 +44,7 @@ angular.module('o19s.splainer-search') explain.tf = function() { return tfExpl; }; - + explain.idf = function() { return idfExpl; }; @@ -62,7 +62,7 @@ angular.module('o19s.splainer-search') /*this.fieldNorm = function() { };*/ }; - + this.QueryWeightExplain = function() { this.realExplanation = 'Query Weight'; tfIdfable(this); @@ -87,7 +87,7 @@ angular.module('o19s.splainer-search') // For default similarity, IDF of the term being searched // in the case of phrase queries, this is a sum of - // all the members of the phrase. + // all the members of the phrase. // // TODO -- the underlying idf for each member of a phrase // does not identify the term corresponding to that idf, diff --git a/services/solrUrlSvc.js b/services/solrUrlSvc.js index 55e0145..1fef6e4 100644 --- a/services/solrUrlSvc.js +++ b/services/solrUrlSvc.js @@ -146,22 +146,6 @@ angular.module('o19s.splainer-search') * */ this.removeUnsupported = function(solrArgs) { var warnings = {}; - var deleteThenWarn = function(arg, warning) { - if (solrArgs.hasOwnProperty(arg)) { - warnings[arg] = warning; - delete solrArgs[arg]; - } - }; - - var deleteThenWarnPrefix = function(argPrefix, warning) { - var argsCpy = angular.copy(solrArgs); - angular.forEach(argsCpy, function(value, key) { - if (key.startsWith(argPrefix)) { - deleteThenWarn(key, warning); - } - }); - }; - // Stuff I think we can safely remove without warning the user delete solrArgs['json.wrf']; delete solrArgs.facet; @@ -175,7 +159,6 @@ angular.module('o19s.splainer-search') delete solrArgs.debug; // Unsupported stuff to remove and provide a friendly warning - // deleteThenWarnPrefix('group', 'Group queries/field collapsing not supported'); return warnings; }; diff --git a/services/stringPatch.js b/services/stringPatch.js index 8f8c4e6..b86f4a2 100644 --- a/services/stringPatch.js +++ b/services/stringPatch.js @@ -2,7 +2,7 @@ if (typeof String.prototype.startsWith !== 'function') { // see below for better implementation! - String.prototype.startsWith = function (str){ + String.prototype.startsWith = function (str) { return this.indexOf(str) === 0; }; } @@ -15,6 +15,6 @@ if (typeof String.prototype.hasSubstr !== 'function') { if (typeof String.prototype.endsWith !== 'function') { String.prototype.endsWith = function(suffix) { - return this.indexOf(suffix, this.length - suffix.length) !== -1; + return this.indexOf(suffix, this.length - suffix.length) !== -1; }; } diff --git a/services/vectorSvc.js b/services/vectorSvc.js index 662e4c4..310abc2 100644 --- a/services/vectorSvc.js +++ b/services/vectorSvc.js @@ -66,6 +66,5 @@ angular.module('o19s.splainer-search') rVal.set(key, value * scalar); }); return rVal; - }; - + }; }); diff --git a/splainer-search.js b/splainer-search.js index a311cc3..b1be8a8 100644 --- a/splainer-search.js +++ b/splainer-search.js @@ -169,7 +169,7 @@ angular.module('o19s.splainer-search') var replaceQuery = function(args, queryText) { if (queryText) { - queryText = queryText.replace(/\\/g, "\\\\");; + queryText = queryText.replace(/\\/g, '\\\\'); queryText = queryText.replace(/"/g, '\\\"'); } @@ -251,7 +251,7 @@ angular.module('o19s.splainer-search') self.password = a.password(); self.parsed = true; - }; + } /** * @@ -315,7 +315,7 @@ angular.module('o19s.splainer-search') var url = self.protocol + '://' + self.host; - return url + return url; } function setParams (params) { @@ -325,7 +325,7 @@ angular.module('o19s.splainer-search') function UrlNotParseException() { var self = this; - self.message = "URL not parsed. Must call the parse() function first."; + self.message = 'URL not parsed. Must call the parse() function first.'; self.toString = function() { return self.message; }; @@ -471,7 +471,7 @@ angular.module('o19s.splainer-search') angular.module('o19s.splainer-search') .service('fieldSpecSvc', function fieldSpecSvc() { // AngularJS will instantiate a singleton by calling 'new' on this function - + var addFieldOfType = function(fieldSpec, fieldType, fieldName) { if (fieldType === 'sub') { if (!fieldSpec.hasOwnProperty('subs')) { @@ -479,7 +479,7 @@ angular.module('o19s.splainer-search') } if (fieldSpec.subs !== '*') { fieldSpec.subs.push(fieldName); - } + } if (fieldName === '*') { fieldSpec.subs = '*'; } @@ -515,8 +515,8 @@ angular.module('o19s.splainer-search') } }); }; - - + + var FieldSpec = function(fieldSpecStr) { this.fields = []; this.fieldSpecStr = fieldSpecStr; @@ -1138,7 +1138,7 @@ angular.module('o19s.splainer-search') }); this.formulaStr = function() { - return 'TF=' + this.fieldWeight.tf().contribution() + + return 'TF=' + this.fieldWeight.tf().contribution() + ' * IDF=' + this.fieldWeight.idf().contribution(); }; }; @@ -1157,7 +1157,7 @@ angular.module('o19s.splainer-search') explain.tf = function() { return tfExpl; }; - + explain.idf = function() { return idfExpl; }; @@ -1175,7 +1175,7 @@ angular.module('o19s.splainer-search') /*this.fieldNorm = function() { };*/ }; - + this.QueryWeightExplain = function() { this.realExplanation = 'Query Weight'; tfIdfable(this); @@ -1200,7 +1200,7 @@ angular.module('o19s.splainer-search') // For default similarity, IDF of the term being searched // in the case of phrase queries, this is a sum of - // all the members of the phrase. + // all the members of the phrase. // // TODO -- the underlying idf for each member of a phrase // does not identify the term corresponding to that idf, @@ -1451,22 +1451,6 @@ angular.module('o19s.splainer-search') * */ this.removeUnsupported = function(solrArgs) { var warnings = {}; - var deleteThenWarn = function(arg, warning) { - if (solrArgs.hasOwnProperty(arg)) { - warnings[arg] = warning; - delete solrArgs[arg]; - } - }; - - var deleteThenWarnPrefix = function(argPrefix, warning) { - var argsCpy = angular.copy(solrArgs); - angular.forEach(argsCpy, function(value, key) { - if (key.startsWith(argPrefix)) { - deleteThenWarn(key, warning); - } - }); - }; - // Stuff I think we can safely remove without warning the user delete solrArgs['json.wrf']; delete solrArgs.facet; @@ -1480,7 +1464,6 @@ angular.module('o19s.splainer-search') delete solrArgs.debug; // Unsupported stuff to remove and provide a friendly warning - // deleteThenWarnPrefix('group', 'Group queries/field collapsing not supported'); return warnings; }; @@ -1490,7 +1473,7 @@ angular.module('o19s.splainer-search') if (typeof String.prototype.startsWith !== 'function') { // see below for better implementation! - String.prototype.startsWith = function (str){ + String.prototype.startsWith = function (str) { return this.indexOf(str) === 0; }; } @@ -1503,7 +1486,7 @@ if (typeof String.prototype.hasSubstr !== 'function') { if (typeof String.prototype.endsWith !== 'function') { String.prototype.endsWith = function(suffix) { - return this.indexOf(suffix, this.length - suffix.length) !== -1; + return this.indexOf(suffix, this.length - suffix.length) !== -1; }; } @@ -1575,8 +1558,7 @@ angular.module('o19s.splainer-search') rVal.set(key, value * scalar); }); return rVal; - }; - + }; }); 'use strict'; @@ -1685,7 +1667,7 @@ angular.module('o19s.splainer-search') /*jslint validthis:true*/ var self = this; - if (self.doc.hasOwnProperty("highlight")) { + if (self.doc.hasOwnProperty('highlight')) { var docHls = self.doc.highlight; if (docHls.hasOwnProperty(fieldName)) { return docHls[fieldName]; @@ -1714,9 +1696,9 @@ angular.module('o19s.splainer-search') angular.forEach(fieldValue, function (value) { // Doing the naive thing and assuming that the highlight tags // were not overridden in the query DSL. - var preRegex = new RegExp("", 'g'); + var preRegex = new RegExp('', 'g'); var hlPre = value.replace(preRegex, preText); - var postRegex = new RegExp("", 'g'); + var postRegex = new RegExp('', 'g'); newValue.push(hlPre.replace(postRegex, postText)); }); @@ -2109,9 +2091,9 @@ angular.module('o19s.splainer-search') var args = { }; var fields = '*'; - if ( self.searchEngine == 'solr' ) { + if ( self.searchEngine === 'solr' ) { args = { q: ['*:*'] }; - } else if ( self.searchEngine == 'es' ) { + } else if ( self.searchEngine === 'es' ) { fields = null; } @@ -2132,7 +2114,7 @@ angular.module('o19s.splainer-search') // the entire list of fields possible. // This is not perfect as the top 10 results might not include // a comprehensive list, but it's the best we can do. - if ( self.searchEngine == 'solr' ) { + if ( self.searchEngine === 'solr' ) { angular.forEach(self.searcher.docs, function(doc) { var attributes = Object.keys(doc.doc); @@ -2140,8 +2122,8 @@ angular.module('o19s.splainer-search') return self.fields.indexOf(attribute) < 0; })); }); - } else if ( self.searchEngine == 'es' ) { - self.fields.push("_id"); + } else if ( self.searchEngine === 'es' ) { + self.fields.push('_id'); angular.forEach(self.searcher.docs, function(doc) { var attributes = Object.keys(doc.doc._source);