From 5a93e5a2bcf0e0aa5370b45dd3fa1c67a3109828 Mon Sep 17 00:00:00 2001 From: shale Date: Tue, 21 Jul 2015 14:23:44 -0700 Subject: [PATCH] [Search] Correct search updating The search controller now updates the display results list, then repeatedly asks the aggregator to update until the timestamps all are at least as new as the one that the controller originally gave for the query. Basically, the search now updates correctly without having to press enter again. --- platform/features/search/bundle.json | 2 +- .../features/search/res/templates/search.html | 2 +- .../features/search/src/SearchAggregator.js | 48 ++++++++++++------- .../src/controllers/SearchController.js | 34 +++++++++---- .../src/providers/GenericSearchProvider.js | 10 ++-- .../search/src/workers/GenericSearchWorker.js | 19 +++++--- 6 files changed, 77 insertions(+), 38 deletions(-) diff --git a/platform/features/search/bundle.json b/platform/features/search/bundle.json index 47150db2c9..f5df8bce26 100644 --- a/platform/features/search/bundle.json +++ b/platform/features/search/bundle.json @@ -15,7 +15,7 @@ { "key": "SearchController", "implementation": "controllers/SearchController.js", - "depends": [ "$scope", "searchService", "objectService" ] + "depends": [ "$scope", "$timeout", "searchService" ] }, { "key": "SearchbarController", diff --git a/platform/features/search/res/templates/search.html b/platform/features/search/res/templates/search.html index a9ab0bb6fc..f6b730a8c3 100644 --- a/platform/features/search/res/templates/search.html +++ b/platform/features/search/res/templates/search.html @@ -31,7 +31,7 @@ value="" ng-keyup="controller.search('searchinput')" style="width: 66%"/> - +
diff --git a/platform/features/search/src/SearchAggregator.js b/platform/features/search/src/SearchAggregator.js index 10b40fe408..76cc606093 100644 --- a/platform/features/search/src/SearchAggregator.js +++ b/platform/features/search/src/SearchAggregator.js @@ -41,7 +41,8 @@ define( * aggregated */ function SearchAggregator(providers) { - var latestMergedResults = []; + var latestMergedResults = [], + lastMergeTimestamps = []; // Remove extra objects that have the same ID function filterRepeats(results) { @@ -104,11 +105,13 @@ define( } function updateResults() { - var newerResults = []; + var newerResults = [], + providerTimestamps = []; // For each provider, get its most recent results for (var i = 0; i < providers.length; i += 1) { - newerResults = newerResults.concat(providers[i].getLatest()); + newerResults = newerResults.concat(providers[i].getLatestResults()); + providerTimestamps.push(providers[i].getLatestTimestamp()); } // Clean up @@ -117,27 +120,32 @@ define( // After all that is done, now replace latestMergedResults with this latestMergedResults = newerResults; + lastMergeTimestamps = providerTimestamps; } - // Calls the searches of each of the providers, then - // merges the results lists so that there are not redundant - // results /** - * + * Sends a query to each of the providers, then updates the globl + * latestMergedResults accordingly. + * + * @param inputID The name of the ID property of the html text + * input where this funcion should find the search term. + * @param timestamp (optional) The time at which this function + * was called. This timestamp will be associated with the + * latest results list, which allows us to see if it has been + * updated. If not provided, this aggregator will. */ - function queryAll(inputID) { - var promises = [], - date = new Date(), + function queryAll(inputID, timestamp) { + // If there's not a timestamp, make this time the timestamp + if (!timestamp) { + var date = new Date(); timestamp = date.getTime(); + } // Send the query to all the providers for (var i = 0; i < providers.length; i += 1) { - promises.push( - providers[i].query( - inputID, timestamp, DEFAULT_MAX_RESULTS, DEFUALT_TIMEOUT - ) - ); + providers[i].query(inputID, timestamp, DEFAULT_MAX_RESULTS, DEFUALT_TIMEOUT); } + // TODO: Then we want to 'Get the latest results from all the providers' // And then we might also want to check to see if the timestamp // is correct. @@ -148,9 +156,17 @@ define( return { sendQuery: queryAll, + updateResults: updateResults, getLatestResults: function (start, stop) { // TODO: Make sure that slice handles out of bounds - return latestMergedResults.slice(start, stop); + // By default if there are no start or stop provided, will return + // the entire thing. + var a = latestMergedResults.slice(start, stop); + return a; + }, + getLatestTimestamps: function () { + var b = lastMergeTimestamps; + return b; } }; } diff --git a/platform/features/search/src/controllers/SearchController.js b/platform/features/search/src/controllers/SearchController.js index cc07f05296..1b16bb2ce2 100644 --- a/platform/features/search/src/controllers/SearchController.js +++ b/platform/features/search/src/controllers/SearchController.js @@ -28,19 +28,35 @@ define(function () { "use strict"; - function SearchController($scope, searchService, objectService) { + function SearchController($scope, $timeout, searchService) { function search(inputID) { + var date = new Date(), + timestamp = date.getTime(), + numResults = 20; - // Later, the search result format will be different - // Will need to compile search result list (for this - // result page) here, using pseudo linkedlist searchResult + // Send the query + searchService.sendQuery(inputID, timestamp); - searchService.sendQuery(inputID);/*.then(function (c) { - //$scope.results = c; - });*/ - $scope.results = searchService.getLatestResults(0, 5); - console.log('$scope results', $scope.results); + // Get the results + $scope.results = searchService.getLatestResults(0, numResults); + + // Check to make sure that these results are the latest ones + function waitForLatest() { + var timestamps = searchService.getLatestTimestamps(), + areOld = timestamps.some(function(c) {return c < timestamp;}); + // If any of the timestamps are older than the one we made the query with + if (areOld) { + // Then wait and try to update again + searchService.updateResults(); + var latest = searchService.getLatestResults(0, numResults); + $timeout(waitForLatest, 100); + } else { + // We got the latest results now + $scope.results = searchService.getLatestResults(0, numResults); + } + } + waitForLatest(); } return { diff --git a/platform/features/search/src/providers/GenericSearchProvider.js b/platform/features/search/src/providers/GenericSearchProvider.js index f2a33f4416..95adc8e158 100644 --- a/platform/features/search/src/providers/GenericSearchProvider.js +++ b/platform/features/search/src/providers/GenericSearchProvider.js @@ -46,7 +46,7 @@ define( function GenericSearchProvider($rootScope, $timeout, objectService, workerService) { var worker = workerService.run('genericSearchWorker'), latestResults = [], - lastSearchTimestamp; + lastSearchTimestamp = 0; // Tell the web worker to add a new item's model to its list of items. function indexItem(domainObject) { @@ -76,7 +76,6 @@ define( worker.onmessage = handleResponse; function handleResponse(event) { - console.log('handleResponse', event.data); if (event.data.request === 'search') { // Convert the ids given from the web worker into domain objects var ids = []; @@ -93,7 +92,6 @@ define( }); } lastSearchTimestamp = event.data.timestamp; - console.log('updated latestResults', latestResults, 'with time', lastSearchTimestamp); }); } // If the message was from 'index', we don't need to do anything @@ -197,8 +195,12 @@ define( return { query: queryGeneric, - getLatest: function () { + getLatestResults: function () { return latestResults; + }, + + getLatestTimestamp: function () { + return lastSearchTimestamp; } }; } diff --git a/platform/features/search/src/workers/GenericSearchWorker.js b/platform/features/search/src/workers/GenericSearchWorker.js index 8caa9263ac..a1170fb74b 100644 --- a/platform/features/search/src/workers/GenericSearchWorker.js +++ b/platform/features/search/src/workers/GenericSearchWorker.js @@ -44,7 +44,6 @@ function index(data) { // Takes an object model // Add to indexedItems - console.log('webworker index', data); // TODO: Since this is only within genericsearch, do // we really need to check if the index already holds it? @@ -64,7 +63,18 @@ // Helper function for serach() function convertToTerms(input) { - return input.split(' '); + var terms = input; + // Shave any spaces off of the ends of the input + while (terms.substr(0, 1) === ' ') { + terms = terms.substring(1, terms.length); + } + while (terms.substr(terms.length - 1, 1) === ' ') { + terms = terms.substring(0, terms.length - 1); + } + // Then split it at the spaces + terms = terms.split(' '); + console.log('terms', terms); + return terms; } // Helper function for search() @@ -103,8 +113,6 @@ // Takes a search input and the number of items to find // Converts it into search terms // Gets matches from indexedItems - console.log('webworker search', data); - console.log('webworker indexedItems', indexedItems); // This results array will hold objects which are composed of // the object's id, model, and score. (The score is wrt only this @@ -126,8 +134,6 @@ } } - console.log('webworker results', results); - var message = { request: 'search', results: results, @@ -141,7 +147,6 @@ } self.onmessage = function (event) { - console.log('webworker onmessage'); if (event.data.request === 'index') { // TODO: Don't really need to post here. self.postMessage(index(event.data));