• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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
3 // found in the LICENSE file.
4 
5 #include "components/domain_reliability/context.h"
6 
7 #include <map>
8 #include <string>
9 
10 #include "base/bind.h"
11 #include "base/memory/scoped_ptr.h"
12 #include "base/message_loop/message_loop_proxy.h"
13 #include "components/domain_reliability/beacon.h"
14 #include "components/domain_reliability/dispatcher.h"
15 #include "components/domain_reliability/scheduler.h"
16 #include "components/domain_reliability/test_util.h"
17 #include "net/base/net_errors.h"
18 #include "net/url_request/url_request_test_util.h"
19 #include "testing/gtest/include/gtest/gtest.h"
20 
21 namespace domain_reliability {
22 namespace {
23 
24 typedef std::vector<DomainReliabilityBeacon> BeaconVector;
25 
MakeBeacon(MockableTime * time)26 DomainReliabilityBeacon MakeBeacon(MockableTime* time) {
27   DomainReliabilityBeacon beacon;
28   beacon.domain = "localhost";
29   beacon.status = "ok";
30   beacon.chrome_error = net::OK;
31   beacon.server_ip = "127.0.0.1";
32   beacon.protocol = "HTTP";
33   beacon.http_response_code = 200;
34   beacon.elapsed = base::TimeDelta::FromMilliseconds(250);
35   beacon.start_time = time->NowTicks() - beacon.elapsed;
36   return beacon;
37 }
38 
39 class DomainReliabilityContextTest : public testing::Test {
40  protected:
DomainReliabilityContextTest()41   DomainReliabilityContextTest()
42       : dispatcher_(&time_),
43         params_(MakeTestSchedulerParams()),
44         uploader_(base::Bind(&DomainReliabilityContextTest::OnUploadRequest,
45                              base::Unretained(this))),
46         upload_reporter_string_("test-reporter"),
47         context_(&time_,
48                  params_,
49                  upload_reporter_string_,
50                  &dispatcher_,
51                  &uploader_,
52                  MakeTestConfig().Pass()),
53         upload_pending_(false) {}
54 
min_delay() const55   TimeDelta min_delay() const { return params_.minimum_upload_delay; }
max_delay() const56   TimeDelta max_delay() const { return params_.maximum_upload_delay; }
retry_interval() const57   TimeDelta retry_interval() const { return params_.upload_retry_interval; }
zero_delta() const58   TimeDelta zero_delta() const { return TimeDelta::FromMicroseconds(0); }
59 
upload_pending()60   bool upload_pending() { return upload_pending_; }
61 
upload_report()62   const std::string& upload_report() {
63     DCHECK(upload_pending_);
64     return upload_report_;
65   }
66 
upload_url()67   const GURL& upload_url() {
68     DCHECK(upload_pending_);
69     return upload_url_;
70   }
71 
CallUploadCallback(bool success)72   void CallUploadCallback(bool success) {
73     DCHECK(upload_pending_);
74     upload_callback_.Run(success);
75     upload_pending_ = false;
76   }
77 
CheckNoBeacons()78   bool CheckNoBeacons() {
79     BeaconVector beacons;
80     context_.GetQueuedBeaconsForTesting(&beacons);
81     return beacons.empty();
82   }
83 
CheckCounts(size_t index,unsigned expected_successful,unsigned expected_failed)84   bool CheckCounts(size_t index,
85                    unsigned expected_successful,
86                    unsigned expected_failed) {
87     unsigned successful, failed;
88     context_.GetRequestCountsForTesting(index, &successful, &failed);
89     return successful == expected_successful && failed == expected_failed;
90   }
91 
92   MockTime time_;
93   DomainReliabilityDispatcher dispatcher_;
94   DomainReliabilityScheduler::Params params_;
95   MockUploader uploader_;
96   std::string upload_reporter_string_;
97   DomainReliabilityContext context_;
98 
99  private:
OnUploadRequest(const std::string & report_json,const GURL & upload_url,const DomainReliabilityUploader::UploadCallback & callback)100   void OnUploadRequest(
101       const std::string& report_json,
102       const GURL& upload_url,
103       const DomainReliabilityUploader::UploadCallback& callback) {
104     DCHECK(!upload_pending_);
105     upload_report_ = report_json;
106     upload_url_ = upload_url;
107     upload_callback_ = callback;
108     upload_pending_ = true;
109   }
110 
111   bool upload_pending_;
112   std::string upload_report_;
113   GURL upload_url_;
114   DomainReliabilityUploader::UploadCallback upload_callback_;
115 };
116 
TEST_F(DomainReliabilityContextTest,Create)117 TEST_F(DomainReliabilityContextTest, Create) {
118   EXPECT_TRUE(CheckNoBeacons());
119   EXPECT_TRUE(CheckCounts(0, 0, 0));
120   EXPECT_TRUE(CheckCounts(1, 0, 0));
121 }
122 
TEST_F(DomainReliabilityContextTest,NoResource)123 TEST_F(DomainReliabilityContextTest, NoResource) {
124   GURL url("http://example/no_resource");
125   DomainReliabilityBeacon beacon = MakeBeacon(&time_);
126   context_.OnBeacon(url, beacon);
127 
128   EXPECT_TRUE(CheckNoBeacons());
129   EXPECT_TRUE(CheckCounts(0, 0, 0));
130   EXPECT_TRUE(CheckCounts(1, 0, 0));
131 }
132 
TEST_F(DomainReliabilityContextTest,NeverReport)133 TEST_F(DomainReliabilityContextTest, NeverReport) {
134   GURL url("http://example/never_report");
135   DomainReliabilityBeacon beacon = MakeBeacon(&time_);
136   context_.OnBeacon(url, beacon);
137 
138   EXPECT_TRUE(CheckNoBeacons());
139   EXPECT_TRUE(CheckCounts(0, 0, 0));
140   EXPECT_TRUE(CheckCounts(1, 1, 0));
141 }
142 
TEST_F(DomainReliabilityContextTest,AlwaysReport)143 TEST_F(DomainReliabilityContextTest, AlwaysReport) {
144   GURL url("http://example/always_report");
145   DomainReliabilityBeacon beacon = MakeBeacon(&time_);
146   context_.OnBeacon(url, beacon);
147 
148   BeaconVector beacons;
149   context_.GetQueuedBeaconsForTesting(&beacons);
150   EXPECT_EQ(1u, beacons.size());
151   EXPECT_TRUE(CheckCounts(0, 1, 0));
152   EXPECT_TRUE(CheckCounts(1, 0, 0));
153 }
154 
TEST_F(DomainReliabilityContextTest,ReportUpload)155 TEST_F(DomainReliabilityContextTest, ReportUpload) {
156   GURL url("http://example/always_report");
157   DomainReliabilityBeacon beacon = MakeBeacon(&time_);
158   context_.OnBeacon(url, beacon);
159 
160   BeaconVector beacons;
161   context_.GetQueuedBeaconsForTesting(&beacons);
162   EXPECT_EQ(1u, beacons.size());
163   EXPECT_TRUE(CheckCounts(0, 1, 0));
164   EXPECT_TRUE(CheckCounts(1, 0, 0));
165 
166   // N.B.: Assumes max_delay is 5 minutes.
167   const char* kExpectedReport = "{"
168       "\"config_version\":\"1\","
169       "\"entries\":[{\"domain\":\"localhost\","
170           "\"http_response_code\":200,\"protocol\":\"HTTP\","
171           "\"request_age_ms\":300250,\"request_elapsed_ms\":250,"
172           "\"resource\":\"always_report\",\"server_ip\":\"127.0.0.1\","
173           "\"status\":\"ok\"}],"
174       "\"reporter\":\"test-reporter\","
175       "\"resources\":[{\"failed_requests\":0,\"name\":\"always_report\","
176           "\"successful_requests\":1}]}";
177 
178   time_.Advance(max_delay());
179   EXPECT_TRUE(upload_pending());
180   EXPECT_EQ(kExpectedReport, upload_report());
181   EXPECT_EQ(GURL("https://exampleuploader/upload"), upload_url());
182   CallUploadCallback(true);
183 
184   EXPECT_TRUE(CheckNoBeacons());
185   EXPECT_TRUE(CheckCounts(0, 0, 0));
186   EXPECT_TRUE(CheckCounts(1, 0, 0));
187 }
188 
189 }  // namespace
190 }  // namespace domain_reliability
191