summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authortbansal <tbansal@chromium.org>2015-11-06 19:49:24 -0800
committerCommit bot <commit-bot@chromium.org>2015-11-07 03:50:00 +0000
commit0f4c24aa707bbecc888e6c77ba03fec58ed011d1 (patch)
tree5793d88245b7ac67d734f22e2bf763029022e0a9
parente40fbd0e0083b17c3e5c398a448fb7c70a1c8267 (diff)
downloadchromium_src-0f4c24aa707bbecc888e6c77ba03fec58ed011d1.zip
chromium_src-0f4c24aa707bbecc888e6c77ba03fec58ed011d1.tar.gz
chromium_src-0f4c24aa707bbecc888e6c77ba03fec58ed011d1.tar.bz2
ExternalDataUseObserver JNI integration
- ExternalDataUseObserver fetches matching rules over JNI periodically. - ExternalDataUseObserver buffers data use reports until enough number of bytes have been buffered. Once enough bytes have been buffered, data use report is sent over JNI. - Field trial is used to control the value of various constants. BUG=540061 Review URL: https://codereview.chromium.org/1412813007 Cr-Commit-Position: refs/heads/master@{#358511}
-rw-r--r--chrome/browser/android/data_usage/external_data_use_observer.cc76
-rw-r--r--chrome/browser/android/data_usage/external_data_use_observer.h33
-rw-r--r--chrome/browser/android/data_usage/external_data_use_observer_unittest.cc180
3 files changed, 262 insertions, 27 deletions
diff --git a/chrome/browser/android/data_usage/external_data_use_observer.cc b/chrome/browser/android/data_usage/external_data_use_observer.cc
index 2ffa3ff..a9fd19a 100644
--- a/chrome/browser/android/data_usage/external_data_use_observer.cc
+++ b/chrome/browser/android/data_usage/external_data_use_observer.cc
@@ -8,7 +8,10 @@
#include "base/android/jni_string.h"
#include "base/message_loop/message_loop.h"
+#include "base/metrics/field_trial.h"
+#include "base/strings/string_number_conversions.h"
#include "components/data_usage/core/data_use.h"
+#include "components/variations/variations_associated_data.h"
#include "content/public/browser/browser_thread.h"
#include "jni/ExternalDataUseObserver_jni.h"
#include "third_party/re2/re2/re2.h"
@@ -17,10 +20,55 @@
using base::android::ConvertUTF8ToJavaString;
using base::android::ToJavaArrayOfStrings;
+namespace {
+
+// Default duration after which matching rules are periodically fetched. May be
+// overridden by the field trial.
+const int kDefaultFetchMatchingRulesDurationSeconds = 60 * 15; // 15 minutes.
+
+// Default value of the minimum number of bytes that should be buffered before
+// a data use report is submitted. May be overridden by the field trial.
+const int64_t kDefaultDataUseReportMinBytes = 100 * 1024; // 100 KB.
+
+// Populates various parameters from the values specified in the field trial.
+int32_t GetFetchMatchingRulesDurationSeconds() {
+ int32_t duration_seconds = -1;
+ std::string variation_value = variations::GetVariationParamValue(
+ chrome::android::ExternalDataUseObserver::
+ kExternalDataUseObserverFieldTrial,
+ "fetch_matching_rules_duration_seconds");
+ if (!variation_value.empty() &&
+ base::StringToInt(variation_value, &duration_seconds)) {
+ DCHECK_LE(0, duration_seconds);
+ return duration_seconds;
+ }
+ return kDefaultFetchMatchingRulesDurationSeconds;
+}
+
+// Populates various parameters from the values specified in the field trial.
+int64_t GetMinBytes() {
+ int64_t min_bytes = -1;
+ std::string variation_value = variations::GetVariationParamValue(
+ chrome::android::ExternalDataUseObserver::
+ kExternalDataUseObserverFieldTrial,
+ "data_use_report_min_bytes");
+ if (!variation_value.empty() &&
+ base::StringToInt64(variation_value, &min_bytes)) {
+ DCHECK_LE(0, min_bytes);
+ return min_bytes;
+ }
+ return kDefaultDataUseReportMinBytes;
+}
+
+} // namespace
+
namespace chrome {
namespace android {
+const char ExternalDataUseObserver::kExternalDataUseObserverFieldTrial[] =
+ "ExternalDataUseObserver";
+
ExternalDataUseObserver::ExternalDataUseObserver(
data_usage::DataUseAggregator* data_use_aggregator,
scoped_refptr<base::SingleThreadTaskRunner> io_task_runner,
@@ -32,11 +80,17 @@ ExternalDataUseObserver::ExternalDataUseObserver(
io_task_runner_(io_task_runner),
ui_task_runner_(ui_task_runner),
previous_report_time_(base::Time::Now()),
+ last_matching_rules_fetch_time_(base::TimeTicks::Now()),
+ total_bytes_buffered_(0),
+ fetch_matching_rules_duration_(
+ base::TimeDelta::FromSeconds(GetFetchMatchingRulesDurationSeconds())),
+ data_use_report_min_bytes_(GetMinBytes()),
io_weak_factory_(this),
ui_weak_factory_(this) {
DCHECK(data_use_aggregator_);
DCHECK(io_task_runner_);
DCHECK(ui_task_runner_);
+
ui_task_runner_->PostTask(
FROM_HERE,
base::Bind(&ExternalDataUseObserver::CreateJavaObjectOnUIThread,
@@ -154,6 +208,17 @@ void ExternalDataUseObserver::OnDataUse(
const std::vector<const data_usage::DataUse*>& data_use_sequence) {
DCHECK(thread_checker_.CalledOnValidThread());
+ // If the time when the matching rules were last fetched is more than
+ // |fetch_matching_rules_duration_|, fetch them again.
+ if (base::TimeTicks::Now() - last_matching_rules_fetch_time_ >=
+ fetch_matching_rules_duration_) {
+ last_matching_rules_fetch_time_ = base::TimeTicks::Now();
+ ui_task_runner_->PostTask(
+ FROM_HERE,
+ base::Bind(&ExternalDataUseObserver::FetchMatchingRulesOnUIThread,
+ GetUIWeakPtr()));
+ }
+
if (matching_rules_fetch_pending_) {
// TODO(tbansal): Buffer reports.
}
@@ -199,8 +264,7 @@ void ExternalDataUseObserver::BufferDataUseReport(
// Limit the buffer size.
if (buffered_data_reports_.size() == kMaxBufferSize) {
// TODO(tbansal): Add UMA to track impact of lost reports.
- // Remove the first entry.
- buffered_data_reports_.erase(buffered_data_reports_.begin());
+ return;
}
buffered_data_reports_.insert(std::make_pair(data_use_report_key, report));
} else {
@@ -214,9 +278,9 @@ void ExternalDataUseObserver::BufferDataUseReport(
buffered_data_reports_.insert(
std::make_pair(data_use_report_key, merged_report));
}
+ total_bytes_buffered_ += (data_use->rx_bytes + data_use->tx_bytes);
- DCHECK_LE(buffered_data_reports_.size(),
- static_cast<size_t>(kMaxBufferSize));
+ DCHECK_LE(buffered_data_reports_.size(), static_cast<size_t>(kMaxBufferSize));
}
void ExternalDataUseObserver::SubmitBufferedDataUseReport() {
@@ -225,7 +289,8 @@ void ExternalDataUseObserver::SubmitBufferedDataUseReport() {
if (submit_data_report_pending_ || buffered_data_reports_.empty())
return;
- // TODO(tbansal): Keep buffering until enough data has been received.
+ if (total_bytes_buffered_ < data_use_report_min_bytes_)
+ return;
// Send one data use report.
DataUseReports::iterator it = buffered_data_reports_.begin();
@@ -234,6 +299,7 @@ void ExternalDataUseObserver::SubmitBufferedDataUseReport() {
// Remove the entry from the map.
buffered_data_reports_.erase(it);
+ total_bytes_buffered_ -= (report.bytes_downloaded + report.bytes_uploaded);
submit_data_report_pending_ = true;
diff --git a/chrome/browser/android/data_usage/external_data_use_observer.h b/chrome/browser/android/data_usage/external_data_use_observer.h
index 1db5416..20cc178 100644
--- a/chrome/browser/android/data_usage/external_data_use_observer.h
+++ b/chrome/browser/android/data_usage/external_data_use_observer.h
@@ -9,11 +9,11 @@
#include <stdint.h>
#include <string>
-#include <unordered_map>
#include <vector>
#include "base/android/jni_array.h"
#include "base/android/scoped_java_ref.h"
+#include "base/containers/hash_tables.h"
#include "base/gtest_prod_util.h"
#include "base/macros.h"
#include "base/memory/ref_counted.h"
@@ -52,6 +52,9 @@ namespace android {
// TODO(tbansal): Create an inner class that manages the UI and IO threads.
class ExternalDataUseObserver : public data_usage::DataUseAggregator::Observer {
public:
+ // External data use observer field trial name.
+ static const char kExternalDataUseObserverFieldTrial[];
+
ExternalDataUseObserver(
data_usage::DataUseAggregator* data_use_aggregator,
scoped_refptr<base::SingleThreadTaskRunner> io_task_runner,
@@ -93,6 +96,10 @@ class ExternalDataUseObserver : public data_usage::DataUseAggregator::Observer {
TimestampsMergedCorrectly);
FRIEND_TEST_ALL_PREFIXES(ExternalDataUseObserverTest, HashFunction);
FRIEND_TEST_ALL_PREFIXES(ExternalDataUseObserverTest, BufferSize);
+ FRIEND_TEST_ALL_PREFIXES(ExternalDataUseObserverTest,
+ PeriodicFetchMatchingRules);
+ FRIEND_TEST_ALL_PREFIXES(ExternalDataUseObserverTest, BufferDataUseReports);
+ FRIEND_TEST_ALL_PREFIXES(ExternalDataUseObserverTest, Variations);
// DataUseReportKey is a unique identifier for a data use report.
struct DataUseReportKey {
@@ -101,11 +108,6 @@ class ExternalDataUseObserver : public data_usage::DataUseAggregator::Observer {
const std::string& mcc_mnc)
: label(label), connection_type(connection_type), mcc_mnc(mcc_mnc) {}
- DataUseReportKey(const DataUseReportKey& other)
- : label(other.label),
- connection_type(other.connection_type),
- mcc_mnc(other.mcc_mnc) {}
-
bool operator==(const DataUseReportKey& other) const {
return (label == other.label &&
connection_type == other.connection_type &&
@@ -182,9 +184,8 @@ class ExternalDataUseObserver : public data_usage::DataUseAggregator::Observer {
}
};
- typedef std::unordered_map<DataUseReportKey,
- DataUseReport,
- DataUseReportKeyHash> DataUseReports;
+ typedef base::hash_map<DataUseReportKey, DataUseReport, DataUseReportKeyHash>
+ DataUseReports;
// Stores the matching rules.
class MatchingRule {
@@ -312,6 +313,20 @@ class ExternalDataUseObserver : public data_usage::DataUseAggregator::Observer {
// Time when the data use reports were last received from DataUseAggregator.
base::Time previous_report_time_;
+ // Time when the matching rules were last fetched.
+ base::TimeTicks last_matching_rules_fetch_time_;
+
+ // Total number of bytes transmitted or received across all the buffered
+ // reports.
+ int64_t total_bytes_buffered_;
+
+ // Duration after which matching rules are periodically fetched.
+ const base::TimeDelta fetch_matching_rules_duration_;
+
+ // Minimum number of bytes that should be buffered before a data use report is
+ // submitted.
+ const int64_t data_use_report_min_bytes_;
+
base::ThreadChecker thread_checker_;
// |io_weak_factory_| and |ui_weak_factory_| are used for posting tasks on the
diff --git a/chrome/browser/android/data_usage/external_data_use_observer_unittest.cc b/chrome/browser/android/data_usage/external_data_use_observer_unittest.cc
index 18a6985b..cc84caa 100644
--- a/chrome/browser/android/data_usage/external_data_use_observer_unittest.cc
+++ b/chrome/browser/android/data_usage/external_data_use_observer_unittest.cc
@@ -9,11 +9,13 @@
#include "base/memory/scoped_ptr.h"
#include "base/memory/scoped_vector.h"
+#include "base/metrics/field_trial.h"
#include "base/run_loop.h"
#include "base/strings/string_number_conversions.h"
#include "base/thread_task_runner_handle.h"
#include "components/data_usage/core/data_use.h"
#include "components/data_usage/core/data_use_aggregator.h"
+#include "components/variations/variations_associated_data.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/test/test_browser_thread_bundle.h"
#include "net/base/network_change_notifier.h"
@@ -39,6 +41,12 @@ class ExternalDataUseObserverTest : public testing::Test {
ui_task_runner_.get()));
}
+ scoped_ptr<ExternalDataUseObserver> Create() const {
+ return scoped_ptr<ExternalDataUseObserver>(new ExternalDataUseObserver(
+ data_use_aggregator_.get(), io_task_runner_.get(),
+ ui_task_runner_.get()));
+ }
+
ExternalDataUseObserver* external_data_use_observer() const {
return external_data_use_observer_.get();
}
@@ -247,11 +255,13 @@ TEST_F(ExternalDataUseObserverTest, AtMostOneDataUseSubmitRequest) {
std::vector<const data_usage::DataUse*> data_use_sequence;
data_usage::DataUse data_use_foo(
GURL("http://www.google.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
- net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_foo", 1, 2);
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_foo",
+ external_data_use_observer()->data_use_report_min_bytes_, 1);
data_use_sequence.push_back(&data_use_foo);
data_usage::DataUse data_use_bar(
GURL("http://www.google.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
- net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_bar", 1, 2);
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_bar",
+ external_data_use_observer()->data_use_report_min_bytes_, 1);
data_use_sequence.push_back(&data_use_bar);
external_data_use_observer()->OnDataUse(data_use_sequence);
@@ -272,6 +282,8 @@ TEST_F(ExternalDataUseObserverTest, BufferSize) {
std::vector<std::string>(url_regexes.size(), label));
const size_t max_buffer_size = ExternalDataUseObserver::kMaxBufferSize;
+ const int bytes_downloaded = 1000;
+ const int bytes_uploaded = 100;
ScopedVector<data_usage::DataUse> data_use_vector;
// Push more entries than the buffer size. Buffer size should not be exceeded.
@@ -279,7 +291,7 @@ TEST_F(ExternalDataUseObserverTest, BufferSize) {
scoped_ptr<data_usage::DataUse> data_use(new data_usage::DataUse(
GURL("http://www.google.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
net::NetworkChangeNotifier::CONNECTION_UNKNOWN,
- "mccmnc" + base::Int64ToString(i), 0, 0));
+ "mccmnc" + base::Int64ToString(i), bytes_downloaded, bytes_uploaded));
data_use_vector.push_back(data_use.Pass());
}
@@ -287,7 +299,13 @@ TEST_F(ExternalDataUseObserverTest, BufferSize) {
data_use_vector.begin(), data_use_vector.end());
external_data_use_observer()->OnDataUse(const_sequence);
- // One report will be consumed.
+ EXPECT_LE(0, external_data_use_observer()->total_bytes_buffered_);
+
+ // One report will be consumed. Verify that total buffered bytes is computed
+ // correctly.
+ EXPECT_EQ(static_cast<int64_t>((max_buffer_size - 1) *
+ (bytes_downloaded + bytes_uploaded)),
+ external_data_use_observer()->total_bytes_buffered_);
EXPECT_EQ(max_buffer_size - 1,
external_data_use_observer()->buffered_data_reports_.size());
@@ -314,17 +332,20 @@ TEST_F(ExternalDataUseObserverTest, ReportsMergedCorrectly) {
for (size_t i = 0; i < num_iterations; ++i) {
scoped_ptr<data_usage::DataUse> data_use_foo(new data_usage::DataUse(
GURL("http://www.google.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
- net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_foo", 1, 2));
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_foo",
+ external_data_use_observer()->data_use_report_min_bytes_, 1));
data_use_vector.push_back(data_use_foo.Pass());
scoped_ptr<data_usage::DataUse> data_use_bar(new data_usage::DataUse(
GURL("http://www.google.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
- net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_bar", 1, 2));
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_bar",
+ external_data_use_observer()->data_use_report_min_bytes_, 1));
data_use_vector.push_back(data_use_bar.Pass());
scoped_ptr<data_usage::DataUse> data_use_baz(new data_usage::DataUse(
GURL("http://www.google.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
- net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_baz", 1, 2));
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_baz",
+ external_data_use_observer()->data_use_report_min_bytes_, 1));
data_use_vector.push_back(data_use_baz.Pass());
}
@@ -334,11 +355,13 @@ TEST_F(ExternalDataUseObserverTest, ReportsMergedCorrectly) {
external_data_use_observer()->OnDataUse(const_sequence);
EXPECT_EQ(2U, external_data_use_observer()->buffered_data_reports_.size());
- EXPECT_EQ(static_cast<int64_t>(num_iterations * 2),
+ EXPECT_EQ(static_cast<int64_t>(num_iterations * 1),
external_data_use_observer()
->buffered_data_reports_.begin()
->second.bytes_downloaded);
- EXPECT_EQ(static_cast<int64_t>(num_iterations * 1),
+ EXPECT_EQ(static_cast<int64_t>(
+ num_iterations *
+ external_data_use_observer()->data_use_report_min_bytes_),
external_data_use_observer()
->buffered_data_reports_.begin()
->second.bytes_uploaded);
@@ -347,11 +370,13 @@ TEST_F(ExternalDataUseObserverTest, ReportsMergedCorrectly) {
external_data_use_observer()->buffered_data_reports_.erase(
external_data_use_observer()->buffered_data_reports_.begin());
EXPECT_EQ(1U, external_data_use_observer()->buffered_data_reports_.size());
- EXPECT_EQ(static_cast<int64_t>(num_iterations * 2),
+ EXPECT_EQ(static_cast<int64_t>(num_iterations * 1),
external_data_use_observer()
->buffered_data_reports_.begin()
->second.bytes_downloaded);
- EXPECT_EQ(static_cast<int64_t>(num_iterations * 1),
+ EXPECT_EQ(static_cast<int64_t>(
+ num_iterations *
+ external_data_use_observer()->data_use_report_min_bytes_),
external_data_use_observer()
->buffered_data_reports_.begin()
->second.bytes_uploaded);
@@ -426,10 +451,12 @@ TEST_F(ExternalDataUseObserverTest, MultipleMatchingRules) {
std::vector<const data_usage::DataUse*> data_use_sequence;
data_usage::DataUse data_foo_1(
GURL("http://www.foo.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
- net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_1", 0, 0);
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_1",
+ external_data_use_observer()->data_use_report_min_bytes_, 0);
data_usage::DataUse data_foo_2(
GURL("http://www.foo.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
- net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_2", 0, 0);
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_2",
+ external_data_use_observer()->data_use_report_min_bytes_, 0);
data_use_sequence.push_back(&data_foo_1);
data_use_sequence.push_back(&data_foo_2);
external_data_use_observer()->OnDataUse(data_use_sequence);
@@ -484,6 +511,133 @@ TEST_F(ExternalDataUseObserverTest, HashFunction) {
EXPECT_NE(hash(foo), hash(bar_mcc_mnc));
}
+// Tests if matching rules are fetched periodically.
+TEST_F(ExternalDataUseObserverTest, PeriodicFetchMatchingRules) {
+ const std::string label("label");
+
+ std::vector<std::string> url_regexes;
+ url_regexes.push_back(
+ "http://www[.]google[.]com/#q=.*|https://www[.]google[.]com/#q=.*");
+
+ external_data_use_observer()->FetchMatchingRulesCallbackOnIOThread(
+ std::vector<std::string>(url_regexes.size(), std::string()), url_regexes,
+ std::vector<std::string>(url_regexes.size(), label));
+
+ EXPECT_FALSE(external_data_use_observer()->matching_rules_fetch_pending_);
+ EXPECT_FALSE(
+ external_data_use_observer()->last_matching_rules_fetch_time_.is_null());
+
+ std::vector<const data_usage::DataUse*> data_use_sequence;
+ data_usage::DataUse data_use_foo(
+ GURL("http://www.google.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_foo",
+ external_data_use_observer()->data_use_report_min_bytes_, 1);
+ data_use_sequence.push_back(&data_use_foo);
+
+ // Change the time when the fetching rules were fetched.
+ external_data_use_observer()->last_matching_rules_fetch_time_ =
+ base::TimeTicks::Now() -
+ external_data_use_observer()->fetch_matching_rules_duration_;
+ // Matching rules should be expired.
+ EXPECT_GE(base::TimeTicks::Now() -
+ external_data_use_observer()->last_matching_rules_fetch_time_,
+ external_data_use_observer()->fetch_matching_rules_duration_);
+ // OnDataUse should trigger fetching of matching rules.
+ external_data_use_observer()->OnDataUse(data_use_sequence);
+
+ // Matching rules should not be expired.
+ EXPECT_LT(base::TimeTicks::Now() -
+ external_data_use_observer()->last_matching_rules_fetch_time_,
+ external_data_use_observer()->fetch_matching_rules_duration_);
+}
+
+// Tests if data use reports are sent only after the total bytes send/received
+// across all buffered reports have reached the specified threshold.
+TEST_F(ExternalDataUseObserverTest, BufferDataUseReports) {
+ const std::string label("label");
+
+ std::vector<std::string> url_regexes;
+ url_regexes.push_back(
+ "http://www[.]google[.]com/#q=.*|https://www[.]google[.]com/#q=.*");
+
+ external_data_use_observer()->FetchMatchingRulesCallbackOnIOThread(
+ std::vector<std::string>(url_regexes.size(), std::string()), url_regexes,
+ std::vector<std::string>(url_regexes.size(), label));
+
+ // This tests reports 1024 bytes in each loop iteration. For the test to work
+ // properly, |data_use_report_min_bytes_| should be a multiple of 1024.
+ ASSERT_EQ(0, external_data_use_observer()->data_use_report_min_bytes_ % 1024);
+
+ const size_t num_iterations =
+ external_data_use_observer()->data_use_report_min_bytes_ / 1024;
+
+ for (size_t i = 0; i < num_iterations; ++i) {
+ ScopedVector<data_usage::DataUse> data_use_vector;
+
+ scoped_ptr<data_usage::DataUse> data_use_foo(new data_usage::DataUse(
+ GURL("http://www.google.com/#q=abc"), base::TimeTicks::Now(), GURL(), 0,
+ net::NetworkChangeNotifier::CONNECTION_UNKNOWN, "mccmnc_foo", 1024, 0));
+ data_use_vector.push_back(data_use_foo.Pass());
+
+ std::vector<const data_usage::DataUse*> const_sequence(
+ data_use_vector.begin(), data_use_vector.end());
+
+ external_data_use_observer()->OnDataUse(const_sequence);
+ if (i != num_iterations - 1) {
+ // Total buffered bytes is less than the minimum threshold. Data use
+ // report should not be send.
+ EXPECT_FALSE(external_data_use_observer()->submit_data_report_pending_);
+ EXPECT_EQ(static_cast<int64_t>(i + 1),
+ external_data_use_observer()->total_bytes_buffered_ / 1024);
+
+ } else {
+ // Total bytes is at least the minimum threshold. This should trigger
+ // submitting of the buffered data use report.
+ EXPECT_TRUE(external_data_use_observer()->submit_data_report_pending_);
+ EXPECT_EQ(0, external_data_use_observer()->total_bytes_buffered_);
+ }
+ }
+ EXPECT_EQ(0, external_data_use_observer()->total_bytes_buffered_);
+}
+
+// Tests if the parameters from the field trial are populated correctly.
+TEST_F(ExternalDataUseObserverTest, Variations) {
+ EXPECT_EQ(base::TimeDelta::FromSeconds(60 * 15),
+ external_data_use_observer()->fetch_matching_rules_duration_);
+ EXPECT_EQ(100 * 1024,
+ external_data_use_observer()->data_use_report_min_bytes_);
+
+ variations::testing::ClearAllVariationParams();
+ std::map<std::string, std::string> variation_params;
+
+ const int fetch_matching_rules_duration_seconds = 10000;
+ const int64_t data_use_report_min_bytes = 5000;
+ variation_params["fetch_matching_rules_duration_seconds"] =
+ base::Int64ToString(fetch_matching_rules_duration_seconds);
+ variation_params["data_use_report_min_bytes"] =
+ base::Int64ToString(data_use_report_min_bytes);
+
+ ASSERT_TRUE(variations::AssociateVariationParams(
+ ExternalDataUseObserver::kExternalDataUseObserverFieldTrial, "Enabled",
+ variation_params));
+
+ base::FieldTrialList field_trial_list(nullptr);
+
+ base::FieldTrialList::CreateFieldTrial(
+ ExternalDataUseObserver::kExternalDataUseObserverFieldTrial, "Enabled");
+
+ // Create another ExternalDataUseObserver object. This would fetch variation
+ // params.
+ scoped_ptr<ExternalDataUseObserver>
+ external_data_use_obsever_with_variations = Create();
+ EXPECT_EQ(base::TimeDelta::FromSeconds(fetch_matching_rules_duration_seconds),
+ external_data_use_obsever_with_variations
+ ->fetch_matching_rules_duration_);
+ EXPECT_EQ(
+ data_use_report_min_bytes,
+ external_data_use_obsever_with_variations->data_use_report_min_bytes_);
+}
+
} // namespace android
} // namespace chrome