OLD | NEW |
---|---|
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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/ui/passwords/password_bubble_experiment.h" | 5 #include "chrome/browser/ui/passwords/password_bubble_experiment.h" |
6 | 6 |
7 #include "base/files/scoped_temp_dir.h" | 7 #include "base/files/scoped_temp_dir.h" |
8 #include "base/metrics/field_trial.h" | 8 #include "base/metrics/field_trial.h" |
9 #include "base/prefs/pref_service.h" | 9 #include "base/prefs/pref_service.h" |
10 #include "base/strings/string_number_conversions.h" | 10 #include "base/strings/string_number_conversions.h" |
11 #include "chrome/common/pref_names.h" | 11 #include "chrome/common/pref_names.h" |
12 #include "chrome/test/base/testing_profile.h" | 12 #include "chrome/test/base/testing_profile.h" |
13 #include "components/variations/entropy_provider.h" | 13 #include "components/variations/entropy_provider.h" |
14 #include "components/variations/variations_associated_data.h" | 14 #include "components/variations/variations_associated_data.h" |
15 #include "testing/gtest/include/gtest/gtest.h" | 15 #include "testing/gtest/include/gtest/gtest.h" |
16 | 16 |
17 namespace { | 17 namespace { |
18 | 18 |
19 const int kTimeSpanDays = 2; | 19 const char kGroupName[] = "SomeGroupName"; |
20 const int kTimeSpanThreshold = 3; | 20 const int kNopeThreshold = 10; |
21 const int kProbabilityFakeSaves = 0; | |
22 const int kProbabilityHistory = 10; | |
23 | 21 |
24 void SetupTimeSpanExperiment() { | 22 void SetupExperiment() { |
25 ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( | 23 ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( |
26 password_bubble_experiment::kExperimentName, | 24 password_bubble_experiment::kExperimentName, |
27 password_bubble_experiment::kGroupTimeSpanBased)); | 25 kGroupName)); |
28 std::map<std::string, std::string> params; | 26 std::map<std::string, std::string> params; |
29 params[password_bubble_experiment::kParamTimeSpan] = | 27 params[password_bubble_experiment::kParamNopeThreshold] = |
30 base::IntToString(kTimeSpanDays); | 28 base::IntToString(kNopeThreshold); |
31 params[password_bubble_experiment::kParamTimeSpanNopeThreshold] = | |
32 base::IntToString(kTimeSpanThreshold); | |
33 ASSERT_TRUE(variations::AssociateVariationParams( | 29 ASSERT_TRUE(variations::AssociateVariationParams( |
34 password_bubble_experiment::kExperimentName, | 30 password_bubble_experiment::kExperimentName, |
35 password_bubble_experiment::kGroupTimeSpanBased, | 31 kGroupName, |
36 params)); | 32 params)); |
37 } | 33 } |
38 | 34 |
39 void SetupProbabilityExperiment() { | |
40 ASSERT_TRUE(base::FieldTrialList::CreateFieldTrial( | |
41 password_bubble_experiment::kExperimentName, | |
42 password_bubble_experiment::kGroupProbabilityBased)); | |
43 std::map<std::string, std::string> params; | |
44 params[password_bubble_experiment::kParamProbabilityFakeSaves] = | |
45 base::IntToString(kProbabilityFakeSaves); | |
46 params[password_bubble_experiment::kParamProbabilityInteractionsCount] = | |
47 base::IntToString(kProbabilityHistory); | |
48 ASSERT_TRUE(variations::AssociateVariationParams( | |
49 password_bubble_experiment::kExperimentName, | |
50 password_bubble_experiment::kGroupProbabilityBased, | |
51 params)); | |
52 } | |
53 | |
54 } // namespace | 35 } // namespace |
55 | 36 |
56 class PasswordBubbleExperimentTest : public testing::Test { | 37 class PasswordBubbleExperimentTest : public testing::Test { |
57 public: | 38 public: |
58 void SetUp() override { | 39 void SetUp() override { |
59 ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); | 40 ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); |
60 profile_.reset(new TestingProfile(temp_dir_.path())); | 41 profile_.reset(new TestingProfile(temp_dir_.path())); |
61 | 42 |
62 field_trial_list_.reset(new base::FieldTrialList( | 43 field_trial_list_.reset(new base::FieldTrialList( |
63 new metrics::SHA1EntropyProvider("foo"))); | 44 new metrics::SHA1EntropyProvider("foo"))); |
45 } | |
46 | |
47 void TearDown() override { | |
64 variations::testing::ClearAllVariationParams(); | 48 variations::testing::ClearAllVariationParams(); |
65 } | 49 } |
66 | 50 |
67 PrefService* prefs() { return profile_->GetPrefs(); } | 51 PrefService* prefs() { return profile_->GetPrefs(); } |
68 | 52 |
69 private: | 53 private: |
70 base::ScopedTempDir temp_dir_; | 54 base::ScopedTempDir temp_dir_; |
71 scoped_ptr<TestingProfile> profile_; | 55 scoped_ptr<TestingProfile> profile_; |
72 scoped_ptr<base::FieldTrialList> field_trial_list_; | 56 scoped_ptr<base::FieldTrialList> field_trial_list_; |
73 }; | 57 }; |
74 | 58 |
75 TEST_F(PasswordBubbleExperimentTest, TimeSpan) { | 59 TEST_F(PasswordBubbleExperimentTest, NoExperiment) { |
76 SetupTimeSpanExperiment(); | 60 EXPECT_FALSE( |
61 password_bubble_experiment::ShouldShowNeverForThisSiteDefault(prefs())); | |
62 for (int i = 0; i <= kNopeThreshold; ++i) { | |
63 password_bubble_experiment::RecordBubbleClosed( | |
64 prefs(), password_manager::metrics_util::CLICKED_NOPE); | |
65 EXPECT_FALSE( | |
66 password_bubble_experiment::ShouldShowNeverForThisSiteDefault(prefs())); | |
67 } | |
68 } | |
77 | 69 |
78 EXPECT_TRUE(password_bubble_experiment::ShouldShowBubble(prefs())); | 70 TEST_F(PasswordBubbleExperimentTest, WithExperiment) { |
71 SetupExperiment(); | |
72 | |
73 EXPECT_FALSE( | |
74 password_bubble_experiment::ShouldShowNeverForThisSiteDefault(prefs())); | |
79 // Don't save password enough times. | 75 // Don't save password enough times. |
vabr (Chromium)
2015/03/24 09:09:04
This sentence is ambiguous (don't save password, o
vasilii
2015/03/24 10:30:53
Done.
| |
80 for (int i = 0; i < kTimeSpanThreshold; ++i) { | 76 for (int i = 0; i < kNopeThreshold - 1; ++i) { |
81 password_manager::metrics_util::UIDismissalReason reason = i % 2 ? | 77 password_manager::metrics_util::UIDismissalReason reason = |
82 password_manager::metrics_util::NO_DIRECT_INTERACTION : | |
83 password_manager::metrics_util::CLICKED_NOPE; | 78 password_manager::metrics_util::CLICKED_NOPE; |
84 password_bubble_experiment::RecordBubbleClosed(prefs(), reason); | 79 password_bubble_experiment::RecordBubbleClosed(prefs(), reason); |
85 } | 80 } |
86 EXPECT_FALSE(password_bubble_experiment::ShouldShowBubble(prefs())); | 81 EXPECT_FALSE( |
82 password_bubble_experiment::ShouldShowNeverForThisSiteDefault(prefs())); | |
87 | 83 |
88 // Save password many times. It doesn't bring the bubble back while the time | |
89 // span isn't over. | |
90 for (int i = 0; i < 2*kTimeSpanThreshold; ++i) { | |
91 password_bubble_experiment::RecordBubbleClosed( | |
92 prefs(), | |
93 password_manager::metrics_util::CLICKED_SAVE); | |
94 } | |
95 EXPECT_FALSE(password_bubble_experiment::ShouldShowBubble(prefs())); | |
96 } | |
97 | |
98 TEST_F(PasswordBubbleExperimentTest, TimeSpanOver) { | |
99 SetupTimeSpanExperiment(); | |
100 | |
101 base::Time past_interval = | |
102 base::Time::Now() - base::TimeDelta::FromDays(kTimeSpanDays + 1); | |
103 prefs()->SetInt64(prefs::kPasswordBubbleTimeStamp, | |
104 past_interval.ToInternalValue()); | |
105 prefs()->SetInteger(prefs::kPasswordBubbleNopesCount, kTimeSpanThreshold); | |
106 // The time span is over. The bubble should be shown. | |
107 EXPECT_TRUE(password_bubble_experiment::ShouldShowBubble(prefs())); | |
108 EXPECT_EQ(0, prefs()->GetInteger(prefs::kPasswordBubbleNopesCount)); | |
109 | |
110 // Set the old time span again and record "Nope". The counter restarts from 0. | |
111 prefs()->SetInt64(prefs::kPasswordBubbleTimeStamp, | |
112 past_interval.ToInternalValue()); | |
113 password_bubble_experiment::RecordBubbleClosed( | 84 password_bubble_experiment::RecordBubbleClosed( |
114 prefs(), password_manager::metrics_util::CLICKED_NOPE); | 85 prefs(), password_manager::metrics_util::CLICKED_NOPE); |
115 EXPECT_TRUE(password_bubble_experiment::ShouldShowBubble(prefs())); | 86 EXPECT_TRUE( |
116 EXPECT_EQ(1, prefs()->GetInteger(prefs::kPasswordBubbleNopesCount)); | 87 password_bubble_experiment::ShouldShowNeverForThisSiteDefault(prefs())); |
117 } | 88 password_bubble_experiment::RecordBubbleClosed( |
89 prefs(), password_manager::metrics_util::CLICKED_SAVE); | |
90 EXPECT_FALSE( | |
91 password_bubble_experiment::ShouldShowNeverForThisSiteDefault(prefs())); | |
118 | 92 |
119 TEST_F(PasswordBubbleExperimentTest, Probability) { | |
120 SetupProbabilityExperiment(); | |
121 | |
122 EXPECT_TRUE(password_bubble_experiment::ShouldShowBubble(prefs())); | |
123 // Don't save password enough times. | 93 // Don't save password enough times. |
vabr (Chromium)
2015/03/24 09:09:04
This sentence is ambiguous (don't save password, o
vasilii
2015/03/24 10:30:53
Done.
| |
124 for (int i = 0; i < kProbabilityHistory; ++i) { | 94 for (int i = 0; i < kNopeThreshold; ++i) { |
125 password_manager::metrics_util::UIDismissalReason reason = i % 2 ? | 95 password_manager::metrics_util::UIDismissalReason reason = |
126 password_manager::metrics_util::NO_DIRECT_INTERACTION : | |
127 password_manager::metrics_util::CLICKED_NOPE; | 96 password_manager::metrics_util::CLICKED_NOPE; |
128 password_bubble_experiment::RecordBubbleClosed(prefs(), reason); | 97 password_bubble_experiment::RecordBubbleClosed(prefs(), reason); |
129 } | 98 } |
130 EXPECT_FALSE(password_bubble_experiment::ShouldShowBubble(prefs())); | 99 EXPECT_TRUE( |
131 | 100 password_bubble_experiment::ShouldShowNeverForThisSiteDefault(prefs())); |
132 // Save password enough times. | |
133 for (int i = 0; i < kProbabilityHistory; ++i) { | |
134 password_bubble_experiment::RecordBubbleClosed( | |
135 prefs(), | |
136 password_manager::metrics_util::CLICKED_SAVE); | |
137 } | |
138 EXPECT_TRUE(password_bubble_experiment::ShouldShowBubble(prefs())); | |
139 } | 101 } |
OLD | NEW |