Home | History | Annotate | Download | only in test
      1 // Copyright 2017 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "base/test/scoped_feature_list.h"
      6 
      7 #include <map>
      8 #include <string>
      9 #include <utility>
     10 
     11 #include "base/metrics/field_trial.h"
     12 #include "base/metrics/field_trial_params.h"
     13 #include "testing/gtest/include/gtest/gtest.h"
     14 
     15 namespace base {
     16 namespace test {
     17 
     18 namespace {
     19 
     20 const Feature kTestFeature1{"TestFeature1", FEATURE_DISABLED_BY_DEFAULT};
     21 const Feature kTestFeature2{"TestFeature2", FEATURE_DISABLED_BY_DEFAULT};
     22 
     23 void ExpectFeatures(const std::string& enabled_features,
     24                     const std::string& disabled_features) {
     25   FeatureList* list = FeatureList::GetInstance();
     26   std::string actual_enabled_features;
     27   std::string actual_disabled_features;
     28 
     29   list->GetFeatureOverrides(&actual_enabled_features,
     30                             &actual_disabled_features);
     31 
     32   EXPECT_EQ(enabled_features, actual_enabled_features);
     33   EXPECT_EQ(disabled_features, actual_disabled_features);
     34 }
     35 
     36 }  // namespace
     37 
     38 class ScopedFeatureListTest : public testing::Test {
     39  public:
     40   ScopedFeatureListTest() {
     41     // Clear default feature list.
     42     std::unique_ptr<FeatureList> feature_list(new FeatureList);
     43     feature_list->InitializeFromCommandLine(std::string(), std::string());
     44     original_feature_list_ = FeatureList::ClearInstanceForTesting();
     45     FeatureList::SetInstance(std::move(feature_list));
     46   }
     47 
     48   ~ScopedFeatureListTest() override {
     49     // Restore feature list.
     50     if (original_feature_list_) {
     51       FeatureList::ClearInstanceForTesting();
     52       FeatureList::RestoreInstanceForTesting(std::move(original_feature_list_));
     53     }
     54   }
     55 
     56  private:
     57   // Save the present FeatureList and restore it after test finish.
     58   std::unique_ptr<FeatureList> original_feature_list_;
     59 
     60   DISALLOW_COPY_AND_ASSIGN(ScopedFeatureListTest);
     61 };
     62 
     63 TEST_F(ScopedFeatureListTest, BasicScoped) {
     64   ExpectFeatures(std::string(), std::string());
     65   EXPECT_FALSE(FeatureList::IsEnabled(kTestFeature1));
     66   {
     67     test::ScopedFeatureList feature_list1;
     68     feature_list1.InitFromCommandLine("TestFeature1", std::string());
     69     ExpectFeatures("TestFeature1", std::string());
     70     EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature1));
     71   }
     72   ExpectFeatures(std::string(), std::string());
     73   EXPECT_FALSE(FeatureList::IsEnabled(kTestFeature1));
     74 }
     75 
     76 TEST_F(ScopedFeatureListTest, EnableWithFeatureParameters) {
     77   const char kParam1[] = "param_1";
     78   const char kParam2[] = "param_2";
     79   const char kValue1[] = "value_1";
     80   const char kValue2[] = "value_2";
     81   std::map<std::string, std::string> parameters;
     82   parameters[kParam1] = kValue1;
     83   parameters[kParam2] = kValue2;
     84 
     85   ExpectFeatures(std::string(), std::string());
     86   EXPECT_EQ(nullptr, FeatureList::GetFieldTrial(kTestFeature1));
     87   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature1, kParam1));
     88   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature1, kParam2));
     89   FieldTrial::ActiveGroups active_groups;
     90   FieldTrialList::GetActiveFieldTrialGroups(&active_groups);
     91   EXPECT_EQ(0u, active_groups.size());
     92 
     93   {
     94     test::ScopedFeatureList feature_list;
     95 
     96     feature_list.InitAndEnableFeatureWithParameters(kTestFeature1, parameters);
     97     EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature1));
     98     EXPECT_EQ(kValue1,
     99               GetFieldTrialParamValueByFeature(kTestFeature1, kParam1));
    100     EXPECT_EQ(kValue2,
    101               GetFieldTrialParamValueByFeature(kTestFeature1, kParam2));
    102     active_groups.clear();
    103     FieldTrialList::GetActiveFieldTrialGroups(&active_groups);
    104     EXPECT_EQ(1u, active_groups.size());
    105   }
    106 
    107   ExpectFeatures(std::string(), std::string());
    108   EXPECT_EQ(nullptr, FeatureList::GetFieldTrial(kTestFeature1));
    109   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature1, kParam1));
    110   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature1, kParam2));
    111   active_groups.clear();
    112   FieldTrialList::GetActiveFieldTrialGroups(&active_groups);
    113   EXPECT_EQ(0u, active_groups.size());
    114 }
    115 
    116 TEST_F(ScopedFeatureListTest, OverrideWithFeatureParameters) {
    117   FieldTrialList field_trial_list(nullptr);
    118   scoped_refptr<FieldTrial> trial =
    119       FieldTrialList::CreateFieldTrial("foo", "bar");
    120   const char kParam[] = "param_1";
    121   const char kValue[] = "value_1";
    122   std::map<std::string, std::string> parameters;
    123   parameters[kParam] = kValue;
    124 
    125   test::ScopedFeatureList feature_list1;
    126   feature_list1.InitFromCommandLine("TestFeature1<foo,TestFeature2",
    127                                     std::string());
    128 
    129   // Check initial state.
    130   ExpectFeatures("TestFeature1<foo,TestFeature2", std::string());
    131   EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature1));
    132   EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature2));
    133   EXPECT_EQ(trial.get(), FeatureList::GetFieldTrial(kTestFeature1));
    134   EXPECT_EQ(nullptr, FeatureList::GetFieldTrial(kTestFeature2));
    135   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature1, kParam));
    136   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature2, kParam));
    137 
    138   {
    139     // Override feature with existing field trial.
    140     test::ScopedFeatureList feature_list2;
    141 
    142     feature_list2.InitAndEnableFeatureWithParameters(kTestFeature1, parameters);
    143     EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature1));
    144     EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature2));
    145     EXPECT_EQ(kValue, GetFieldTrialParamValueByFeature(kTestFeature1, kParam));
    146     EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature2, kParam));
    147     EXPECT_NE(trial.get(), FeatureList::GetFieldTrial(kTestFeature1));
    148     EXPECT_NE(nullptr, FeatureList::GetFieldTrial(kTestFeature1));
    149     EXPECT_EQ(nullptr, FeatureList::GetFieldTrial(kTestFeature2));
    150   }
    151 
    152   // Check that initial state is restored.
    153   ExpectFeatures("TestFeature1<foo,TestFeature2", std::string());
    154   EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature1));
    155   EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature2));
    156   EXPECT_EQ(trial.get(), FeatureList::GetFieldTrial(kTestFeature1));
    157   EXPECT_EQ(nullptr, FeatureList::GetFieldTrial(kTestFeature2));
    158   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature1, kParam));
    159   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature2, kParam));
    160 
    161   {
    162     // Override feature with no existing field trial.
    163     test::ScopedFeatureList feature_list2;
    164 
    165     feature_list2.InitAndEnableFeatureWithParameters(kTestFeature2, parameters);
    166     EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature1));
    167     EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature2));
    168     EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature1, kParam));
    169     EXPECT_EQ(kValue, GetFieldTrialParamValueByFeature(kTestFeature2, kParam));
    170     EXPECT_EQ(trial.get(), FeatureList::GetFieldTrial(kTestFeature1));
    171     EXPECT_NE(nullptr, FeatureList::GetFieldTrial(kTestFeature2));
    172   }
    173 
    174   // Check that initial state is restored.
    175   ExpectFeatures("TestFeature1<foo,TestFeature2", std::string());
    176   EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature1));
    177   EXPECT_TRUE(FeatureList::IsEnabled(kTestFeature2));
    178   EXPECT_EQ(trial.get(), FeatureList::GetFieldTrial(kTestFeature1));
    179   EXPECT_EQ(nullptr, FeatureList::GetFieldTrial(kTestFeature2));
    180   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature1, kParam));
    181   EXPECT_EQ("", GetFieldTrialParamValueByFeature(kTestFeature2, kParam));
    182 }
    183 
    184 TEST_F(ScopedFeatureListTest, EnableFeatureOverrideDisable) {
    185   test::ScopedFeatureList feature_list1;
    186   feature_list1.InitWithFeatures({}, {kTestFeature1});
    187 
    188   {
    189     test::ScopedFeatureList feature_list2;
    190     feature_list2.InitWithFeatures({kTestFeature1}, {});
    191     ExpectFeatures("TestFeature1", std::string());
    192   }
    193 }
    194 
    195 TEST_F(ScopedFeatureListTest, FeatureOverrideNotMakeDuplicate) {
    196   test::ScopedFeatureList feature_list1;
    197   feature_list1.InitWithFeatures({}, {kTestFeature1});
    198 
    199   {
    200     test::ScopedFeatureList feature_list2;
    201     feature_list2.InitWithFeatures({}, {kTestFeature1});
    202     ExpectFeatures(std::string(), "TestFeature1");
    203   }
    204 }
    205 
    206 TEST_F(ScopedFeatureListTest, FeatureOverrideFeatureWithDefault) {
    207   test::ScopedFeatureList feature_list1;
    208   feature_list1.InitFromCommandLine("*TestFeature1", std::string());
    209 
    210   {
    211     test::ScopedFeatureList feature_list2;
    212     feature_list2.InitWithFeatures({kTestFeature1}, {});
    213     ExpectFeatures("TestFeature1", std::string());
    214   }
    215 }
    216 
    217 TEST_F(ScopedFeatureListTest, FeatureOverrideFeatureWithDefault2) {
    218   test::ScopedFeatureList feature_list1;
    219   feature_list1.InitFromCommandLine("*TestFeature1", std::string());
    220 
    221   {
    222     test::ScopedFeatureList feature_list2;
    223     feature_list2.InitWithFeatures({}, {kTestFeature1});
    224     ExpectFeatures(std::string(), "TestFeature1");
    225   }
    226 }
    227 
    228 TEST_F(ScopedFeatureListTest, FeatureOverrideFeatureWithEnabledFieldTrial) {
    229   test::ScopedFeatureList feature_list1;
    230 
    231   std::unique_ptr<FeatureList> feature_list(new FeatureList);
    232   FieldTrialList field_trial_list(nullptr);
    233   FieldTrial* trial = FieldTrialList::CreateFieldTrial("TrialExample", "A");
    234   feature_list->RegisterFieldTrialOverride(
    235       kTestFeature1.name, FeatureList::OVERRIDE_ENABLE_FEATURE, trial);
    236   feature_list1.InitWithFeatureList(std::move(feature_list));
    237 
    238   {
    239     test::ScopedFeatureList feature_list2;
    240     feature_list2.InitWithFeatures({kTestFeature1}, {});
    241     ExpectFeatures("TestFeature1", std::string());
    242   }
    243 }
    244 
    245 TEST_F(ScopedFeatureListTest, FeatureOverrideFeatureWithDisabledFieldTrial) {
    246   test::ScopedFeatureList feature_list1;
    247 
    248   std::unique_ptr<FeatureList> feature_list(new FeatureList);
    249   FieldTrialList field_trial_list(nullptr);
    250   FieldTrial* trial = FieldTrialList::CreateFieldTrial("TrialExample", "A");
    251   feature_list->RegisterFieldTrialOverride(
    252       kTestFeature1.name, FeatureList::OVERRIDE_DISABLE_FEATURE, trial);
    253   feature_list1.InitWithFeatureList(std::move(feature_list));
    254 
    255   {
    256     test::ScopedFeatureList feature_list2;
    257     feature_list2.InitWithFeatures({kTestFeature1}, {});
    258     ExpectFeatures("TestFeature1", std::string());
    259   }
    260 }
    261 
    262 TEST_F(ScopedFeatureListTest, FeatureOverrideKeepsOtherExistingFeature) {
    263   test::ScopedFeatureList feature_list1;
    264   feature_list1.InitWithFeatures({}, {kTestFeature1});
    265 
    266   {
    267     test::ScopedFeatureList feature_list2;
    268     feature_list2.InitWithFeatures({}, {kTestFeature2});
    269     EXPECT_FALSE(FeatureList::IsEnabled(kTestFeature1));
    270     EXPECT_FALSE(FeatureList::IsEnabled(kTestFeature2));
    271   }
    272 }
    273 
    274 TEST_F(ScopedFeatureListTest, FeatureOverrideKeepsOtherExistingFeature2) {
    275   test::ScopedFeatureList feature_list1;
    276   feature_list1.InitWithFeatures({}, {kTestFeature1});
    277 
    278   {
    279     test::ScopedFeatureList feature_list2;
    280     feature_list2.InitWithFeatures({kTestFeature2}, {});
    281     ExpectFeatures("TestFeature2", "TestFeature1");
    282   }
    283 }
    284 
    285 TEST_F(ScopedFeatureListTest, FeatureOverrideKeepsOtherExistingDefaultFeature) {
    286   test::ScopedFeatureList feature_list1;
    287   feature_list1.InitFromCommandLine("*TestFeature1", std::string());
    288 
    289   {
    290     test::ScopedFeatureList feature_list2;
    291     feature_list2.InitWithFeatures({}, {kTestFeature2});
    292     ExpectFeatures("*TestFeature1", "TestFeature2");
    293   }
    294 }
    295 
    296 TEST_F(ScopedFeatureListTest, ScopedFeatureListIsNoopWhenNotInitialized) {
    297   test::ScopedFeatureList feature_list1;
    298   feature_list1.InitFromCommandLine("*TestFeature1", std::string());
    299 
    300   // A ScopedFeatureList on which Init() is not called should not reset things
    301   // when going out of scope.
    302   { test::ScopedFeatureList feature_list2; }
    303 
    304   ExpectFeatures("*TestFeature1", std::string());
    305 }
    306 
    307 }  // namespace test
    308 }  // namespace base
    309