Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(142)

Side by Side Diff: net/url_request/url_request_job_tracker_unittest.cc

Issue 3010037: Add the actual data being read to the OnBytesRead callback, take two.... (Closed) Base URL: http://src.chromium.org/svn/trunk/src/
Patch Set: '' Created 10 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « net/url_request/url_request_job_tracker.cc ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Property Changes:
Added: svn:eol-style
+ LF
OLDNEW
(Empty)
1 // Copyright (c) 2010 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 <string.h>
6 #include <algorithm>
7 #include <string>
8 #include <vector>
9 #include "base/message_loop.h"
10 #include "googleurl/src/gurl.h"
11 #include "net/base/filter.h"
12 #include "net/base/io_buffer.h"
13 #include "net/url_request/url_request.h"
14 #include "net/url_request/url_request_job.h"
15 #include "net/url_request/url_request_job_tracker.h"
16 #include "net/url_request/url_request_status.h"
17 #include "net/url_request/url_request_unittest.h"
18 #include "testing/gmock/include/gmock/gmock.h"
19 #include "testing/gtest/include/gtest/gtest.h"
20 #include "testing/platform_test.h"
21
22 using testing::Eq;
23 using testing::InSequence;
24 using testing::NotNull;
25 using testing::StrictMock;
26
27 namespace {
28
29 const char kBasic[] = "Hello\n";
30
31 // The above string "Hello\n", gzip compressed.
32 const unsigned char kCompressed[] = {
33 0x1f, 0x8b, 0x08, 0x08, 0x38, 0x18, 0x2e, 0x4c, 0x00, 0x03, 0x63,
34 0x6f, 0x6d, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x2e, 0x68,
35 0x74, 0x6d, 0x6c, 0x00, 0xf3, 0x48, 0xcd, 0xc9, 0xc9, 0xe7, 0x02,
36 0x00, 0x16, 0x35, 0x96, 0x31, 0x06, 0x00, 0x00, 0x00
37 };
38
39 bool GetResponseBody(const GURL& url, std::string* out_body) {
40 if (url.spec() == "test:basic") {
41 *out_body = kBasic;
42 } else if (url.spec() == "test:compressed") {
43 out_body->assign(reinterpret_cast<const char*>(kCompressed),
44 sizeof(kCompressed));
45 } else {
46 return false;
47 }
48
49 return true;
50 }
51
52 class MockJobObserver : public URLRequestJobTracker::JobObserver {
53 public:
54 MOCK_METHOD1(OnJobAdded, void(URLRequestJob* job));
55 MOCK_METHOD1(OnJobRemoved, void(URLRequestJob* job));
56 MOCK_METHOD2(OnJobDone, void(URLRequestJob* job,
57 const URLRequestStatus& status));
58 MOCK_METHOD3(OnJobRedirect, void(URLRequestJob* job,
59 const GURL& location,
60 int status_code));
61 MOCK_METHOD3(OnBytesRead, void(URLRequestJob* job,
62 const char* buf,
63 int byte_count));
64 };
65
66 // A URLRequestJob that returns static content for given URLs. We do
67 // not use URLRequestTestJob here because URLRequestTestJob fakes
68 // async operations by calling ReadRawData synchronously in an async
69 // callback. This test requires a URLRequestJob that returns false for
70 // async reads, in order to exercise the real async read codepath.
71 class URLRequestJobTrackerTestJob : public URLRequestJob {
72 public:
73 URLRequestJobTrackerTestJob(URLRequest* request, bool async_reads)
74 : URLRequestJob(request), async_reads_(async_reads) {}
75
76 void Start() {
77 ASSERT_TRUE(GetResponseBody(request_->url(), &response_data_));
78
79 // Start reading asynchronously so that all error reporting and data
80 // callbacks happen as they would for network requests.
81 MessageLoop::current()->PostTask(FROM_HERE, NewRunnableMethod(
82 this, &URLRequestJobTrackerTestJob::NotifyHeadersComplete));
83 }
84
85 bool ReadRawData(net::IOBuffer* buf, int buf_size,
86 int *bytes_read) {
87 const size_t bytes_to_read = std::min(
88 response_data_.size(), static_cast<size_t>(buf_size));
89
90 // Regardless of whether we're performing a sync or async read,
91 // copy the data into the caller's buffer now. That way we don't
92 // have to hold on to the buffers in the async case.
93 memcpy(buf->data(), response_data_.data(), bytes_to_read);
94 response_data_.erase(0, bytes_to_read);
95
96 if (async_reads_) {
97 SetStatus(URLRequestStatus(URLRequestStatus::IO_PENDING, 0));
98 MessageLoop::current()->PostTask(FROM_HERE, NewRunnableMethod(
99 this, &URLRequestJobTrackerTestJob::OnReadCompleted,
100 bytes_to_read));
101 } else {
102 SetStatus(URLRequestStatus());
103 *bytes_read = bytes_to_read;
104 }
105 return !async_reads_;
106 }
107
108 void OnReadCompleted(int status) {
109 if (status == 0) {
110 NotifyDone(URLRequestStatus());
111 } else if (status > 0) {
112 SetStatus(URLRequestStatus());
113 } else {
114 ASSERT_FALSE(true) << "Unexpected OnReadCompleted callback.";
115 }
116
117 NotifyReadComplete(status);
118 }
119
120 bool GetContentEncodings(
121 std::vector<Filter::FilterType>* encoding_types) {
122 if (request_->url().spec() == "test:basic") {
123 return false;
124 } else if (request_->url().spec() == "test:compressed") {
125 encoding_types->push_back(Filter::FILTER_TYPE_GZIP);
126 return true;
127 } else {
128 return URLRequestJob::GetContentEncodings(encoding_types);
129 }
130 }
131
132 // The data to send, will be set in Start().
133 std::string response_data_;
134
135 // Should reads be synchronous or asynchronous?
136 const bool async_reads_;
137 };
138
139 // Google Mock Matcher to check two URLRequestStatus instances for
140 // equality.
141 MATCHER_P(StatusEq, other, "") {
142 return (arg.status() == other.status() &&
143 arg.os_error() == other.os_error());
144 }
145
146 // Google Mock Matcher to check that two blocks of memory are equal.
147 MATCHER_P2(MemEq, other, len, "") {
148 return memcmp(arg, other, len) == 0;
149 }
150
151 class URLRequestJobTrackerTest : public PlatformTest {
152 protected:
153 static void SetUpTestCase() {
154 URLRequest::RegisterProtocolFactory("test", &Factory);
155 }
156
157 virtual void SetUp() {
158 g_async_reads = true;
159 }
160
161 void AssertJobTrackerCallbacks(const char* url) {
162 InSequence seq;
163 testing::StrictMock<MockJobObserver> observer;
164
165 const GURL gurl(url);
166 std::string body;
167 ASSERT_TRUE(GetResponseBody(gurl, &body));
168
169 // We expect to receive one call for each method on the JobObserver,
170 // in the following order:
171 EXPECT_CALL(observer, OnJobAdded(NotNull()));
172 EXPECT_CALL(observer, OnBytesRead(NotNull(),
173 MemEq(body.data(), body.size()),
174 Eq(static_cast<int>(body.size()))));
175 EXPECT_CALL(observer, OnJobDone(NotNull(), StatusEq(URLRequestStatus())));
176 EXPECT_CALL(observer, OnJobRemoved(NotNull()));
177
178 // Attach our observer and perform the resource fetch.
179 g_url_request_job_tracker.AddObserver(&observer);
180 Fetch(gurl);
181 g_url_request_job_tracker.RemoveObserver(&observer);
182 }
183
184 void Fetch(const GURL& url) {
185 TestDelegate d;
186 {
187 URLRequest request(url, &d);
188 request.Start();
189 MessageLoop::current()->RunAllPending();
190 }
191
192 // A few sanity checks to make sure that the delegate also
193 // receives the expected callbacks.
194 EXPECT_EQ(1, d.response_started_count());
195 EXPECT_FALSE(d.received_data_before_response());
196 EXPECT_STREQ(kBasic, d.data_received().c_str());
197 }
198
199 static URLRequest::ProtocolFactory Factory;
200 static bool g_async_reads;
201 };
202
203 // static
204 URLRequestJob* URLRequestJobTrackerTest::Factory(URLRequest* request,
205 const std::string& scheme) {
206 return new URLRequestJobTrackerTestJob(request, g_async_reads);
207 }
208
209 // static
210 bool URLRequestJobTrackerTest::g_async_reads = true;
211
212 TEST_F(URLRequestJobTrackerTest, BasicAsync) {
213 g_async_reads = true;
214 AssertJobTrackerCallbacks("test:basic");
215 }
216
217 TEST_F(URLRequestJobTrackerTest, BasicSync) {
218 g_async_reads = false;
219 AssertJobTrackerCallbacks("test:basic");
220 }
221
222 TEST_F(URLRequestJobTrackerTest, CompressedAsync) {
223 g_async_reads = true;
224 AssertJobTrackerCallbacks("test:compressed");
225 }
226
227 TEST_F(URLRequestJobTrackerTest, CompressedSync) {
228 g_async_reads = false;
229 AssertJobTrackerCallbacks("test:compressed");
230 }
231
232 } // namespace
OLDNEW
« no previous file with comments | « net/url_request/url_request_job_tracker.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698