OLD | NEW |
---|---|
(Empty) | |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | |
Alexei Svitkine (slow)
2016/03/29 16:29:10
2016
gayane -on leave until 09-2017
2016/03/31 01:38:24
Done.
| |
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 "components/metrics/data_use_tracker.h" | |
6 | |
7 #include <string> | |
8 | |
9 #include "base/strings/string_number_conversions.h" | |
10 #include "base/strings/stringprintf.h" | |
11 #include "components/metrics/metrics_pref_names.h" | |
12 #include "components/prefs/scoped_user_pref_update.h" | |
13 #include "components/variations/variations_associated_data.h" | |
14 #include "content/public/browser/browser_thread.h" | |
15 | |
16 namespace metrics { | |
17 | |
18 namespace { | |
19 static scoped_ptr<metrics::DataUseTracker> instance_; | |
Alexei Svitkine (slow)
2016/03/29 16:29:10
This is not needed anymore, right?
gayane -on leave until 09-2017
2016/03/31 01:38:24
Done.
| |
20 } | |
21 | |
22 // static | |
23 void DataUseTracker::GetForwardingCallback( | |
24 base::WeakPtr<DataUseTracker> data_use_tracker, | |
25 base::Callback<void(base::Callback<void(const std::string&, int)>)> | |
26 reply_callback) { | |
27 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); | |
28 content::BrowserThread::PostTaskAndReplyWithResult( | |
29 content::BrowserThread::UI, FROM_HERE, | |
30 base::Bind(&DataUseTracker::GetForwardingCallbackOnUIThread, | |
31 data_use_tracker), | |
32 reply_callback); | |
33 } | |
34 | |
35 // static | |
36 base::Callback<void(const std::string&, int)> | |
37 DataUseTracker::GetForwardingCallbackOnUIThread( | |
38 base::WeakPtr<DataUseTracker> data_use_tracker) { | |
39 DCHECK_CURRENTLY_ON(content::BrowserThread::UI); | |
40 return base::Bind(&DataUseTracker::UpdateMetricsUsagePrefsOnUIThread, | |
41 data_use_tracker); | |
42 } | |
43 | |
44 void DataUseTracker::RunOnUI( | |
45 base::Callback<void(const std::string&, int)> callback, | |
46 const std::string& service_name, | |
47 int message_size) { | |
48 content::BrowserThread::PostTask( | |
49 content::BrowserThread::UI, FROM_HERE, | |
50 base::Bind(callback, service_name, message_size)); | |
51 } | |
52 | |
53 // static | |
54 void DataUseTracker::RegisterPrefs(PrefRegistrySimple* registry) { | |
55 registry->RegisterDictionaryPref(metrics::prefs::kUserCellDataUse); | |
56 registry->RegisterDictionaryPref(metrics::prefs::kUmaCellDataUse); | |
57 } | |
58 | |
59 DataUseTracker::DataUseTracker(PrefService* local_state) | |
60 : local_state_(local_state), | |
61 uma_qouta_for_testing_(0), | |
62 uma_ratio_for_testing_(0), | |
63 weak_ptr_factory_(this) {} | |
64 | |
65 DataUseTracker::~DataUseTracker() {} | |
66 | |
67 std::string DataUseTracker::GetCurrentMeasurementDate() { | |
68 if (!date_for_testing_.empty()) | |
69 return date_for_testing_; | |
70 | |
71 base::Time::Exploded today_exploded; | |
72 base::Time::Now().LocalMidnight().LocalExplode(&today_exploded); | |
73 return base::StringPrintf("%04d-%02d-%02d", today_exploded.year, | |
74 today_exploded.month, today_exploded.day_of_month); | |
75 } | |
76 | |
77 void DataUseTracker::UpdateMetricsUsagePrefsOnUIThread( | |
78 const std::string& service_name, | |
79 int message_size) { | |
80 DCHECK_CURRENTLY_ON(content::BrowserThread::UI); | |
81 UpdateUsagePref(prefs::kUserCellDataUse, message_size); | |
82 if (service_name == "UMA") | |
83 UpdateUsagePref(prefs::kUmaCellDataUse, message_size); | |
84 } | |
85 | |
86 void DataUseTracker::RemoveExpiredEntries() { | |
87 RemoveExpiredEntriesForPref(prefs::kUmaCellDataUse); | |
88 RemoveExpiredEntriesForPref(prefs::kUserCellDataUse); | |
89 } | |
90 | |
91 void DataUseTracker::RemoveExpiredEntriesForPref(const std::string& pref_name) { | |
92 const base::DictionaryValue* user_pref_dict = | |
93 local_state_->GetDictionary(pref_name); | |
94 if (!user_pref_dict) | |
95 return; | |
96 base::DictionaryValue user_pref_new_dict; | |
97 for (base::DictionaryValue::Iterator it(*user_pref_dict); !it.IsAtEnd(); | |
98 it.Advance()) { | |
99 base::Time start_of_week = | |
100 base::Time::Now().LocalMidnight() - base::TimeDelta::FromDays(7); | |
101 base::Time key_date; | |
102 base::Time::FromString(it.key().c_str(), &key_date); | |
103 if (key_date >= start_of_week) { | |
104 user_pref_new_dict.Set(it.key(), it.value().CreateDeepCopy()); | |
105 } | |
106 } | |
107 local_state_->Set(pref_name, user_pref_new_dict); | |
108 } | |
109 | |
110 void DataUseTracker::UpdateUsagePref(const std::string& pref_name, | |
111 int message_size) { | |
112 DictionaryPrefUpdate pref_updater(local_state_, pref_name); | |
113 int todays_traffic = 0; | |
114 std::string todays_key = GetCurrentMeasurementDate(); | |
115 local_state_->GetDictionary(pref_name)->GetInteger(todays_key, | |
116 &todays_traffic); | |
117 pref_updater->SetInteger(todays_key, todays_traffic + message_size); | |
118 } | |
119 | |
120 bool DataUseTracker::CanUploadUMALog(int log_bytes) { | |
121 RemoveExpiredEntries(); | |
122 int uma_total_data_use = ComputeTotalDataUse(prefs::kUmaCellDataUse); | |
123 int uma_qouta; | |
124 bool is_qouta_specified = GetUmaQouta(&uma_qouta); | |
125 if (!is_qouta_specified || log_bytes + uma_total_data_use <= uma_qouta) | |
126 return true; | |
127 | |
128 double uma_ratio; | |
129 bool is_ratio_specified = GetUmaRatio(&uma_ratio); | |
130 if (!is_ratio_specified) | |
131 return true; | |
132 | |
133 int user_total_data_use = ComputeTotalDataUse(prefs::kUserCellDataUse); | |
134 return (log_bytes + uma_total_data_use) / | |
135 (double)(log_bytes + user_total_data_use) <= | |
136 uma_ratio; | |
137 } | |
138 | |
139 int DataUseTracker::ComputeTotalDataUse(std::string pref_name) { | |
140 int total_data_use = 0; | |
141 const base::DictionaryValue* pref_dict = | |
142 local_state_->GetDictionary(pref_name); | |
143 if (!pref_dict) | |
144 return total_data_use; | |
145 for (base::DictionaryValue::Iterator it(*pref_dict); !it.IsAtEnd(); | |
146 it.Advance()) { | |
147 int value = 0; | |
148 it.value().GetAsInteger(&value); | |
149 total_data_use += value; | |
150 } | |
151 return total_data_use; | |
152 } | |
153 | |
154 bool DataUseTracker::GetUmaQouta(int* qouta) { | |
155 if (uma_qouta_for_testing_ > 0) { | |
156 *qouta = uma_qouta_for_testing_; | |
157 return true; | |
158 } | |
159 | |
160 std::string param_value_str = variations::GetVariationParamValue( | |
161 "UMA_EnableCellularLogUpload", "Uma_Qouta"); | |
162 if (param_value_str.empty()) | |
163 return false; | |
164 | |
165 base::StringToInt(param_value_str, qouta); | |
166 return true; | |
167 } | |
168 | |
169 bool DataUseTracker::GetUmaRatio(double* ratio) { | |
170 if (uma_ratio_for_testing_ > 0) { | |
171 *ratio = uma_ratio_for_testing_; | |
172 return true; | |
173 } | |
174 | |
175 std::string param_value_str = variations::GetVariationParamValue( | |
176 "UMA_EnableCellularLogUpload", "Uma_Ratio"); | |
177 if (param_value_str.empty()) | |
178 return false; | |
179 base::StringToDouble(param_value_str, ratio); | |
180 return true; | |
181 } | |
182 | |
183 void DataUseTracker::SetMeasurementDateForTesting(const std::string& date) { | |
184 date_for_testing_ = date; | |
185 } | |
186 | |
187 void DataUseTracker::SetUmaQoutaForTesting(int uma_qouta) { | |
188 uma_qouta_for_testing_ = uma_qouta; | |
189 } | |
190 | |
191 void DataUseTracker::SetUmaRatioForTesting(double uma_ratio) { | |
192 uma_ratio_for_testing_ = uma_ratio; | |
193 } | |
194 | |
195 base::WeakPtr<DataUseTracker> DataUseTracker::GetWeakPtr() { | |
196 return weak_ptr_factory_.GetWeakPtr(); | |
197 } | |
198 | |
199 } // namespace metrics | |
OLD | NEW |