diff options
Diffstat (limited to 'background_scripts')
| -rw-r--r-- | background_scripts/completion.coffee | 37 | ||||
| -rw-r--r-- | background_scripts/completion_engines.coffee | 26 |
2 files changed, 36 insertions, 27 deletions
diff --git a/background_scripts/completion.coffee b/background_scripts/completion.coffee index 4ae0c44b..bffb9700 100644 --- a/background_scripts/completion.coffee +++ b/background_scripts/completion.coffee @@ -363,23 +363,22 @@ class SearchEngineCompleter haveDescription = description? and 0 < description.length description ||= "#{if custom then "custom " else ""}search" + queryTerms = queryTerms[1..] if custom + query = queryTerms.join " " + + if queryTerms.length == 0 + return onComplete suggestions + # For custom search engines, we add an auto-selected suggestion. if custom - queryTerms = queryTerms[1..] - query = queryTerms.join " " suggestions.push new Suggestion queryTerms: queryTerms type: description - url: searchUrl.replace /%s/g, Utils.createSearchQuery query.split /\s+/ - title: if haveDescription then query else "#{keyword}: #{query}" + url: Utils.createSearchUrl queryTerms, searchUrl + title: if haveDescription then query else "#{keyword}: #{query}" relevancy: 1 - autoSelect: true highlightTerms: false - else - query = queryTerms.join " " - - if queryTerms.length == 0 - return onComplete suggestions + autoSelect: true onComplete suggestions, (existingSuggestions, onComplete) => suggestions = [] @@ -399,23 +398,22 @@ class SearchEngineCompleter relavancy = 0.6 * (Math.min(characterCount, 10.0)/10.0) if 0 < existingSuggestions.length - existingSuggestionMinScore = existingSuggestions[existingSuggestions.length-1].relevancy - if relavancy < existingSuggestionMinScore and MultiCompleter.maxResults <= existingSuggestions.length + existingSuggestionsMinScore = existingSuggestions[existingSuggestions.length-1].relevancy + if relavancy < existingSuggestionsMinScore and MultiCompleter.maxResults <= existingSuggestions.length # No suggestion we propose will have a high enough relavancy to beat the existing suggestions, so bail # immediately. return onComplete [] - CompletionEngines.complete searchUrl, queryTerms, (searchSuggestions = []) => - for suggestion in searchSuggestions + CompletionEngines.complete searchUrl, queryTerms, (completionSuggestions = []) => + for suggestion in completionSuggestions suggestions.push new Suggestion queryTerms: queryTerms type: description - url: searchUrl.replace /%s/g, Utils.createSearchQuery suggestion.split /\s+/ + url: Utils.createSearchUrl suggestion, searchUrl title: suggestion - relevancy: relavancy - insertText: if custom then "#{keyword} #{suggestion}" else suggestion + relevancy: relavancy *= 0.9 highlightTerms: false - relavancy *= 0.9 + insertText: if custom then "#{keyword} #{suggestion}" else suggestion # We keep at least three suggestions (if possible) and at most six. We keep more than three only if # there are enough slots. The idea is that these suggestions shouldn't wholly displace suggestions @@ -501,7 +499,8 @@ class MultiCompleter @filterInProgress = false if shouldRunContinuation continuation suggestions, (newSuggestions) => - onComplete @prepareSuggestions queryTerms, suggestions.concat newSuggestions + if 0 < newSuggestions.length + onComplete @prepareSuggestions queryTerms, suggestions.concat newSuggestions else @filter @mostRecentQuery.queryTerms, @mostRecentQuery.onComplete if @mostRecentQuery diff --git a/background_scripts/completion_engines.coffee b/background_scripts/completion_engines.coffee index 0177806a..1386256f 100644 --- a/background_scripts/completion_engines.coffee +++ b/background_scripts/completion_engines.coffee @@ -116,6 +116,9 @@ completionEngines = [ CompletionEngines = debug: true + # The amount of time to wait for new completions before launching the HTTP request. + delay: 250 + get: (searchUrl, url, callback) -> xhr = new XMLHttpRequest() xhr.open "GET", url, true @@ -139,7 +142,7 @@ CompletionEngines = engine = new engine() return @engineCache.set searchUrl, engine if engine.match searchUrl - # This is the main (actually, the only) entry point. + # This is the main entry point. # - searchUrl is the search engine's URL, e.g. Settings.get("searchUrl"), or a custome search engine's URL. # This is only used as a key for determining the relevant completion engine. # - queryTerms are the queryTerms. @@ -169,34 +172,41 @@ CompletionEngines = completionCacheKey = searchUrl + junk + queryTerms.join junk @completionCache ?= new SimpleCache 60 * 60 * 1000, 2000 # One hour, 2000 entries. if @completionCache.has completionCacheKey - console.log "hit", completionCacheKey if @debug - return callback @completionCache.get completionCacheKey + # We add a short delay, even for a cache hit. This avoids an ugly flicker when the additional + # suggestions are posted. It also makes the vomnibar behave similarly regardless of whether there's a + # cache hit. + Utils.setTimeout @delay, => + console.log "hit", completionCacheKey if @debug + callback @completionCache.get completionCacheKey + return fetchSuggestions = (callback) => engine = @lookupEngine searchUrl url = engine.getUrl queryTerms - console.log "get", url if @debug query = queryTerms.join(" ").toLowerCase() @get searchUrl, url, (xhr = null) => # Parsing the response may fail if we receive an unexpected or an unexpectedly-formatted response. In - # all cases, we fall back to the catch clause, below. + # all cases, we fall back to the catch clause, below. Therefore, we "fail safe" in the case of + # incorrect or out-of-date completion engines. try suggestions = engine.parse xhr # Make sure we really do have an iterable of strings. suggestions = (suggestion for suggestion in suggestions when "string" == typeof suggestion) # Filter out the query itself. It's not adding anything. suggestions = (suggestion for suggestion in suggestions when suggestion.toLowerCase() != query) + console.log "GET", url if @debug catch suggestions = [] - # We cache failures, but remove them after just ten minutes. This (it is hoped) avoids repeated - # XMLHttpRequest failures over a short period of time. + # We allow failures to be cached, but remove them after just ten minutes. This (it is hoped) avoids + # repeated unnecessary XMLHttpRequest failures over a short period of time. removeCompletionCacheKey = => @completionCache.set completionCacheKey, null setTimeout removeCompletionCacheKey, 10 * 60 * 1000 # Ten minutes. + console.log "fail", url if @debug callback suggestions # We pause in case the user is still typing. - Utils.setTimeout 200, handler = @mostRecentHandler = => + Utils.setTimeout @delay, handler = @mostRecentHandler = => if handler != @mostRecentHandler # Bail if another completion has begun, or the user is typing. console.log "bail", completionCacheKey if @debug return callback [] |
