OLD | NEW |
(Empty) | |
| 1 // Copyright (c) 2012 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 "chrome/browser/net/http_pipelining_compatibility_client.h" |
| 6 |
| 7 #include <map> |
| 8 #include <string> |
| 9 #include <vector> |
| 10 |
| 11 #include "base/basictypes.h" |
| 12 #include "base/message_loop.h" |
| 13 #include "base/metrics/histogram.h" |
| 14 #include "base/stl_util.h" |
| 15 #include "base/stringprintf.h" |
| 16 #include "chrome/test/base/test_url_request_context_getter.h" |
| 17 #include "content/test/test_browser_thread.h" |
| 18 #include "net/base/net_errors.h" |
| 19 #include "net/base/test_completion_callback.h" |
| 20 #include "net/url_request/url_request_context_getter.h" |
| 21 #include "net/test/test_server.h" |
| 22 #include "testing/gtest/include/gtest/gtest.h" |
| 23 |
| 24 namespace chrome_browser_net { |
| 25 |
| 26 namespace { |
| 27 |
| 28 static const char* const kHistogramNames[] = { |
| 29 "NetConnectivity.Pipeline.0.NetworkError", |
| 30 "NetConnectivity.Pipeline.0.ResponseCode", |
| 31 "NetConnectivity.Pipeline.0.Status", |
| 32 "NetConnectivity.Pipeline.1.NetworkError", |
| 33 "NetConnectivity.Pipeline.1.ResponseCode", |
| 34 "NetConnectivity.Pipeline.1.Status", |
| 35 "NetConnectivity.Pipeline.2.NetworkError", |
| 36 "NetConnectivity.Pipeline.2.ResponseCode", |
| 37 "NetConnectivity.Pipeline.2.Status", |
| 38 }; |
| 39 |
| 40 enum HistogramField { |
| 41 FIELD_NETWORK_ERROR, |
| 42 FIELD_RESPONSE_CODE, |
| 43 FIELD_STATUS, |
| 44 }; |
| 45 |
| 46 class HttpPipeliningCompatibilityClientTest : public testing::Test { |
| 47 public: |
| 48 HttpPipeliningCompatibilityClientTest() |
| 49 : test_server_( |
| 50 net::TestServer::TYPE_HTTP, |
| 51 FilePath(FILE_PATH_LITERAL("chrome/test/data/http_pipelining"))), |
| 52 io_thread_(content::BrowserThread::IO, &message_loop_) { |
| 53 } |
| 54 |
| 55 protected: |
| 56 virtual void SetUp() OVERRIDE { |
| 57 ASSERT_TRUE(test_server_.Start()); |
| 58 context_ = new TestURLRequestContextGetter; |
| 59 context_->AddRef(); |
| 60 |
| 61 for (size_t i = 0; i < arraysize(kHistogramNames); ++i) { |
| 62 const char* name = kHistogramNames[i]; |
| 63 base::Histogram::SampleSet sample = GetHistogram(name); |
| 64 if (sample.TotalCount() > 0) { |
| 65 original_samples_[name] = sample; |
| 66 } |
| 67 } |
| 68 } |
| 69 |
| 70 virtual void TearDown() OVERRIDE { |
| 71 content::BrowserThread::ReleaseSoon(content::BrowserThread::IO, |
| 72 FROM_HERE, context_); |
| 73 message_loop_.RunAllPending(); |
| 74 } |
| 75 |
| 76 void RunTest( |
| 77 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests) { |
| 78 HttpPipeliningCompatibilityClient client; |
| 79 net::TestCompletionCallback callback; |
| 80 client.Start(test_server_.GetURL("").spec(), |
| 81 requests, callback.callback(), |
| 82 context_->GetURLRequestContext()); |
| 83 callback.WaitForResult(); |
| 84 |
| 85 for (size_t i = 0; i < arraysize(kHistogramNames); ++i) { |
| 86 const char* name = kHistogramNames[i]; |
| 87 base::Histogram::SampleSet sample = GetHistogram(name); |
| 88 if (ContainsKey(original_samples_, name)) { |
| 89 sample.Subtract(original_samples_[name]); |
| 90 } |
| 91 samples_[name] = sample; |
| 92 } |
| 93 } |
| 94 |
| 95 base::Histogram::SampleSet GetHistogramValue(int request_id, |
| 96 HistogramField field) { |
| 97 const char* field_str = ""; |
| 98 switch (field) { |
| 99 case FIELD_STATUS: |
| 100 field_str = "Status"; |
| 101 break; |
| 102 |
| 103 case FIELD_NETWORK_ERROR: |
| 104 field_str = "NetworkError"; |
| 105 break; |
| 106 |
| 107 case FIELD_RESPONSE_CODE: |
| 108 field_str = "ResponseCode"; |
| 109 break; |
| 110 |
| 111 default: |
| 112 NOTREACHED(); |
| 113 break; |
| 114 } |
| 115 |
| 116 std::string name = base::StringPrintf("NetConnectivity.Pipeline.%d.%s", |
| 117 request_id, field_str); |
| 118 return samples_[name]; |
| 119 } |
| 120 |
| 121 MessageLoopForIO message_loop_; |
| 122 net::TestServer test_server_; |
| 123 TestURLRequestContextGetter* context_; |
| 124 content::TestBrowserThread io_thread_; |
| 125 |
| 126 private: |
| 127 base::Histogram::SampleSet GetHistogram(const char* name) { |
| 128 base::Histogram::SampleSet sample; |
| 129 base::Histogram* histogram; |
| 130 if (ContainsKey(histograms_, name)) { |
| 131 histogram = histograms_[name]; |
| 132 histogram->SnapshotSample(&sample); |
| 133 } else if (base::StatisticsRecorder::FindHistogram(name, &histogram)) { |
| 134 histograms_[name] = histogram; |
| 135 histogram->SnapshotSample(&sample); |
| 136 } |
| 137 return sample; |
| 138 } |
| 139 |
| 140 static std::map<std::string, base::Histogram*> histograms_; |
| 141 std::map<std::string, base::Histogram::SampleSet> samples_; |
| 142 std::map<std::string, base::Histogram::SampleSet> original_samples_; |
| 143 base::StatisticsRecorder recorder_; |
| 144 }; |
| 145 |
| 146 // static |
| 147 std::map<std::string, base::Histogram*> |
| 148 HttpPipeliningCompatibilityClientTest::histograms_; |
| 149 |
| 150 TEST_F(HttpPipeliningCompatibilityClientTest, Success) { |
| 151 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 152 info.filename = "files/alphabet.txt"; |
| 153 info.expected_response = "abcdefghijklmnopqrstuvwxyz"; |
| 154 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 155 requests.push_back(info); |
| 156 |
| 157 RunTest(requests); |
| 158 |
| 159 base::Histogram::SampleSet status_sample = |
| 160 GetHistogramValue(0, FIELD_STATUS); |
| 161 EXPECT_EQ(1, status_sample.TotalCount()); |
| 162 EXPECT_EQ(1, status_sample.counts( |
| 163 HttpPipeliningCompatibilityClient::SUCCESS)); |
| 164 |
| 165 base::Histogram::SampleSet network_sample = |
| 166 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 167 EXPECT_EQ(0, network_sample.TotalCount()); |
| 168 |
| 169 base::Histogram::SampleSet response_sample = |
| 170 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 171 EXPECT_EQ(1, response_sample.TotalCount()); |
| 172 EXPECT_EQ(1, response_sample.counts(200)); |
| 173 } |
| 174 |
| 175 TEST_F(HttpPipeliningCompatibilityClientTest, TooSmall) { |
| 176 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 177 info.filename = "files/alphabet.txt"; |
| 178 info.expected_response = "abcdefghijklmnopqrstuvwxyz26"; |
| 179 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 180 requests.push_back(info); |
| 181 |
| 182 RunTest(requests); |
| 183 |
| 184 base::Histogram::SampleSet status_sample = |
| 185 GetHistogramValue(0, FIELD_STATUS); |
| 186 EXPECT_EQ(1, status_sample.TotalCount()); |
| 187 EXPECT_EQ(1, status_sample.counts( |
| 188 HttpPipeliningCompatibilityClient::TOO_SMALL)); |
| 189 |
| 190 base::Histogram::SampleSet network_sample = |
| 191 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 192 EXPECT_EQ(0, network_sample.TotalCount()); |
| 193 |
| 194 base::Histogram::SampleSet response_sample = |
| 195 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 196 EXPECT_EQ(1, response_sample.TotalCount()); |
| 197 EXPECT_EQ(1, response_sample.counts(200)); |
| 198 } |
| 199 |
| 200 TEST_F(HttpPipeliningCompatibilityClientTest, TooLarge) { |
| 201 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 202 info.filename = "files/alphabet.txt"; |
| 203 info.expected_response = "abc"; |
| 204 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 205 requests.push_back(info); |
| 206 |
| 207 RunTest(requests); |
| 208 |
| 209 base::Histogram::SampleSet status_sample = |
| 210 GetHistogramValue(0, FIELD_STATUS); |
| 211 EXPECT_EQ(1, status_sample.TotalCount()); |
| 212 EXPECT_EQ(1, status_sample.counts( |
| 213 HttpPipeliningCompatibilityClient::TOO_LARGE)); |
| 214 |
| 215 base::Histogram::SampleSet network_sample = |
| 216 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 217 EXPECT_EQ(0, network_sample.TotalCount()); |
| 218 |
| 219 base::Histogram::SampleSet response_sample = |
| 220 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 221 EXPECT_EQ(1, response_sample.TotalCount()); |
| 222 EXPECT_EQ(1, response_sample.counts(200)); |
| 223 } |
| 224 |
| 225 TEST_F(HttpPipeliningCompatibilityClientTest, Mismatch) { |
| 226 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 227 info.filename = "files/alphabet.txt"; |
| 228 info.expected_response = "zyxwvutsrqponmlkjihgfedcba"; |
| 229 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 230 requests.push_back(info); |
| 231 |
| 232 RunTest(requests); |
| 233 |
| 234 base::Histogram::SampleSet status_sample = |
| 235 GetHistogramValue(0, FIELD_STATUS); |
| 236 EXPECT_EQ(1, status_sample.TotalCount()); |
| 237 EXPECT_EQ(1, status_sample.counts( |
| 238 HttpPipeliningCompatibilityClient::CONTENT_MISMATCH)); |
| 239 |
| 240 base::Histogram::SampleSet network_sample = |
| 241 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 242 EXPECT_EQ(0, network_sample.TotalCount()); |
| 243 |
| 244 base::Histogram::SampleSet response_sample = |
| 245 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 246 EXPECT_EQ(1, response_sample.TotalCount()); |
| 247 EXPECT_EQ(1, response_sample.counts(200)); |
| 248 } |
| 249 |
| 250 TEST_F(HttpPipeliningCompatibilityClientTest, Redirect) { |
| 251 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 252 info.filename = "server-redirect?http://foo.bar/asdf"; |
| 253 info.expected_response = "shouldn't matter"; |
| 254 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 255 requests.push_back(info); |
| 256 |
| 257 RunTest(requests); |
| 258 |
| 259 base::Histogram::SampleSet status_sample = |
| 260 GetHistogramValue(0, FIELD_STATUS); |
| 261 EXPECT_EQ(1, status_sample.TotalCount()); |
| 262 EXPECT_EQ(1, status_sample.counts( |
| 263 HttpPipeliningCompatibilityClient::REDIRECTED)); |
| 264 |
| 265 base::Histogram::SampleSet network_sample = |
| 266 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 267 EXPECT_EQ(0, network_sample.TotalCount()); |
| 268 |
| 269 base::Histogram::SampleSet response_sample = |
| 270 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 271 EXPECT_EQ(0, response_sample.TotalCount()); |
| 272 } |
| 273 |
| 274 TEST_F(HttpPipeliningCompatibilityClientTest, AuthRequired) { |
| 275 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 276 info.filename = "auth-basic"; |
| 277 info.expected_response = "shouldn't matter"; |
| 278 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 279 requests.push_back(info); |
| 280 |
| 281 RunTest(requests); |
| 282 |
| 283 base::Histogram::SampleSet status_sample = |
| 284 GetHistogramValue(0, FIELD_STATUS); |
| 285 EXPECT_EQ(1, status_sample.TotalCount()); |
| 286 EXPECT_EQ(1, status_sample.counts( |
| 287 HttpPipeliningCompatibilityClient::BAD_RESPONSE_CODE)); |
| 288 |
| 289 base::Histogram::SampleSet network_sample = |
| 290 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 291 EXPECT_EQ(0, network_sample.TotalCount()); |
| 292 |
| 293 base::Histogram::SampleSet response_sample = |
| 294 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 295 EXPECT_EQ(1, response_sample.TotalCount()); |
| 296 EXPECT_EQ(1, response_sample.counts(401)); |
| 297 } |
| 298 |
| 299 TEST_F(HttpPipeliningCompatibilityClientTest, NoContent) { |
| 300 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 301 info.filename = "nocontent"; |
| 302 info.expected_response = "shouldn't matter"; |
| 303 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 304 requests.push_back(info); |
| 305 |
| 306 RunTest(requests); |
| 307 |
| 308 base::Histogram::SampleSet status_sample = |
| 309 GetHistogramValue(0, FIELD_STATUS); |
| 310 EXPECT_EQ(1, status_sample.TotalCount()); |
| 311 EXPECT_EQ(1, status_sample.counts( |
| 312 HttpPipeliningCompatibilityClient::BAD_RESPONSE_CODE)); |
| 313 |
| 314 base::Histogram::SampleSet network_sample = |
| 315 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 316 EXPECT_EQ(0, network_sample.TotalCount()); |
| 317 |
| 318 base::Histogram::SampleSet response_sample = |
| 319 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 320 EXPECT_EQ(1, response_sample.TotalCount()); |
| 321 EXPECT_EQ(1, response_sample.counts(204)); |
| 322 } |
| 323 |
| 324 TEST_F(HttpPipeliningCompatibilityClientTest, CloseSocket) { |
| 325 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 326 info.filename = "close-socket"; |
| 327 info.expected_response = "shouldn't matter"; |
| 328 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 329 requests.push_back(info); |
| 330 |
| 331 RunTest(requests); |
| 332 |
| 333 base::Histogram::SampleSet status_sample = |
| 334 GetHistogramValue(0, FIELD_STATUS); |
| 335 EXPECT_EQ(1, status_sample.TotalCount()); |
| 336 EXPECT_EQ(1, status_sample.counts( |
| 337 HttpPipeliningCompatibilityClient::NETWORK_ERROR)); |
| 338 |
| 339 base::Histogram::SampleSet network_sample = |
| 340 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 341 EXPECT_EQ(1, network_sample.TotalCount()); |
| 342 EXPECT_EQ(1, network_sample.counts(-net::ERR_EMPTY_RESPONSE)); |
| 343 |
| 344 base::Histogram::SampleSet response_sample = |
| 345 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 346 EXPECT_EQ(0, response_sample.TotalCount()); |
| 347 } |
| 348 |
| 349 TEST_F(HttpPipeliningCompatibilityClientTest, OldHttpVersion) { |
| 350 HttpPipeliningCompatibilityClient::RequestInfo info; |
| 351 info.filename = "http-1.0"; |
| 352 info.expected_response = "abcdefghijklmnopqrstuvwxyz"; |
| 353 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 354 requests.push_back(info); |
| 355 |
| 356 RunTest(requests); |
| 357 |
| 358 base::Histogram::SampleSet status_sample = |
| 359 GetHistogramValue(0, FIELD_STATUS); |
| 360 EXPECT_EQ(1, status_sample.TotalCount()); |
| 361 EXPECT_EQ(1, status_sample.counts( |
| 362 HttpPipeliningCompatibilityClient::BAD_HTTP_VERSION)); |
| 363 |
| 364 base::Histogram::SampleSet network_sample = |
| 365 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 366 EXPECT_EQ(0, network_sample.TotalCount()); |
| 367 |
| 368 base::Histogram::SampleSet response_sample = |
| 369 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 370 EXPECT_EQ(1, response_sample.TotalCount()); |
| 371 EXPECT_EQ(1, response_sample.counts(200)); |
| 372 } |
| 373 |
| 374 TEST_F(HttpPipeliningCompatibilityClientTest, MultipleRequests) { |
| 375 std::vector<HttpPipeliningCompatibilityClient::RequestInfo> requests; |
| 376 |
| 377 HttpPipeliningCompatibilityClient::RequestInfo info1; |
| 378 info1.filename = "files/alphabet.txt"; |
| 379 info1.expected_response = "abcdefghijklmnopqrstuvwxyz"; |
| 380 requests.push_back(info1); |
| 381 |
| 382 HttpPipeliningCompatibilityClient::RequestInfo info2; |
| 383 info2.filename = "close-socket"; |
| 384 info2.expected_response = "shouldn't matter"; |
| 385 requests.push_back(info2); |
| 386 |
| 387 HttpPipeliningCompatibilityClient::RequestInfo info3; |
| 388 info3.filename = "auth-basic"; |
| 389 info3.expected_response = "shouldn't matter"; |
| 390 requests.push_back(info3); |
| 391 |
| 392 RunTest(requests); |
| 393 |
| 394 base::Histogram::SampleSet status_sample1 = |
| 395 GetHistogramValue(0, FIELD_STATUS); |
| 396 EXPECT_EQ(1, status_sample1.TotalCount()); |
| 397 EXPECT_EQ(1, status_sample1.counts( |
| 398 HttpPipeliningCompatibilityClient::SUCCESS)); |
| 399 |
| 400 base::Histogram::SampleSet network_sample1 = |
| 401 GetHistogramValue(0, FIELD_NETWORK_ERROR); |
| 402 EXPECT_EQ(0, network_sample1.TotalCount()); |
| 403 |
| 404 base::Histogram::SampleSet response_sample1 = |
| 405 GetHistogramValue(0, FIELD_RESPONSE_CODE); |
| 406 EXPECT_EQ(1, response_sample1.TotalCount()); |
| 407 EXPECT_EQ(1, response_sample1.counts(200)); |
| 408 |
| 409 base::Histogram::SampleSet status_sample2 = |
| 410 GetHistogramValue(1, FIELD_STATUS); |
| 411 EXPECT_EQ(1, status_sample2.TotalCount()); |
| 412 EXPECT_EQ(1, status_sample2.counts( |
| 413 HttpPipeliningCompatibilityClient::NETWORK_ERROR)); |
| 414 |
| 415 base::Histogram::SampleSet network_sample2 = |
| 416 GetHistogramValue(1, FIELD_NETWORK_ERROR); |
| 417 EXPECT_EQ(1, network_sample2.TotalCount()); |
| 418 EXPECT_EQ(1, network_sample2.counts(-net::ERR_EMPTY_RESPONSE)); |
| 419 |
| 420 base::Histogram::SampleSet response_sample2 = |
| 421 GetHistogramValue(1, FIELD_RESPONSE_CODE); |
| 422 EXPECT_EQ(0, response_sample2.TotalCount()); |
| 423 |
| 424 base::Histogram::SampleSet status_sample3 = |
| 425 GetHistogramValue(2, FIELD_STATUS); |
| 426 EXPECT_EQ(1, status_sample3.TotalCount()); |
| 427 EXPECT_EQ(1, status_sample3.counts( |
| 428 HttpPipeliningCompatibilityClient::BAD_RESPONSE_CODE)); |
| 429 |
| 430 base::Histogram::SampleSet network_sample3 = |
| 431 GetHistogramValue(2, FIELD_NETWORK_ERROR); |
| 432 EXPECT_EQ(0, network_sample3.TotalCount()); |
| 433 |
| 434 base::Histogram::SampleSet response_sample3 = |
| 435 GetHistogramValue(2, FIELD_RESPONSE_CODE); |
| 436 EXPECT_EQ(1, response_sample3.TotalCount()); |
| 437 EXPECT_EQ(1, response_sample3.counts(401)); |
| 438 } |
| 439 |
| 440 } // anonymous namespace |
| 441 |
| 442 } // namespace chrome_browser_net |
OLD | NEW |