Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2012 The Chromium Authors. All rights reserved. | 1 // Copyright 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "chrome/browser/autocomplete/search_provider.h" | 5 #include "chrome/browser/autocomplete/search_provider.h" |
| 6 | 6 |
| 7 #include "base/metrics/field_trial.h" | 7 #include "base/metrics/field_trial.h" |
| 8 #include "base/run_loop.h" | 8 #include "base/run_loop.h" |
| 9 #include "base/string_util.h" | 9 #include "base/string_util.h" |
| 10 #include "base/time.h" | 10 #include "base/time.h" |
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 61 | 61 |
| 62 static void SetUpTestCase(); | 62 static void SetUpTestCase(); |
| 63 | 63 |
| 64 static void TearDownTestCase(); | 64 static void TearDownTestCase(); |
| 65 | 65 |
| 66 // See description above class for what this registers. | 66 // See description above class for what this registers. |
| 67 virtual void SetUp(); | 67 virtual void SetUp(); |
| 68 | 68 |
| 69 virtual void TearDown(); | 69 virtual void TearDown(); |
| 70 | 70 |
| 71 template<class ResultType> | |
| 72 struct test_data { | |
| 73 const string16 input; | |
| 74 const size_t num_results; | |
| 75 const ResultType output[3]; | |
| 76 }; | |
| 77 | |
| 78 template<class ResultType> | |
| 79 void RunTest(test_data<ResultType>* cases, | |
| 80 int num_cases, | |
| 81 bool prefer_keyword, | |
| 82 ResultType AutocompleteMatch::* member); | |
| 83 | |
| 71 protected: | 84 protected: |
| 72 // Adds a search for |term|, using the engine |t_url| to the history, and | 85 // Adds a search for |term|, using the engine |t_url| to the history, and |
| 73 // returns the URL for that search. | 86 // returns the URL for that search. |
| 74 GURL AddSearchToHistory(TemplateURL* t_url, string16 term, int visit_count); | 87 GURL AddSearchToHistory(TemplateURL* t_url, string16 term, int visit_count); |
| 75 | 88 |
| 76 // Looks for a match in |provider_| with |contents| equal to |contents|. | 89 // Looks for a match in |provider_| with |contents| equal to |contents|. |
| 77 // Sets |match| to it if found. Returns whether |match| was set. | 90 // Sets |match| to it if found. Returns whether |match| was set. |
| 78 bool FindMatchWithContents(const string16& contents, | 91 bool FindMatchWithContents(const string16& contents, |
| 79 AutocompleteMatch* match); | 92 AutocompleteMatch* match); |
| 80 | 93 |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 165 &profile_, &TemplateURLServiceFactory::BuildInstanceFor); | 178 &profile_, &TemplateURLServiceFactory::BuildInstanceFor); |
| 166 | 179 |
| 167 TemplateURLService* turl_model = | 180 TemplateURLService* turl_model = |
| 168 TemplateURLServiceFactory::GetForProfile(&profile_); | 181 TemplateURLServiceFactory::GetForProfile(&profile_); |
| 169 | 182 |
| 170 turl_model->Load(); | 183 turl_model->Load(); |
| 171 | 184 |
| 172 // Reset the default TemplateURL. | 185 // Reset the default TemplateURL. |
| 173 TemplateURLData data; | 186 TemplateURLData data; |
| 174 data.short_name = ASCIIToUTF16("t"); | 187 data.short_name = ASCIIToUTF16("t"); |
| 175 data.SetURL("http://defaultturl/{searchTerms}"); | 188 data.SetURL("http://defaulturl/{searchTerms}"); |
|
msw
2013/02/02 02:27:52
The extra 't' stands for 'template', but this is o
Mark P
2013/02/04 19:46:09
Okay. I thought it was a typo. Put back, and twe
| |
| 176 data.suggestions_url = "http://defaultturl2/{searchTerms}"; | 189 data.suggestions_url = "http://defaulturl2/{searchTerms}"; |
| 177 default_t_url_ = new TemplateURL(&profile_, data); | 190 default_t_url_ = new TemplateURL(&profile_, data); |
| 178 turl_model->Add(default_t_url_); | 191 turl_model->Add(default_t_url_); |
| 179 turl_model->SetDefaultSearchProvider(default_t_url_); | 192 turl_model->SetDefaultSearchProvider(default_t_url_); |
| 180 TemplateURLID default_provider_id = default_t_url_->id(); | 193 TemplateURLID default_provider_id = default_t_url_->id(); |
| 181 ASSERT_NE(0, default_provider_id); | 194 ASSERT_NE(0, default_provider_id); |
| 182 | 195 |
| 183 // Add url1, with search term term1_. | 196 // Add url1, with search term term1_. |
| 184 term1_url_ = AddSearchToHistory(default_t_url_, term1_, 1); | 197 term1_url_ = AddSearchToHistory(default_t_url_, term1_, 1); |
| 185 | 198 |
| 186 // Create another TemplateURL. | 199 // Create another TemplateURL. |
| (...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 263 wyt_match)); | 276 wyt_match)); |
| 264 } | 277 } |
| 265 | 278 |
| 266 void SearchProviderTest::TearDown() { | 279 void SearchProviderTest::TearDown() { |
| 267 message_loop_.RunUntilIdle(); | 280 message_loop_.RunUntilIdle(); |
| 268 | 281 |
| 269 // Shutdown the provider before the profile. | 282 // Shutdown the provider before the profile. |
| 270 provider_ = NULL; | 283 provider_ = NULL; |
| 271 } | 284 } |
| 272 | 285 |
| 286 template<class ResultType> | |
| 287 void SearchProviderTest::RunTest( | |
| 288 test_data<ResultType>* cases, | |
| 289 int num_cases, | |
| 290 bool prefer_keyword, | |
| 291 ResultType AutocompleteMatch::* member) { | |
|
msw
2013/02/02 02:27:52
nit: I'm unfamiliar with this syntax, but others s
Mark P
2013/02/04 19:46:09
Left as is. I copied this format from keyword pro
| |
| 292 ACMatches matches; | |
| 293 for (int i = 0; i < num_cases; ++i) { | |
| 294 AutocompleteInput input(cases[i].input, string16::npos, string16(), | |
| 295 false, prefer_keyword, true, | |
| 296 AutocompleteInput::ALL_MATCHES); | |
| 297 provider_->Start(input, false); | |
| 298 matches = provider_->matches(); | |
| 299 EXPECT_EQ(cases[i].num_results, matches.size()) << | |
| 300 ASCIIToUTF16("Input was: ") + cases[i].input; | |
| 301 if (matches.size() == cases[i].num_results) { | |
|
msw
2013/02/02 02:27:52
optional nit: it's okay to ignore this since you c
Mark P
2013/02/04 19:46:09
Left as is. It's not okay because cases could be
| |
| 302 for (size_t j = 0; j < cases[i].num_results; ++j) { | |
| 303 EXPECT_EQ(cases[i].output[j], matches[j].*member) << | |
| 304 ASCIIToUTF16("Input was: ") + cases[i].input; | |
| 305 } | |
| 306 } | |
| 307 } | |
| 308 } | |
| 309 | |
| 273 GURL SearchProviderTest::AddSearchToHistory(TemplateURL* t_url, | 310 GURL SearchProviderTest::AddSearchToHistory(TemplateURL* t_url, |
| 274 string16 term, | 311 string16 term, |
| 275 int visit_count) { | 312 int visit_count) { |
| 276 HistoryService* history = | 313 HistoryService* history = |
| 277 HistoryServiceFactory::GetForProfile(&profile_, | 314 HistoryServiceFactory::GetForProfile(&profile_, |
| 278 Profile::EXPLICIT_ACCESS); | 315 Profile::EXPLICIT_ACCESS); |
| 279 GURL search(t_url->url_ref().ReplaceSearchTerms( | 316 GURL search(t_url->url_ref().ReplaceSearchTerms( |
| 280 TemplateURLRef::SearchTermsArgs(term))); | 317 TemplateURLRef::SearchTermsArgs(term))); |
| 281 static base::Time last_added_time; | 318 static base::Time last_added_time; |
| 282 last_added_time = std::max(base::Time::Now(), | 319 last_added_time = std::max(base::Time::Now(), |
| (...skipping 497 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 780 ASSERT_NO_FATAL_FAILURE(QueryForInputAndSetWYTMatch(ASCIIToUTF16("f"), | 817 ASSERT_NO_FATAL_FAILURE(QueryForInputAndSetWYTMatch(ASCIIToUTF16("f"), |
| 781 &wyt_match)); | 818 &wyt_match)); |
| 782 ASSERT_EQ(2u, provider_->matches().size()); | 819 ASSERT_EQ(2u, provider_->matches().size()); |
| 783 AutocompleteMatch term_match; | 820 AutocompleteMatch term_match; |
| 784 EXPECT_TRUE(FindMatchWithDestination(term_url, &term_match)); | 821 EXPECT_TRUE(FindMatchWithDestination(term_url, &term_match)); |
| 785 EXPECT_GT(term_match.relevance, wyt_match.relevance); | 822 EXPECT_GT(term_match.relevance, wyt_match.relevance); |
| 786 EXPECT_EQ(1u, term_match.inline_autocomplete_offset); | 823 EXPECT_EQ(1u, term_match.inline_autocomplete_offset); |
| 787 EXPECT_EQ(ASCIIToUTF16("FOO"), term_match.fill_into_edit); | 824 EXPECT_EQ(ASCIIToUTF16("FOO"), term_match.fill_into_edit); |
| 788 } | 825 } |
| 789 | 826 |
| 790 // Verifies AutocompleteControllers sets descriptions for results correctly. | 827 // Verifies AutocompleteControllers return results (including keyword |
| 791 TEST_F(SearchProviderTest, UpdateKeywordDescriptions) { | 828 // results) in the right order and set descriptions for them correctly. |
| 829 TEST_F(SearchProviderTest, KeywordOrderingAndDescriptions) { | |
| 792 // Add an entry that corresponds to a keyword search with 'term2'. | 830 // Add an entry that corresponds to a keyword search with 'term2'. |
| 793 AddSearchToHistory(keyword_t_url_, ASCIIToUTF16("term2"), 1); | 831 AddSearchToHistory(keyword_t_url_, ASCIIToUTF16("term2"), 1); |
| 794 profile_.BlockUntilHistoryProcessesPendingRequests(); | 832 profile_.BlockUntilHistoryProcessesPendingRequests(); |
| 795 | 833 |
| 796 AutocompleteController controller(&profile_, NULL, | 834 AutocompleteController controller(&profile_, NULL, |
| 797 AutocompleteProvider::TYPE_SEARCH); | 835 AutocompleteProvider::TYPE_SEARCH); |
| 798 controller.Start(AutocompleteInput( | 836 controller.Start(AutocompleteInput( |
| 799 ASCIIToUTF16("k t"), string16::npos, string16(), false, false, true, | 837 ASCIIToUTF16("k t"), string16::npos, string16(), false, false, true, |
| 800 AutocompleteInput::ALL_MATCHES)); | 838 AutocompleteInput::ALL_MATCHES)); |
| 801 const AutocompleteResult& result = controller.result(); | 839 const AutocompleteResult& result = controller.result(); |
| 802 | 840 |
| 803 // There should be two matches, one for the keyword one for what you typed. | 841 // There should be three matches, one for the keyword history, one for |
| 804 ASSERT_EQ(2u, result.size()); | 842 // keyword provider's what-you-typed, and one for the default provider's |
| 843 // what you typed, in that order. | |
| 844 ASSERT_EQ(3u, result.size()); | |
| 845 EXPECT_EQ(AutocompleteMatch::SEARCH_HISTORY, result.match_at(0).type); | |
| 846 EXPECT_EQ(AutocompleteMatch::SEARCH_OTHER_ENGINE, result.match_at(1).type); | |
| 847 EXPECT_EQ(AutocompleteMatch::SEARCH_WHAT_YOU_TYPED, result.match_at(2).type); | |
| 848 EXPECT_GT(result.match_at(0).relevance, result.match_at(1).relevance); | |
| 849 EXPECT_GT(result.match_at(1).relevance, result.match_at(2).relevance); | |
| 805 | 850 |
| 806 EXPECT_FALSE(result.match_at(0).keyword.empty()); | 851 // The two keyword results should come with the keyword we expect. |
| 807 EXPECT_FALSE(result.match_at(1).keyword.empty()); | 852 EXPECT_EQ(ASCIIToUTF16("k"), result.match_at(0).keyword); |
| 808 EXPECT_NE(result.match_at(0).keyword, result.match_at(1).keyword); | 853 EXPECT_EQ(ASCIIToUTF16("k"), result.match_at(1).keyword); |
| 854 // The default provider has a different keyword. (We don't explicitly | |
| 855 // set it during this test, so all we do is assert that it's different.) | |
| 856 EXPECT_NE(result.match_at(0).keyword, result.match_at(2).keyword); | |
| 809 | 857 |
| 858 // The top result will always have a description. The third result, | |
| 859 // coming from a different provider than the first two, should also. | |
| 860 // Whether the second result has one doesn't matter much. (If it was | |
| 861 // missing, people would infer that it's the same search provider as | |
| 862 // the one above it.) | |
| 810 EXPECT_FALSE(result.match_at(0).description.empty()); | 863 EXPECT_FALSE(result.match_at(0).description.empty()); |
| 811 EXPECT_FALSE(result.match_at(1).description.empty()); | 864 EXPECT_FALSE(result.match_at(2).description.empty()); |
| 812 EXPECT_NE(result.match_at(0).description, result.match_at(1).description); | 865 EXPECT_NE(result.match_at(0).description, result.match_at(2).description); |
| 866 } | |
| 867 | |
| 868 TEST_F(SearchProviderTest, VerbatimURLs) { | |
| 869 test_data<GURL> url_cases[] = { | |
| 870 // Test a simple keyword input. | |
| 871 {ASCIIToUTF16("k foo"), 2, {GURL("http://keyword/foo"), | |
|
msw
2013/02/02 02:27:52
nit: spaces after '{' here and elsewhere
Mark P
2013/02/04 19:46:09
Done.
| |
| 872 GURL("http://defaulturl/k%20foo")}}, | |
| 873 | |
| 874 // Make sure extra whitespace after the keyword doesn't change the | |
|
msw
2013/02/02 02:27:52
What about whitespace before the keyword?
Mark P
2013/02/04 19:46:09
Commented.
| |
| 875 // keyword verbatim query. | |
| 876 {ASCIIToUTF16("k foo"), 2, {GURL("http://keyword/foo"), | |
| 877 GURL("http://defaulturl/k%20%20%20foo")}}, | |
| 878 | |
| 879 // But whitespace elsewhere in the query string should matter to both | |
| 880 // matches. | |
| 881 {ASCIIToUTF16("k foo bar"), 2, | |
| 882 {GURL("http://keyword/foo%20%20bar"), | |
| 883 GURL("http://defaulturl/k%20%20foo%20%20bar")}}, | |
| 884 // Note in the above test case we don't test trailing whitespace because | |
| 885 // SearchProvider still doesn't handle this well. See related bugs: | |
| 886 // 102690, 99239, 164635. | |
| 887 | |
| 888 // Keywords can be prefixed by certain things that should get ignored | |
| 889 // when constructing the keyword match. | |
| 890 {ASCIIToUTF16("www.k foo"), 2, {GURL("http://keyword/foo"), | |
|
msw
2013/02/02 02:27:52
Definitely also check .com if that's applicable (o
Mark P
2013/02/04 19:46:09
Added some tests. (BTW, you cannot add a .com; no
| |
| 891 GURL("http://defaulturl/www.k%20foo")}}, | |
| 892 | |
| 893 // A keyword with no remaining input shouldn't get a keyword verbatim match. | |
| 894 {ASCIIToUTF16("k"), 1, {GURL("http://defaulturl/k")}}, | |
| 895 {ASCIIToUTF16("k "), 1, {GURL("http://defaulturl/k%20")}} | |
| 896 | |
| 897 // The fact that verbatim queries to keyword are handled by KeywordProvider | |
| 898 // not SearchProvider is tested in | |
| 899 // chrome/browser/extensions/api/omnibox/omnibox_apitest.cc. | |
| 900 }; | |
| 901 | |
| 902 // Test not in keyword mode. | |
| 903 RunTest<GURL>(url_cases, arraysize(url_cases), false, | |
| 904 &AutocompleteMatch::destination_url); | |
| 905 | |
| 906 // Test in keyword mode. (Both modes should give the same result.) | |
| 907 RunTest<GURL>(url_cases, arraysize(url_cases), true, | |
| 908 &AutocompleteMatch::destination_url); | |
| 909 } | |
| 910 | |
| 911 // This is similar to the above test except it checks the fill_into_edit | |
|
msw
2013/02/02 02:27:52
You could add these other types to the same TestDa
Mark P
2013/02/04 19:46:09
Done.
| |
| 912 // of the AutocompleteMatch, not the destination_url. | |
| 913 TEST_F(SearchProviderTest, VerbatimFillIntoEdit) { | |
| 914 } | |
| 915 | |
| 916 // This is similar to the above test except it checks the result_type | |
| 917 // of the AutocompleteMatch, not the destination_url. | |
| 918 TEST_F(SearchProviderTest, VerbatimResultTypes) { | |
| 813 } | 919 } |
| 814 | 920 |
| 815 // Verifies Navsuggest results don't set a TemplateURL, which instant relies on. | 921 // Verifies Navsuggest results don't set a TemplateURL, which instant relies on. |
| 816 // Also verifies that just the *first* navigational result is listed as a match | 922 // Also verifies that just the *first* navigational result is listed as a match |
| 817 // if suggested relevance scores were not sent. | 923 // if suggested relevance scores were not sent. |
| 818 TEST_F(SearchProviderTest, NavSuggestNoSuggestedRelevanceScores) { | 924 TEST_F(SearchProviderTest, NavSuggestNoSuggestedRelevanceScores) { |
| 819 QueryForInput(ASCIIToUTF16("a.c"), string16(), false); | 925 QueryForInput(ASCIIToUTF16("a.c"), string16(), false); |
| 820 | 926 |
| 821 // Make sure the default providers suggest service was queried. | 927 // Make sure the default providers suggest service was queried. |
| 822 net::TestURLFetcher* fetcher = test_factory_.GetFetcherByID( | 928 net::TestURLFetcher* fetcher = test_factory_.GetFetcherByID( |
| (...skipping 594 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1417 EXPECT_EQ(AutocompleteMatch::ACMatchClassification::URL, | 1523 EXPECT_EQ(AutocompleteMatch::ACMatchClassification::URL, |
| 1418 match.contents_class[0].style); | 1524 match.contents_class[0].style); |
| 1419 EXPECT_EQ(4U, match.contents_class[1].offset); | 1525 EXPECT_EQ(4U, match.contents_class[1].offset); |
| 1420 EXPECT_EQ(AutocompleteMatch::ACMatchClassification::URL | | 1526 EXPECT_EQ(AutocompleteMatch::ACMatchClassification::URL | |
| 1421 AutocompleteMatch::ACMatchClassification::MATCH, | 1527 AutocompleteMatch::ACMatchClassification::MATCH, |
| 1422 match.contents_class[1].style); | 1528 match.contents_class[1].style); |
| 1423 EXPECT_EQ(5U, match.contents_class[2].offset); | 1529 EXPECT_EQ(5U, match.contents_class[2].offset); |
| 1424 EXPECT_EQ(AutocompleteMatch::ACMatchClassification::URL, | 1530 EXPECT_EQ(AutocompleteMatch::ACMatchClassification::URL, |
| 1425 match.contents_class[2].style); | 1531 match.contents_class[2].style); |
| 1426 } | 1532 } |
| OLD | NEW |