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

Side by Side Diff: chrome/browser/policy/device_management_service_unittest.cc

Issue 12189011: Split up chrome/browser/policy subdirectory (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Rebase. Created 7 years, 10 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
OLDNEW
(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 <ostream>
6 #include <vector>
7
8 #include "base/bind.h"
9 #include "base/message_loop.h"
10 #include "base/string_split.h"
11 #include "chrome/browser/policy/cloud_policy_constants.h"
12 #include "chrome/browser/policy/device_management_service.h"
13 #include "chrome/test/base/testing_browser_process.h"
14 #include "content/public/test/test_browser_thread.h"
15 #include "net/base/escape.h"
16 #include "net/base/load_flags.h"
17 #include "net/base/net_errors.h"
18 #include "net/http/http_response_headers.h"
19 #include "net/url_request/test_url_fetcher_factory.h"
20 #include "net/url_request/url_request_status.h"
21 #include "net/url_request/url_request_test_util.h"
22 #include "testing/gmock/include/gmock/gmock.h"
23 #include "testing/gtest/include/gtest/gtest.h"
24
25 using content::BrowserThread;
26 using testing::_;
27
28 namespace em = enterprise_management;
29
30 namespace policy {
31
32 const char kServiceUrl[] = "https://example.com/management_service";
33
34 // Encoded empty response messages for testing the error code paths.
35 const char kResponseEmpty[] = "\x08\x00";
36
37 #define PROTO_STRING(name) (std::string(name, arraysize(name) - 1))
38
39 // Some helper constants.
40 const char kGaiaAuthToken[] = "gaia-auth-token";
41 const char kOAuthToken[] = "oauth-token";
42 const char kDMToken[] = "device-management-token";
43 const char kClientID[] = "device-id";
44
45 // Unit tests for the device management policy service. The tests are run
46 // against a TestURLFetcherFactory that is used to short-circuit the request
47 // without calling into the actual network stack.
48 class DeviceManagementServiceTestBase : public testing::Test {
49 protected:
50 DeviceManagementServiceTestBase()
51 : ui_thread_(BrowserThread::UI, &loop_),
52 io_thread_(BrowserThread::IO, &loop_) {
53 ResetService();
54 InitializeService();
55 }
56
57 virtual void TearDown() {
58 service_.reset();
59 loop_.RunUntilIdle();
60 }
61
62 void ResetService() {
63 service_.reset(new DeviceManagementService(kServiceUrl));
64 }
65
66 void InitializeService() {
67 service_->ScheduleInitialization(0);
68 loop_.RunUntilIdle();
69 }
70
71 DeviceManagementRequestJob* StartRegistrationJob() {
72 DeviceManagementRequestJob* job =
73 service_->CreateJob(DeviceManagementRequestJob::TYPE_REGISTRATION);
74 job->SetGaiaToken(kGaiaAuthToken);
75 job->SetOAuthToken(kOAuthToken);
76 job->SetClientID(kClientID);
77 job->GetRequest()->mutable_register_request();
78 job->Start(base::Bind(&DeviceManagementServiceTestBase::OnJobDone,
79 base::Unretained(this)));
80 return job;
81 }
82
83 DeviceManagementRequestJob* StartUnregistrationJob() {
84 DeviceManagementRequestJob* job =
85 service_->CreateJob(DeviceManagementRequestJob::TYPE_UNREGISTRATION);
86 job->SetDMToken(kDMToken);
87 job->SetClientID(kClientID);
88 job->GetRequest()->mutable_unregister_request();
89 job->Start(base::Bind(&DeviceManagementServiceTestBase::OnJobDone,
90 base::Unretained(this)));
91 return job;
92 }
93
94 DeviceManagementRequestJob* StartPolicyFetchJob() {
95 DeviceManagementRequestJob* job =
96 service_->CreateJob(DeviceManagementRequestJob::TYPE_POLICY_FETCH);
97 job->SetGaiaToken(kGaiaAuthToken);
98 job->SetOAuthToken(kOAuthToken);
99 job->SetClientID(kClientID);
100 em::PolicyFetchRequest* fetch_request =
101 job->GetRequest()->mutable_policy_request()->add_request();
102 fetch_request->set_policy_type(dm_protocol::kChromeUserPolicyType);
103 job->Start(base::Bind(&DeviceManagementServiceTestBase::OnJobDone,
104 base::Unretained(this)));
105 return job;
106 }
107
108 DeviceManagementRequestJob* StartAutoEnrollmentJob() {
109 DeviceManagementRequestJob* job =
110 service_->CreateJob(DeviceManagementRequestJob::TYPE_AUTO_ENROLLMENT);
111 job->SetClientID(kClientID);
112 em::DeviceAutoEnrollmentRequest* request =
113 job->GetRequest()->mutable_auto_enrollment_request();
114 request->set_modulus(1);
115 request->set_remainder(0);
116 job->Start(base::Bind(&DeviceManagementServiceTestBase::OnJobDone,
117 base::Unretained(this)));
118 return job;
119 }
120
121 void SendResponse(net::TestURLFetcher* fetcher,
122 const net::URLRequestStatus request_status,
123 int http_status,
124 const std::string& response) {
125 fetcher->set_url(GURL(kServiceUrl));
126 fetcher->set_status(request_status);
127 fetcher->set_response_code(http_status);
128 fetcher->SetResponseString(response);
129 fetcher->delegate()->OnURLFetchComplete(fetcher);
130 }
131
132 MOCK_METHOD2(OnJobDone, void(DeviceManagementStatus,
133 const em::DeviceManagementResponse&));
134
135 net::TestURLFetcherFactory factory_;
136 scoped_ptr<DeviceManagementService> service_;
137
138 private:
139 MessageLoopForUI loop_;
140 content::TestBrowserThread ui_thread_;
141 content::TestBrowserThread io_thread_;
142 };
143
144 struct FailedRequestParams {
145 FailedRequestParams(DeviceManagementStatus expected_status,
146 net::URLRequestStatus::Status request_status,
147 int http_status,
148 const std::string& response)
149 : expected_status_(expected_status),
150 request_status_(request_status, 0),
151 http_status_(http_status),
152 response_(response) {}
153
154 DeviceManagementStatus expected_status_;
155 net::URLRequestStatus request_status_;
156 int http_status_;
157 std::string response_;
158 };
159
160 void PrintTo(const FailedRequestParams& params, std::ostream* os) {
161 *os << "FailedRequestParams " << params.expected_status_
162 << " " << params.request_status_.status()
163 << " " << params.http_status_;
164 }
165
166 // A parameterized test case for erroneous response situations, they're mostly
167 // the same for all kinds of requests.
168 class DeviceManagementServiceFailedRequestTest
169 : public DeviceManagementServiceTestBase,
170 public testing::WithParamInterface<FailedRequestParams> {
171 };
172
173 TEST_P(DeviceManagementServiceFailedRequestTest, RegisterRequest) {
174 EXPECT_CALL(*this, OnJobDone(GetParam().expected_status_, _));
175 scoped_ptr<DeviceManagementRequestJob> request_job(StartRegistrationJob());
176 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
177 ASSERT_TRUE(fetcher);
178
179 SendResponse(fetcher, GetParam().request_status_, GetParam().http_status_,
180 GetParam().response_);
181 }
182
183 TEST_P(DeviceManagementServiceFailedRequestTest, UnregisterRequest) {
184 EXPECT_CALL(*this, OnJobDone(GetParam().expected_status_, _));
185 scoped_ptr<DeviceManagementRequestJob> request_job(StartUnregistrationJob());
186 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
187 ASSERT_TRUE(fetcher);
188
189 SendResponse(fetcher, GetParam().request_status_, GetParam().http_status_,
190 GetParam().response_);
191 }
192
193 TEST_P(DeviceManagementServiceFailedRequestTest, PolicyRequest) {
194 EXPECT_CALL(*this, OnJobDone(GetParam().expected_status_, _));
195 scoped_ptr<DeviceManagementRequestJob> request_job(StartPolicyFetchJob());
196 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
197 ASSERT_TRUE(fetcher);
198
199 SendResponse(fetcher, GetParam().request_status_, GetParam().http_status_,
200 GetParam().response_);
201 }
202
203 TEST_P(DeviceManagementServiceFailedRequestTest, AutoEnrollmentRequest) {
204 EXPECT_CALL(*this, OnJobDone(GetParam().expected_status_, _));
205 scoped_ptr<DeviceManagementRequestJob> request_job(StartAutoEnrollmentJob());
206 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
207 ASSERT_TRUE(fetcher);
208
209 SendResponse(fetcher, GetParam().request_status_, GetParam().http_status_,
210 GetParam().response_);
211 }
212
213 INSTANTIATE_TEST_CASE_P(
214 DeviceManagementServiceFailedRequestTestInstance,
215 DeviceManagementServiceFailedRequestTest,
216 testing::Values(
217 FailedRequestParams(
218 DM_STATUS_REQUEST_FAILED,
219 net::URLRequestStatus::FAILED,
220 200,
221 PROTO_STRING(kResponseEmpty)),
222 FailedRequestParams(
223 DM_STATUS_HTTP_STATUS_ERROR,
224 net::URLRequestStatus::SUCCESS,
225 666,
226 PROTO_STRING(kResponseEmpty)),
227 FailedRequestParams(
228 DM_STATUS_RESPONSE_DECODING_ERROR,
229 net::URLRequestStatus::SUCCESS,
230 200,
231 PROTO_STRING("Not a protobuf.")),
232 FailedRequestParams(
233 DM_STATUS_SERVICE_MANAGEMENT_NOT_SUPPORTED,
234 net::URLRequestStatus::SUCCESS,
235 403,
236 PROTO_STRING(kResponseEmpty)),
237 FailedRequestParams(
238 DM_STATUS_SERVICE_INVALID_SERIAL_NUMBER,
239 net::URLRequestStatus::SUCCESS,
240 405,
241 PROTO_STRING(kResponseEmpty)),
242 FailedRequestParams(
243 DM_STATUS_SERVICE_DEVICE_ID_CONFLICT,
244 net::URLRequestStatus::SUCCESS,
245 409,
246 PROTO_STRING(kResponseEmpty)),
247 FailedRequestParams(
248 DM_STATUS_SERVICE_DEVICE_NOT_FOUND,
249 net::URLRequestStatus::SUCCESS,
250 410,
251 PROTO_STRING(kResponseEmpty)),
252 FailedRequestParams(
253 DM_STATUS_SERVICE_MANAGEMENT_TOKEN_INVALID,
254 net::URLRequestStatus::SUCCESS,
255 401,
256 PROTO_STRING(kResponseEmpty)),
257 FailedRequestParams(
258 DM_STATUS_REQUEST_INVALID,
259 net::URLRequestStatus::SUCCESS,
260 400,
261 PROTO_STRING(kResponseEmpty)),
262 FailedRequestParams(
263 DM_STATUS_TEMPORARY_UNAVAILABLE,
264 net::URLRequestStatus::SUCCESS,
265 404,
266 PROTO_STRING(kResponseEmpty)),
267 FailedRequestParams(
268 DM_STATUS_SERVICE_ACTIVATION_PENDING,
269 net::URLRequestStatus::SUCCESS,
270 412,
271 PROTO_STRING(kResponseEmpty)),
272 FailedRequestParams(
273 DM_STATUS_SERVICE_MISSING_LICENSES,
274 net::URLRequestStatus::SUCCESS,
275 402,
276 PROTO_STRING(kResponseEmpty))));
277
278 // Simple query parameter parser for testing.
279 class QueryParams {
280 public:
281 explicit QueryParams(const std::string& query) {
282 base::SplitStringIntoKeyValuePairs(query, '=', '&', &params_);
283 }
284
285 bool Check(const std::string& name, const std::string& expected_value) {
286 bool found = false;
287 for (ParamMap::const_iterator i(params_.begin()); i != params_.end(); ++i) {
288 std::string unescaped_name(net::UnescapeURLComponent(
289 i->first,
290 net::UnescapeRule::NORMAL |
291 net::UnescapeRule::SPACES |
292 net::UnescapeRule::URL_SPECIAL_CHARS |
293 net::UnescapeRule::CONTROL_CHARS |
294 net::UnescapeRule::REPLACE_PLUS_WITH_SPACE));
295 if (unescaped_name == name) {
296 if (found)
297 return false;
298 found = true;
299 std::string unescaped_value(net::UnescapeURLComponent(
300 i->second,
301 net::UnescapeRule::NORMAL |
302 net::UnescapeRule::SPACES |
303 net::UnescapeRule::URL_SPECIAL_CHARS |
304 net::UnescapeRule::CONTROL_CHARS |
305 net::UnescapeRule::REPLACE_PLUS_WITH_SPACE));
306 if (unescaped_value != expected_value)
307 return false;
308 }
309 }
310 return found;
311 }
312
313 private:
314 typedef std::vector<std::pair<std::string, std::string> > ParamMap;
315 ParamMap params_;
316 };
317
318 class DeviceManagementServiceTest
319 : public DeviceManagementServiceTestBase {
320 protected:
321 void CheckURLAndQueryParams(const GURL& request_url,
322 const std::string& request_type,
323 const std::string& device_id) {
324 const GURL service_url(kServiceUrl);
325 EXPECT_EQ(service_url.scheme(), request_url.scheme());
326 EXPECT_EQ(service_url.host(), request_url.host());
327 EXPECT_EQ(service_url.port(), request_url.port());
328 EXPECT_EQ(service_url.path(), request_url.path());
329
330 QueryParams query_params(request_url.query());
331 EXPECT_TRUE(query_params.Check(dm_protocol::kParamRequest, request_type));
332 EXPECT_TRUE(query_params.Check(dm_protocol::kParamDeviceID, device_id));
333 EXPECT_TRUE(query_params.Check(dm_protocol::kParamDeviceType,
334 dm_protocol::kValueDeviceType));
335 EXPECT_TRUE(query_params.Check(dm_protocol::kParamAppType,
336 dm_protocol::kValueAppType));
337 }
338 };
339
340 MATCHER_P(MessageEquals, reference, "") {
341 std::string reference_data;
342 std::string arg_data;
343 return arg.SerializeToString(&arg_data) &&
344 reference.SerializeToString(&reference_data) &&
345 arg_data == reference_data;
346 }
347
348 TEST_F(DeviceManagementServiceTest, RegisterRequest) {
349 em::DeviceManagementResponse expected_response;
350 expected_response.mutable_register_response()->
351 set_device_management_token(kDMToken);
352 EXPECT_CALL(*this, OnJobDone(DM_STATUS_SUCCESS,
353 MessageEquals(expected_response)));
354 scoped_ptr<DeviceManagementRequestJob> request_job(StartRegistrationJob());
355 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
356 ASSERT_TRUE(fetcher);
357
358 CheckURLAndQueryParams(fetcher->GetOriginalURL(),
359 dm_protocol::kValueRequestRegister,
360 kClientID);
361
362 std::string expected_data;
363 ASSERT_TRUE(request_job->GetRequest()->SerializeToString(&expected_data));
364 EXPECT_EQ(expected_data, fetcher->upload_data());
365
366 // Generate the response.
367 std::string response_data;
368 ASSERT_TRUE(expected_response.SerializeToString(&response_data));
369 net::URLRequestStatus status(net::URLRequestStatus::SUCCESS, 0);
370 SendResponse(fetcher, status, 200, response_data);
371 }
372
373 TEST_F(DeviceManagementServiceTest, UnregisterRequest) {
374 em::DeviceManagementResponse expected_response;
375 expected_response.mutable_unregister_response();
376 EXPECT_CALL(*this, OnJobDone(DM_STATUS_SUCCESS,
377 MessageEquals(expected_response)));
378 scoped_ptr<DeviceManagementRequestJob> request_job(StartUnregistrationJob());
379 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
380 ASSERT_TRUE(fetcher);
381
382 // Check the data the fetcher received.
383 const GURL& request_url(fetcher->GetOriginalURL());
384 const GURL service_url(kServiceUrl);
385 EXPECT_EQ(service_url.scheme(), request_url.scheme());
386 EXPECT_EQ(service_url.host(), request_url.host());
387 EXPECT_EQ(service_url.port(), request_url.port());
388 EXPECT_EQ(service_url.path(), request_url.path());
389
390 CheckURLAndQueryParams(fetcher->GetOriginalURL(),
391 dm_protocol::kValueRequestUnregister,
392 kClientID);
393
394 std::string expected_data;
395 ASSERT_TRUE(request_job->GetRequest()->SerializeToString(&expected_data));
396 EXPECT_EQ(expected_data, fetcher->upload_data());
397
398 // Generate the response.
399 std::string response_data;
400 ASSERT_TRUE(expected_response.SerializeToString(&response_data));
401 net::URLRequestStatus status(net::URLRequestStatus::SUCCESS, 0);
402 SendResponse(fetcher, status, 200, response_data);
403 }
404
405 TEST_F(DeviceManagementServiceTest, CancelRegisterRequest) {
406 EXPECT_CALL(*this, OnJobDone(_, _)).Times(0);
407 scoped_ptr<DeviceManagementRequestJob> request_job(StartRegistrationJob());
408 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
409 ASSERT_TRUE(fetcher);
410
411 // There shouldn't be any callbacks.
412 request_job.reset();
413 }
414
415 TEST_F(DeviceManagementServiceTest, CancelUnregisterRequest) {
416 EXPECT_CALL(*this, OnJobDone(_, _)).Times(0);
417 scoped_ptr<DeviceManagementRequestJob> request_job(StartUnregistrationJob());
418 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
419 ASSERT_TRUE(fetcher);
420
421 // There shouldn't be any callbacks.
422 request_job.reset();
423 }
424
425 TEST_F(DeviceManagementServiceTest, CancelPolicyRequest) {
426 EXPECT_CALL(*this, OnJobDone(_, _)).Times(0);
427 scoped_ptr<DeviceManagementRequestJob> request_job(StartPolicyFetchJob());
428 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
429 ASSERT_TRUE(fetcher);
430
431 // There shouldn't be any callbacks.
432 request_job.reset();
433 }
434
435 TEST_F(DeviceManagementServiceTest, JobQueueing) {
436 // Start with a non-initialized service.
437 ResetService();
438
439 em::DeviceManagementResponse expected_response;
440 expected_response.mutable_register_response()->
441 set_device_management_token(kDMToken);
442 EXPECT_CALL(*this, OnJobDone(DM_STATUS_SUCCESS,
443 MessageEquals(expected_response)));
444
445 // Make a request. We should not see any fetchers being created.
446 scoped_ptr<DeviceManagementRequestJob> request_job(StartRegistrationJob());
447 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
448 ASSERT_FALSE(fetcher);
449
450 // Now initialize the service. That should start the job.
451 InitializeService();
452 fetcher = factory_.GetFetcherByID(0);
453 ASSERT_TRUE(fetcher);
454 factory_.RemoveFetcherFromMap(0);
455
456 // Check that the request is processed as expected.
457 std::string response_data;
458 ASSERT_TRUE(expected_response.SerializeToString(&response_data));
459 net::URLRequestStatus status(net::URLRequestStatus::SUCCESS, 0);
460 SendResponse(fetcher, status, 200, response_data);
461 }
462
463 TEST_F(DeviceManagementServiceTest, CancelRequestAfterShutdown) {
464 EXPECT_CALL(*this, OnJobDone(_, _)).Times(0);
465 scoped_ptr<DeviceManagementRequestJob> request_job(StartPolicyFetchJob());
466 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
467 ASSERT_TRUE(fetcher);
468
469 // Shutdown the service and cancel the job afterwards.
470 service_->Shutdown();
471 request_job.reset();
472 }
473
474 ACTION_P(ResetPointer, pointer) {
475 pointer->reset();
476 }
477
478 TEST_F(DeviceManagementServiceTest, CancelDuringCallback) {
479 // Make a request.
480 scoped_ptr<DeviceManagementRequestJob> request_job(StartRegistrationJob());
481 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
482 ASSERT_TRUE(fetcher);
483
484 EXPECT_CALL(*this, OnJobDone(_, _))
485 .WillOnce(ResetPointer(&request_job));
486
487 // Generate a callback.
488 net::URLRequestStatus status(net::URLRequestStatus::SUCCESS, 0);
489 SendResponse(fetcher, status, 500, "");
490
491 // Job should have been reset.
492 EXPECT_FALSE(request_job.get());
493 }
494
495 TEST_F(DeviceManagementServiceTest, RetryOnProxyError) {
496 // Make a request.
497 EXPECT_CALL(*this, OnJobDone(_, _)).Times(0);
498
499 scoped_ptr<DeviceManagementRequestJob> request_job(StartRegistrationJob());
500 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
501 ASSERT_TRUE(fetcher);
502 EXPECT_TRUE((fetcher->GetLoadFlags() & net::LOAD_BYPASS_PROXY) == 0);
503 const GURL original_url(fetcher->GetOriginalURL());
504 const std::string upload_data(fetcher->upload_data());
505
506 // Generate a callback with a proxy failure.
507 net::URLRequestStatus status(net::URLRequestStatus::FAILED,
508 net::ERR_PROXY_CONNECTION_FAILED);
509 SendResponse(fetcher, status, 200, "");
510
511 // Verify that a new URLFetcher was started that bypasses the proxy.
512 fetcher = factory_.GetFetcherByID(0);
513 ASSERT_TRUE(fetcher);
514 EXPECT_TRUE(fetcher->GetLoadFlags() & net::LOAD_BYPASS_PROXY);
515 EXPECT_EQ(original_url, fetcher->GetOriginalURL());
516 EXPECT_EQ(upload_data, fetcher->upload_data());
517 }
518
519 TEST_F(DeviceManagementServiceTest, RetryOnBadResponseFromProxy) {
520 // Make a request.
521 EXPECT_CALL(*this, OnJobDone(_, _)).Times(0);
522
523 scoped_ptr<DeviceManagementRequestJob> request_job(StartRegistrationJob());
524 net::TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
525 ASSERT_TRUE(fetcher);
526 EXPECT_TRUE((fetcher->GetLoadFlags() & net::LOAD_BYPASS_PROXY) == 0);
527 const GURL original_url(fetcher->GetOriginalURL());
528 const std::string upload_data(fetcher->upload_data());
529 fetcher->set_was_fetched_via_proxy(true);
530 scoped_refptr<net::HttpResponseHeaders> headers;
531 headers = new net::HttpResponseHeaders(
532 "HTTP/1.1 200 OK\0Content-type: bad/type\0\0");
533 fetcher->set_response_headers(headers);
534
535 // Generate a callback with a valid http response, that was generated by
536 // a bad/wrong proxy.
537 net::URLRequestStatus status;
538 SendResponse(fetcher, status, 200, "");
539
540 // Verify that a new URLFetcher was started that bypasses the proxy.
541 fetcher = factory_.GetFetcherByID(0);
542 ASSERT_TRUE(fetcher);
543 EXPECT_TRUE((fetcher->GetLoadFlags() & net::LOAD_BYPASS_PROXY) != 0);
544 EXPECT_EQ(original_url, fetcher->GetOriginalURL());
545 EXPECT_EQ(upload_data, fetcher->upload_data());
546 }
547
548 } // namespace policy
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698