diff options
author | sdefresne <sdefresne@chromium.org> | 2015-08-03 07:18:13 -0700 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2015-08-03 14:18:41 +0000 |
commit | 51bbec7be7014d4d75d39c1a5c27b1ba9ddc3dcd (patch) | |
tree | 912625ef3699b6c080aa3cca3340966298130333 /components/search | |
parent | e52e8da071b5d27eead353a38ddbc822af9ef0fc (diff) | |
download | chromium_src-51bbec7be7014d4d75d39c1a5c27b1ba9ddc3dcd.zip chromium_src-51bbec7be7014d4d75d39c1a5c27b1ba9ddc3dcd.tar.gz chromium_src-51bbec7be7014d4d75d39c1a5c27b1ba9ddc3dcd.tar.bz2 |
Partially componentize //chrome/browser/search/search.{h,cc}
Move functions from //chrome/browser/search/search.{h,cc} to the search
component //components/search/search.{h,cc} so that they can be shared
with iOS.
Move all the code in those two files (and supporting unittests) from
the "chrome" to the "search" namespace.
Move unittests that do not depends on non-componentized functions into
the search component.
Implements GetSearchTerms() on iOS that uses a web::WebState* instead
of content::WebContents and simplify the code to remove unsupported
features.
Directly use //components/search on iOS instead of the SearchProvider
when possible.
BUG=514239
TBR=sky,droger,benwells
Review URL: https://codereview.chromium.org/1260033003
Cr-Commit-Position: refs/heads/master@{#341525}
Diffstat (limited to 'components/search')
-rw-r--r-- | components/search/BUILD.gn | 3 | ||||
-rw-r--r-- | components/search/DEPS | 2 | ||||
-rw-r--r-- | components/search/search.cc | 114 | ||||
-rw-r--r-- | components/search/search.h | 57 | ||||
-rw-r--r-- | components/search/search_android_unittest.cc | 87 | ||||
-rw-r--r-- | components/search/search_switches.cc | 11 | ||||
-rw-r--r-- | components/search/search_switches.h | 5 | ||||
-rw-r--r-- | components/search/search_unittest.cc | 110 |
8 files changed, 382 insertions, 7 deletions
diff --git a/components/search/BUILD.gn b/components/search/BUILD.gn index a895701..21c49c4d 100644 --- a/components/search/BUILD.gn +++ b/components/search/BUILD.gn @@ -12,5 +12,8 @@ static_library("search") { deps = [ "//base", + "//components/google/core/browser", + "//components/search_engines", + "//url", ] } diff --git a/components/search/DEPS b/components/search/DEPS index 80f6f90..d9bc813 100644 --- a/components/search/DEPS +++ b/components/search/DEPS @@ -1,3 +1,5 @@ include_rules = [ + "+components/google/core", + "+components/search_engines", "+components/variations", ] diff --git a/components/search/search.cc b/components/search/search.cc index 92b8ccb..654ec55 100644 --- a/components/search/search.cc +++ b/components/search/search.cc @@ -10,9 +10,12 @@ #include "base/strings/string_split.h" #include "base/strings/string_util.h" #include "base/strings/utf_string_conversions.h" +#include "components/google/core/browser/google_util.h" #include "components/search/search_switches.h" +#include "components/search_engines/template_url.h" +#include "url/gurl.h" -namespace chrome { +namespace search { namespace { @@ -49,8 +52,25 @@ const char kEmbeddedSearchFieldTrialName[] = "EmbeddedSearch"; // be ignored and Instant Extended will not be enabled by default. const char kDisablingSuffix[] = "DISABLED"; +#if !defined(OS_IOS) && !defined(OS_ANDROID) +const char kEnableQueryExtractionFlagName[] = "query_extraction"; +#endif + +const char kAllowPrefetchNonDefaultMatch[] = "allow_prefetch_non_default_match"; + +#if defined(OS_ANDROID) +const char kPrefetchSearchResultsFlagName[] = "prefetch_results"; + +// Controls whether to reuse prerendered Instant Search base page to commit any +// search query. +const char kReuseInstantSearchBasePage[] = "reuse_instant_search_base_page"; +#endif + } // namespace +// Negative start-margin values prevent the "es_sm" parameter from being used. +const int kDisableStartMargin = -1; + bool IsInstantExtendedAPIEnabled() { #if defined(OS_IOS) return false; @@ -144,4 +164,94 @@ bool GetBoolValueForFlagWithDefault(const std::string& flag, return !!GetUInt64ValueForFlagWithDefault(flag, default_value ? 1 : 0, flags); } -} // namespace chrome +std::string InstantExtendedEnabledParam(bool for_search) { + if (for_search && !IsQueryExtractionEnabled()) + return std::string(); + return std::string(google_util::kInstantExtendedAPIParam) + "=" + + base::Uint64ToString(EmbeddedSearchPageVersion()) + "&"; +} + +std::string ForceInstantResultsParam(bool for_prerender) { + return (for_prerender || !IsInstantExtendedAPIEnabled()) ? "ion=1&" + : std::string(); +} + +bool IsQueryExtractionEnabled() { +#if defined(OS_IOS) || defined(OS_ANDROID) + return true; +#else + if (!IsInstantExtendedAPIEnabled()) + return false; + + const base::CommandLine* command_line = + base::CommandLine::ForCurrentProcess(); + if (command_line->HasSwitch(switches::kEnableQueryExtraction)) + return true; + + FieldTrialFlags flags; + return GetFieldTrialInfo(&flags) && + GetBoolValueForFlagWithDefault(kEnableQueryExtractionFlagName, false, + flags); +#endif // defined(OS_IOS) || defined(OS_ANDROID) +} + +bool ShouldPrefetchSearchResults() { + if (!IsInstantExtendedAPIEnabled()) + return false; + +#if defined(OS_ANDROID) + if (base::CommandLine::ForCurrentProcess()->HasSwitch( + switches::kPrefetchSearchResults)) { + return true; + } + + FieldTrialFlags flags; + return GetFieldTrialInfo(&flags) && + GetBoolValueForFlagWithDefault(kPrefetchSearchResultsFlagName, false, + flags); +#else + return true; +#endif +} + +bool ShouldReuseInstantSearchBasePage() { + if (!ShouldPrefetchSearchResults()) + return false; + +#if defined(OS_ANDROID) + FieldTrialFlags flags; + return GetFieldTrialInfo(&flags) && + GetBoolValueForFlagWithDefault(kReuseInstantSearchBasePage, false, + flags); +#else + return true; +#endif +} + +bool ShouldAllowPrefetchNonDefaultMatch() { + if (!ShouldPrefetchSearchResults()) + return false; + + FieldTrialFlags flags; + return GetFieldTrialInfo(&flags) && + GetBoolValueForFlagWithDefault(kAllowPrefetchNonDefaultMatch, false, + flags); +} + +// |url| should either have a secure scheme or have a non-HTTPS base URL that +// the user specified using --google-base-url. (This allows testers to use +// --google-base-url to point at non-HTTPS servers, which eases testing.) +bool IsSuitableURLForInstant(const GURL& url, const TemplateURL* template_url) { + return template_url->HasSearchTermsReplacementKey(url) && + (url.SchemeIsCryptographic() || + google_util::StartsWithCommandLineGoogleBaseURL(url)); +} + +void EnableQueryExtractionForTesting() { +#if !defined(OS_IOS) && !defined(OS_ANDROID) + base::CommandLine* cl = base::CommandLine::ForCurrentProcess(); + cl->AppendSwitch(switches::kEnableQueryExtraction); +#endif +} + +} // namespace search diff --git a/components/search/search.h b/components/search/search.h index 0a7a55b..2ce6204 100644 --- a/components/search/search.h +++ b/components/search/search.h @@ -13,7 +13,14 @@ #include "base/strings/string16.h" #include "base/strings/string_split.h" -namespace chrome { +class GURL; +class TemplateURL; + +namespace search { + +// Use this value for "start margin" to prevent the "es_sm" parameter from +// being used. +extern const int kDisableStartMargin; // Returns whether the Instant Extended API is enabled. bool IsInstantExtendedAPIEnabled(); @@ -55,6 +62,52 @@ bool GetBoolValueForFlagWithDefault(const std::string& flag, bool default_value, const FieldTrialFlags& flags); -} // namespace chrome +// Returns a string indicating whether InstantExtended is enabled, suitable +// for adding as a query string param to the homepage or search requests. +// Returns an empty string otherwise. +// +// |for_search| should be set to true for search requests, in which case this +// returns a non-empty string only if query extraction is enabled. +std::string InstantExtendedEnabledParam(bool for_search); + +// Returns a string that will cause the search results page to update +// incrementally. Currently, Instant Extended passes a different param to +// search results pages that also has this effect, so by default this function +// returns the empty string when Instant Extended is enabled. However, when +// doing instant search result prerendering, we still need to pass this param, +// as Instant Extended does not cause incremental updates by default for the +// prerender page. Callers should set |for_prerender| in this case to force +// the returned string to be non-empty. +std::string ForceInstantResultsParam(bool for_prerender); + +// Returns whether query extraction is enabled. +bool IsQueryExtractionEnabled(); + +// Returns true if 'prefetch_results' flag is set to true in field trials to +// prefetch high-confidence search suggestions. +bool ShouldPrefetchSearchResults(); + +// Returns true if 'reuse_instant_search_base_page' flag is set to true in field +// trials to reuse the prerendered page to commit any search query. +bool ShouldReuseInstantSearchBasePage(); + +// Returns true if 'allow_prefetch_non_default_match' flag is enabled in field +// trials to allow prefetching the suggestion marked to be prefetched by the +// suggest server even if it is not the default match. +bool ShouldAllowPrefetchNonDefaultMatch(); + +// |url| should either have a secure scheme or have a non-HTTPS base URL that +// the user specified using --google-base-url. (This allows testers to use +// --google-base-url to point at non-HTTPS servers, which eases testing.) +bool IsSuitableURLForInstant(const GURL& url, const TemplateURL* template_url); + +// ----------------------------------------------------- +// The following APIs are exposed for use in tests only. +// ----------------------------------------------------- + +// Forces query in the omnibox to be on for tests. +void EnableQueryExtractionForTesting(); + +} // namespace search #endif // COMPONENTS_SEARCH_SEARCH_H_ diff --git a/components/search/search_android_unittest.cc b/components/search/search_android_unittest.cc index 772daaf..f5c8320 100644 --- a/components/search/search_android_unittest.cc +++ b/components/search/search_android_unittest.cc @@ -8,11 +8,12 @@ #include "base/memory/scoped_ptr.h" #include "base/metrics/field_trial.h" #include "base/metrics/statistics_recorder.h" +#include "components/search/search.h" #include "components/search/search_switches.h" #include "components/variations/entropy_provider.h" #include "testing/gtest/include/gtest/gtest.h" -namespace chrome { +namespace search { namespace { @@ -25,6 +26,90 @@ TEST(SearchTest, EmbeddedSearchAPIEnabled) { EXPECT_TRUE(IsInstantExtendedAPIEnabled()); } +TEST(SearchTest, QueryExtractionEnabled) { + // Query extraction is always enabled on mobile. + EXPECT_TRUE(IsQueryExtractionEnabled()); +} + +class SearchUtilTest : public testing::Test { + protected: + void SetUp() override { + field_trial_list_.reset( + new base::FieldTrialList(new metrics::SHA1EntropyProvider("42"))); + base::StatisticsRecorder::Initialize(); + } + + private: + scoped_ptr<base::FieldTrialList> field_trial_list_; +}; + +TEST_F(SearchUtilTest, UseDefaultEmbeddedSearchPageVersion) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:-1 query_extraction:1")); + EXPECT_TRUE(IsQueryExtractionEnabled()); + EXPECT_EQ("espv=1&", InstantExtendedEnabledParam(true)); + EXPECT_EQ("espv=1&", InstantExtendedEnabledParam(false)); +} + +TEST_F(SearchUtilTest, ShouldPrefetchSearchResults_InstantExtendedAPIEnabled) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:2 prefetch_results:1")); + EXPECT_TRUE(ShouldPrefetchSearchResults()); + EXPECT_TRUE(IsInstantExtendedAPIEnabled()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + +TEST_F(SearchUtilTest, ShouldPrefetchSearchResults_InstantExtendedAPIDisabled) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:1 prefetch_results:1")); + EXPECT_FALSE(ShouldPrefetchSearchResults()); + EXPECT_FALSE(IsInstantExtendedAPIEnabled()); + EXPECT_EQ(1ul, EmbeddedSearchPageVersion()); +} + +TEST_F(SearchUtilTest, ShouldPrefetchSearchResults_DisabledViaFieldTrials) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:2 prefetch_results:0")); + EXPECT_FALSE(ShouldPrefetchSearchResults()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + +TEST_F(SearchUtilTest, ShouldPrefetchSearchResults_EnabledViaCommandLine) { + base::CommandLine::ForCurrentProcess()->AppendSwitch( + switches::kPrefetchSearchResults); + // Command-line enable should override Finch. + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:2 prefetch_results:0")); + EXPECT_TRUE(ShouldPrefetchSearchResults()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + +TEST_F(SearchUtilTest, + ShouldReuseInstantSearchBasePage_PrefetchResultsFlagDisabled) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", + "Group1 espv:2 prefetch_results:0 reuse_instant_search_base_page:1")); + EXPECT_FALSE(ShouldPrefetchSearchResults()); + EXPECT_FALSE(ShouldReuseInstantSearchBasePage()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + +TEST_F(SearchUtilTest, ShouldReuseInstantSearchBasePage_EnabledViaFieldTrial) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", + "Group1 espv:2 prefetch_results:1 reuse_instant_search_base_page:1")); + EXPECT_TRUE(ShouldReuseInstantSearchBasePage()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + +TEST_F(SearchUtilTest, ShouldReuseInstantSearchBasePage_DisabledViaFieldTrial) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", + "Group1 espv:2 prefetch_results:1 reuse_instant_search_base_page:0")); + EXPECT_FALSE(ShouldReuseInstantSearchBasePage()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + } // namespace } // namespace chrome diff --git a/components/search/search_switches.cc b/components/search/search_switches.cc index 9359725..d3b80da 100644 --- a/components/search/search_switches.cc +++ b/components/search/search_switches.cc @@ -11,6 +11,17 @@ namespace switches { // Enables EmbeddedSearch API in the search results page. const char kEnableEmbeddedSearchAPI[] = "enable-embeddedsearch-api"; +// Triggers prerendering of search base page to prefetch results for the typed +// omnibox query. Only has an effect when prerender is enabled. +const char kPrefetchSearchResults[] = "prefetch-search-results"; + +#endif + +#if !defined(OS_ANDROID) && !defined(OS_IOS) + +// Enables query in the omnibox. +const char kEnableQueryExtraction[] = "enable-query-extraction"; + #endif } // namespace switches diff --git a/components/search/search_switches.h b/components/search/search_switches.h index 48b50c1..46208e07 100644 --- a/components/search/search_switches.h +++ b/components/search/search_switches.h @@ -11,6 +11,11 @@ namespace switches { #if defined(OS_ANDROID) extern const char kEnableEmbeddedSearchAPI[]; +extern const char kPrefetchSearchResults[]; +#endif + +#if !defined(OS_ANDROID) && !defined(OS_IOS) +extern const char kEnableQueryExtraction[]; #endif } // namespace switches diff --git a/components/search/search_unittest.cc b/components/search/search_unittest.cc index 2fd5a23..4a5db38 100644 --- a/components/search/search_unittest.cc +++ b/components/search/search_unittest.cc @@ -9,7 +9,7 @@ #include "components/variations/entropy_provider.h" #include "testing/gtest/include/gtest/gtest.h" -namespace chrome { +namespace search { class EmbeddedSearchFieldTrialTest : public testing::Test { protected: @@ -130,4 +130,110 @@ TEST_F(EmbeddedSearchFieldTrialTest, GetFieldTrialInfoControlFlags) { EXPECT_EQ(3ul, flags.size()); } -} // namespace chrome +#if !defined(OS_IOS) && !defined(OS_ANDROID) +typedef EmbeddedSearchFieldTrialTest SearchTest; + +TEST_F(SearchTest, ShouldPrefetchSearchResults_InstantExtendedAPIEnabled) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial("EmbeddedSearch", + "Group1 espv:2")); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); + EXPECT_TRUE(ShouldPrefetchSearchResults()); +} + +TEST_F(SearchTest, ShouldPrefetchSearchResults_Default) { + EXPECT_TRUE(ShouldPrefetchSearchResults()); +} + +TEST_F(SearchTest, ShouldReuseInstantSearchBasePage_Default) { + EXPECT_TRUE(ShouldReuseInstantSearchBasePage()); +} + +TEST_F(SearchTest, ShouldAllowPrefetchNonDefaultMatch_DisabledViaFieldTrial) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:89 allow_prefetch_non_default_match:0")); + EXPECT_FALSE(ShouldAllowPrefetchNonDefaultMatch()); + EXPECT_EQ(89ul, EmbeddedSearchPageVersion()); +} + +TEST_F(SearchTest, ShouldAllowPrefetchNonDefaultMatch_EnabledViaFieldTrial) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:80 allow_prefetch_non_default_match:1")); + EXPECT_TRUE(ShouldAllowPrefetchNonDefaultMatch()); + EXPECT_EQ(80ul, EmbeddedSearchPageVersion()); +} + +TEST_F(SearchTest, ForceInstantResultsParam) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial("EmbeddedSearch", + "Group1 espv:2")); + EXPECT_TRUE(IsInstantExtendedAPIEnabled()); + EXPECT_EQ("ion=1&", ForceInstantResultsParam(true)); + EXPECT_EQ(std::string(), ForceInstantResultsParam(false)); +} + +typedef EmbeddedSearchFieldTrialTest InstantExtendedEnabledParamTest; + +TEST_F(InstantExtendedEnabledParamTest, QueryExtractionDisabled) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial("EmbeddedSearch", + "Group1 espv:12")); + // Make sure InstantExtendedEnabledParam() returns an empty string for search + // requests. + EXPECT_FALSE(IsQueryExtractionEnabled()); + EXPECT_EQ("", InstantExtendedEnabledParam(true)); + EXPECT_EQ("espv=12&", InstantExtendedEnabledParam(false)); +} + +TEST_F(InstantExtendedEnabledParamTest, QueryExtractionEnabled) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:10 query_extraction:1")); + EXPECT_TRUE(IsQueryExtractionEnabled()); + // Make sure InstantExtendedEnabledParam() returns a non-empty param string + // for search requests. + EXPECT_EQ("espv=10&", InstantExtendedEnabledParam(true)); + EXPECT_EQ("espv=10&", InstantExtendedEnabledParam(false)); +} + +TEST_F(InstantExtendedEnabledParamTest, UseDefaultEmbeddedSearchPageVersion) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:-1 query_extraction:1")); + EXPECT_TRUE(IsQueryExtractionEnabled()); + EXPECT_EQ("espv=2&", InstantExtendedEnabledParam(true)); + EXPECT_EQ("espv=2&", InstantExtendedEnabledParam(false)); +} + +typedef EmbeddedSearchFieldTrialTest IsQueryExtractionEnabledTest; + +TEST_F(IsQueryExtractionEnabledTest, NotSet) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial("EmbeddedSearch", + "Group1 espv:2")); + EXPECT_TRUE(IsInstantExtendedAPIEnabled()); + EXPECT_FALSE(IsQueryExtractionEnabled()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + +TEST_F(IsQueryExtractionEnabledTest, EnabledViaFieldTrial) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:2 query_extraction:1")); + EXPECT_TRUE(IsInstantExtendedAPIEnabled()); + EXPECT_TRUE(IsQueryExtractionEnabled()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + +TEST_F(IsQueryExtractionEnabledTest, DisabledViaFieldTrial) { + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:2 query_extraction:0")); + EXPECT_TRUE(IsInstantExtendedAPIEnabled()); + EXPECT_FALSE(IsQueryExtractionEnabled()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} + +TEST_F(IsQueryExtractionEnabledTest, EnabledViaCommandLine) { + EnableQueryExtractionForTesting(); + ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( + "EmbeddedSearch", "Group1 espv:2 query_extraction:0")); + EXPECT_TRUE(IsInstantExtendedAPIEnabled()); + EXPECT_TRUE(IsQueryExtractionEnabled()); + EXPECT_EQ(2ul, EmbeddedSearchPageVersion()); +} +#endif // !defined(OS_IOS) && !defined(OS_ANDROID) + +} // namespace search |