d6e3655d98249b051830694dc77edee53bccb5ee
[platform/framework/web/crosswalk.git] / src / components / policy / core / common / cloud / cloud_policy_client_unittest.cc
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 "components/policy/core/common/cloud/cloud_policy_client.h"
6
7 #include <map>
8 #include <set>
9
10 #include "base/bind.h"
11 #include "base/compiler_specific.h"
12 #include "base/memory/ref_counted.h"
13 #include "base/memory/scoped_ptr.h"
14 #include "base/message_loop/message_loop.h"
15 #include "components/policy/core/common/cloud/mock_cloud_policy_client.h"
16 #include "components/policy/core/common/cloud/mock_device_management_service.h"
17 #include "net/url_request/url_request_context_getter.h"
18 #include "net/url_request/url_request_test_util.h"
19 #include "policy/proto/device_management_backend.pb.h"
20 #include "testing/gmock/include/gmock/gmock.h"
21 #include "testing/gtest/include/gtest/gtest.h"
22
23 using testing::Mock;
24 using testing::Return;
25 using testing::SaveArg;
26 using testing::StrictMock;
27 using testing::_;
28
29 namespace em = enterprise_management;
30
31 namespace policy {
32
33 namespace {
34
35 const char kClientID[] = "fake-client-id";
36 const char kMachineID[] = "fake-machine-id";
37 const char kMachineModel[] = "fake-machine-model";
38 const char kOAuthToken[] = "fake-oauth-token";
39 const char kDMToken[] = "fake-dm-token";
40 const char kDeviceCertificate[] = "fake-device-certificate";
41 const char kRequisition[] = "fake-requisition";
42 const char kStateKey[] = "fake-state-key";
43
44 class MockStatusProvider : public CloudPolicyClient::StatusProvider {
45  public:
46   MockStatusProvider() {}
47   virtual ~MockStatusProvider() {}
48
49   MOCK_METHOD1(GetDeviceStatus, bool(em::DeviceStatusReportRequest* status));
50   MOCK_METHOD1(GetSessionStatus, bool(em::SessionStatusReportRequest* status));
51   MOCK_METHOD0(OnSubmittedSuccessfully, void(void));
52
53  private:
54   DISALLOW_COPY_AND_ASSIGN(MockStatusProvider);
55 };
56
57 MATCHER_P(MatchProto, expected, "matches protobuf") {
58   return arg.SerializePartialAsString() == expected.SerializePartialAsString();
59 }
60
61 // A mock class to allow us to set expectations on upload certificate callbacks.
62 class MockUploadCertificateObserver {
63  public:
64   MockUploadCertificateObserver() {}
65   virtual ~MockUploadCertificateObserver() {}
66
67   MOCK_METHOD1(OnUploadComplete, void(bool));
68 };
69
70 }  // namespace
71
72 class CloudPolicyClientTest : public testing::Test {
73  protected:
74   CloudPolicyClientTest()
75       : client_id_(kClientID),
76         policy_ns_key_(dm_protocol::kChromeUserPolicyType, std::string()) {
77     em::DeviceRegisterRequest* register_request =
78         registration_request_.mutable_register_request();
79     register_request->set_type(em::DeviceRegisterRequest::USER);
80     register_request->set_machine_id(kMachineID);
81     register_request->set_machine_model(kMachineModel);
82     registration_response_.mutable_register_response()->
83         set_device_management_token(kDMToken);
84
85     em::PolicyFetchRequest* policy_fetch_request =
86         policy_request_.mutable_policy_request()->add_request();
87     policy_fetch_request->set_policy_type(dm_protocol::kChromeUserPolicyType);
88     policy_fetch_request->set_signature_type(em::PolicyFetchRequest::SHA1_RSA);
89     policy_fetch_request->set_verification_key_hash(kPolicyVerificationKeyHash);
90     policy_response_.mutable_policy_response()->add_response()->set_policy_data(
91         CreatePolicyData("fake-policy-data"));
92
93     unregistration_request_.mutable_unregister_request();
94     unregistration_response_.mutable_unregister_response();
95     upload_certificate_request_.mutable_cert_upload_request()->
96         set_device_certificate(kDeviceCertificate);
97     upload_certificate_response_.mutable_cert_upload_response();
98   }
99
100   virtual void SetUp() OVERRIDE {
101     EXPECT_CALL(status_provider_, GetDeviceStatus(_))
102         .WillRepeatedly(Return(false));
103     EXPECT_CALL(status_provider_, GetSessionStatus(_))
104         .WillRepeatedly(Return(false));
105     CreateClient(USER_AFFILIATION_NONE);
106   }
107
108   virtual void TearDown() OVERRIDE {
109     client_->RemoveObserver(&observer_);
110   }
111
112   void Register() {
113     EXPECT_CALL(observer_, OnRegistrationStateChanged(_));
114     client_->SetupRegistration(kDMToken, client_id_);
115   }
116
117   void CreateClient(UserAffiliation user_affiliation) {
118     if (client_.get())
119       client_->RemoveObserver(&observer_);
120
121     request_context_ = new net::TestURLRequestContextGetter(
122         loop_.message_loop_proxy());
123     client_.reset(new CloudPolicyClient(kMachineID, kMachineModel,
124                                         kPolicyVerificationKeyHash,
125                                         user_affiliation, &status_provider_,
126                                         &service_,
127                                         request_context_));
128     client_->AddNamespaceToFetch(policy_ns_key_);
129     client_->AddObserver(&observer_);
130   }
131
132   void ExpectRegistration(const std::string& oauth_token) {
133     EXPECT_CALL(service_,
134                 CreateJob(DeviceManagementRequestJob::TYPE_REGISTRATION,
135                           request_context_))
136         .WillOnce(service_.SucceedJob(registration_response_));
137     EXPECT_CALL(service_, StartJob(dm_protocol::kValueRequestRegister,
138                                    "", oauth_token, "", "", _,
139                                    MatchProto(registration_request_)))
140         .WillOnce(SaveArg<5>(&client_id_));
141   }
142
143   void ExpectPolicyFetch(const std::string& dm_token,
144                          const std::string& user_affiliation) {
145     EXPECT_CALL(service_,
146                 CreateJob(DeviceManagementRequestJob::TYPE_POLICY_FETCH,
147                           request_context_))
148         .WillOnce(service_.SucceedJob(policy_response_));
149     EXPECT_CALL(service_, StartJob(dm_protocol::kValueRequestPolicy,
150                                    "", "", dm_token, user_affiliation,
151                                    client_id_,
152                                    MatchProto(policy_request_)));
153   }
154
155   void ExpectUnregistration(const std::string& dm_token) {
156     EXPECT_CALL(service_,
157                 CreateJob(DeviceManagementRequestJob::TYPE_UNREGISTRATION,
158                           request_context_))
159         .WillOnce(service_.SucceedJob(unregistration_response_));
160     EXPECT_CALL(service_, StartJob(dm_protocol::kValueRequestUnregister,
161                                    "", "", dm_token, "", client_id_,
162                                    MatchProto(unregistration_request_)));
163   }
164
165   void ExpectUploadCertificate() {
166     EXPECT_CALL(service_,
167                 CreateJob(DeviceManagementRequestJob::TYPE_UPLOAD_CERTIFICATE,
168                           request_context_))
169         .WillOnce(service_.SucceedJob(upload_certificate_response_));
170     EXPECT_CALL(service_, StartJob(dm_protocol::kValueRequestUploadCertificate,
171                                    "", "", kDMToken, "", client_id_,
172                                    MatchProto(upload_certificate_request_)));
173   }
174
175   void CheckPolicyResponse() {
176     ASSERT_TRUE(client_->GetPolicyFor(policy_ns_key_));
177     EXPECT_THAT(*client_->GetPolicyFor(policy_ns_key_),
178                 MatchProto(policy_response_.policy_response().response(0)));
179   }
180
181   std::string CreatePolicyData(const std::string& policy_value) {
182     em::PolicyData policy_data;
183     policy_data.set_policy_type(dm_protocol::kChromeUserPolicyType);
184     policy_data.set_policy_value(policy_value);
185     return policy_data.SerializeAsString();
186   }
187
188   // Request protobufs used as expectations for the client requests.
189   em::DeviceManagementRequest registration_request_;
190   em::DeviceManagementRequest policy_request_;
191   em::DeviceManagementRequest unregistration_request_;
192   em::DeviceManagementRequest upload_certificate_request_;
193
194   // Protobufs used in successful responses.
195   em::DeviceManagementResponse registration_response_;
196   em::DeviceManagementResponse policy_response_;
197   em::DeviceManagementResponse unregistration_response_;
198   em::DeviceManagementResponse upload_certificate_response_;
199
200   base::MessageLoop loop_;
201   std::string client_id_;
202   PolicyNamespaceKey policy_ns_key_;
203   MockDeviceManagementService service_;
204   StrictMock<MockStatusProvider> status_provider_;
205   StrictMock<MockCloudPolicyClientObserver> observer_;
206   StrictMock<MockUploadCertificateObserver> upload_certificate_observer_;
207   scoped_ptr<CloudPolicyClient> client_;
208   // Pointer to the client's request context.
209   scoped_refptr<net::URLRequestContextGetter> request_context_;
210 };
211
212 TEST_F(CloudPolicyClientTest, Init) {
213   EXPECT_CALL(service_, CreateJob(_, _)).Times(0);
214   EXPECT_FALSE(client_->is_registered());
215   EXPECT_FALSE(client_->GetPolicyFor(policy_ns_key_));
216   EXPECT_EQ(0, client_->fetched_invalidation_version());
217 }
218
219 TEST_F(CloudPolicyClientTest, SetupRegistrationAndPolicyFetch) {
220   EXPECT_CALL(service_, CreateJob(_, _)).Times(0);
221   EXPECT_CALL(observer_, OnRegistrationStateChanged(_));
222   client_->SetupRegistration(kDMToken, client_id_);
223   EXPECT_TRUE(client_->is_registered());
224   EXPECT_FALSE(client_->GetPolicyFor(policy_ns_key_));
225
226   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
227   EXPECT_CALL(observer_, OnPolicyFetched(_));
228   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
229   client_->FetchPolicy();
230   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
231   CheckPolicyResponse();
232 }
233
234 TEST_F(CloudPolicyClientTest, RegistrationAndPolicyFetch) {
235   ExpectRegistration(kOAuthToken);
236   EXPECT_CALL(observer_, OnRegistrationStateChanged(_));
237   client_->Register(em::DeviceRegisterRequest::USER, kOAuthToken, std::string(),
238                     false, std::string(), std::string());
239   EXPECT_TRUE(client_->is_registered());
240   EXPECT_FALSE(client_->GetPolicyFor(policy_ns_key_));
241   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
242
243   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
244   EXPECT_CALL(observer_, OnPolicyFetched(_));
245   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
246   client_->FetchPolicy();
247   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
248   CheckPolicyResponse();
249 }
250
251 TEST_F(CloudPolicyClientTest, RegistrationParameters) {
252   registration_request_.mutable_register_request()->set_reregister(true);
253   registration_request_.mutable_register_request()->set_auto_enrolled(true);
254   registration_request_.mutable_register_request()->set_requisition(
255       kRequisition);
256   registration_request_.mutable_register_request()->set_server_backed_state_key(
257       kStateKey);
258   ExpectRegistration(kOAuthToken);
259   EXPECT_CALL(observer_, OnRegistrationStateChanged(_));
260   client_->Register(em::DeviceRegisterRequest::USER, kOAuthToken, kClientID,
261                     true, kRequisition, kStateKey);
262   EXPECT_EQ(kClientID, client_id_);
263 }
264
265 TEST_F(CloudPolicyClientTest, RegistrationNoToken) {
266   registration_response_.mutable_register_response()->
267       clear_device_management_token();
268   ExpectRegistration(kOAuthToken);
269   EXPECT_CALL(observer_, OnClientError(_));
270   client_->Register(em::DeviceRegisterRequest::USER, kOAuthToken, std::string(),
271                     false, std::string(), std::string());
272   EXPECT_FALSE(client_->is_registered());
273   EXPECT_FALSE(client_->GetPolicyFor(policy_ns_key_));
274   EXPECT_EQ(DM_STATUS_RESPONSE_DECODING_ERROR, client_->status());
275 }
276
277 TEST_F(CloudPolicyClientTest, RegistrationFailure) {
278   EXPECT_CALL(service_,
279               CreateJob(DeviceManagementRequestJob::TYPE_REGISTRATION,
280                         request_context_))
281       .WillOnce(service_.FailJob(DM_STATUS_REQUEST_FAILED));
282   EXPECT_CALL(service_, StartJob(_, _, _, _, _, _, _));
283   EXPECT_CALL(observer_, OnClientError(_));
284   client_->Register(em::DeviceRegisterRequest::USER, kOAuthToken, std::string(),
285                     false, std::string(), std::string());
286   EXPECT_FALSE(client_->is_registered());
287   EXPECT_FALSE(client_->GetPolicyFor(policy_ns_key_));
288   EXPECT_EQ(DM_STATUS_REQUEST_FAILED, client_->status());
289 }
290
291 TEST_F(CloudPolicyClientTest, RetryRegistration) {
292   // First registration does not set the re-register flag.
293   EXPECT_FALSE(
294       registration_request_.mutable_register_request()->has_reregister());
295   MockDeviceManagementJob* register_job = NULL;
296   EXPECT_CALL(service_,
297               CreateJob(DeviceManagementRequestJob::TYPE_REGISTRATION,
298                         request_context_))
299       .WillOnce(service_.CreateAsyncJob(&register_job));
300   EXPECT_CALL(service_, StartJob(dm_protocol::kValueRequestRegister,
301                                  "", kOAuthToken, "", "", _,
302                                  MatchProto(registration_request_)));
303   client_->Register(em::DeviceRegisterRequest::USER, kOAuthToken, std::string(),
304                     false, std::string(), std::string());
305   EXPECT_FALSE(client_->is_registered());
306   Mock::VerifyAndClearExpectations(&service_);
307
308   // Simulate a retry callback before proceeding; the re-register flag is set.
309   registration_request_.mutable_register_request()->set_reregister(true);
310   EXPECT_CALL(service_, StartJob(dm_protocol::kValueRequestRegister,
311                                  "", kOAuthToken, "", "", _,
312                                  MatchProto(registration_request_)));
313   register_job->RetryJob();
314   Mock::VerifyAndClearExpectations(&service_);
315
316   // Subsequent retries keep the flag set.
317   EXPECT_CALL(service_, StartJob(dm_protocol::kValueRequestRegister,
318                                  "", kOAuthToken, "", "", _,
319                                  MatchProto(registration_request_)));
320   register_job->RetryJob();
321   Mock::VerifyAndClearExpectations(&service_);
322 }
323
324 TEST_F(CloudPolicyClientTest, PolicyUpdate) {
325   Register();
326
327   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
328   EXPECT_CALL(observer_, OnPolicyFetched(_));
329   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
330   client_->FetchPolicy();
331   CheckPolicyResponse();
332
333   policy_response_.mutable_policy_response()->clear_response();
334   policy_response_.mutable_policy_response()->add_response()->set_policy_data(
335       CreatePolicyData("updated-fake-policy-data"));
336   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
337   EXPECT_CALL(observer_, OnPolicyFetched(_));
338   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
339   client_->FetchPolicy();
340   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
341   CheckPolicyResponse();
342 }
343
344 TEST_F(CloudPolicyClientTest, PolicyFetchWithMetaData) {
345   Register();
346
347   const base::Time timestamp(
348       base::Time::UnixEpoch() + base::TimeDelta::FromDays(20));
349   client_->set_submit_machine_id(true);
350   client_->set_last_policy_timestamp(timestamp);
351   client_->set_public_key_version(42);
352   em::PolicyFetchRequest* policy_fetch_request =
353       policy_request_.mutable_policy_request()->mutable_request(0);
354   policy_fetch_request->set_machine_id(kMachineID);
355   policy_fetch_request->set_timestamp(
356       (timestamp - base::Time::UnixEpoch()).InMilliseconds());
357   policy_fetch_request->set_public_key_version(42);
358
359   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
360   EXPECT_CALL(observer_, OnPolicyFetched(_));
361   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
362   client_->FetchPolicy();
363   CheckPolicyResponse();
364 }
365
366 TEST_F(CloudPolicyClientTest, PolicyFetchWithInvalidation) {
367   Register();
368
369   int64 previous_version = client_->fetched_invalidation_version();
370   client_->SetInvalidationInfo(12345, "12345");
371   EXPECT_EQ(previous_version, client_->fetched_invalidation_version());
372   em::PolicyFetchRequest* policy_fetch_request =
373       policy_request_.mutable_policy_request()->mutable_request(0);
374   policy_fetch_request->set_invalidation_version(12345);
375   policy_fetch_request->set_invalidation_payload("12345");
376
377   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
378   EXPECT_CALL(observer_, OnPolicyFetched(_));
379   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
380   client_->FetchPolicy();
381   CheckPolicyResponse();
382   EXPECT_EQ(12345, client_->fetched_invalidation_version());
383 }
384
385 TEST_F(CloudPolicyClientTest, PolicyFetchWithInvalidationNoPayload) {
386   Register();
387
388   int64 previous_version = client_->fetched_invalidation_version();
389   client_->SetInvalidationInfo(-12345, std::string());
390   EXPECT_EQ(previous_version, client_->fetched_invalidation_version());
391
392   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
393   EXPECT_CALL(observer_, OnPolicyFetched(_));
394   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
395   client_->FetchPolicy();
396   CheckPolicyResponse();
397   EXPECT_EQ(-12345, client_->fetched_invalidation_version());
398 }
399
400 TEST_F(CloudPolicyClientTest, BadPolicyResponse) {
401   Register();
402
403   policy_response_.clear_policy_response();
404   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
405   EXPECT_CALL(observer_, OnClientError(_));
406   client_->FetchPolicy();
407   EXPECT_FALSE(client_->GetPolicyFor(policy_ns_key_));
408   EXPECT_EQ(DM_STATUS_RESPONSE_DECODING_ERROR, client_->status());
409
410   policy_response_.mutable_policy_response()->add_response()->set_policy_data(
411       CreatePolicyData("fake-policy-data"));
412   policy_response_.mutable_policy_response()->add_response()->set_policy_data(
413       CreatePolicyData("excess-fake-policy-data"));
414   ExpectPolicyFetch(kDMToken, dm_protocol::kValueUserAffiliationNone);
415   EXPECT_CALL(observer_, OnPolicyFetched(_));
416   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
417   client_->FetchPolicy();
418   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
419   CheckPolicyResponse();
420 }
421
422 TEST_F(CloudPolicyClientTest, PolicyRequestFailure) {
423   Register();
424
425   EXPECT_CALL(service_,
426               CreateJob(DeviceManagementRequestJob::TYPE_POLICY_FETCH,
427                         request_context_))
428       .WillOnce(service_.FailJob(DM_STATUS_REQUEST_FAILED));
429   EXPECT_CALL(service_, StartJob(_, _, _, _, _, _, _));
430   EXPECT_CALL(observer_, OnClientError(_));
431   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully()).Times(0);
432   client_->FetchPolicy();
433   EXPECT_EQ(DM_STATUS_REQUEST_FAILED, client_->status());
434   EXPECT_FALSE(client_->GetPolicyFor(policy_ns_key_));
435 }
436
437 TEST_F(CloudPolicyClientTest, Unregister) {
438   Register();
439
440   ExpectUnregistration(kDMToken);
441   EXPECT_CALL(observer_, OnRegistrationStateChanged(_));
442   client_->Unregister();
443   EXPECT_FALSE(client_->is_registered());
444   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
445 }
446
447 TEST_F(CloudPolicyClientTest, UnregisterEmpty) {
448   Register();
449
450   unregistration_response_.clear_unregister_response();
451   EXPECT_CALL(service_,
452               CreateJob(DeviceManagementRequestJob::TYPE_UNREGISTRATION,
453                         request_context_))
454       .WillOnce(service_.SucceedJob(unregistration_response_));
455   EXPECT_CALL(service_, StartJob(_, _, _, _, _, _, _));
456   EXPECT_CALL(observer_, OnRegistrationStateChanged(_));
457   client_->Unregister();
458   EXPECT_FALSE(client_->is_registered());
459   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
460 }
461
462 TEST_F(CloudPolicyClientTest, UnregisterFailure) {
463   Register();
464
465   EXPECT_CALL(service_,
466               CreateJob(DeviceManagementRequestJob::TYPE_UNREGISTRATION,
467                         request_context_))
468       .WillOnce(service_.FailJob(DM_STATUS_REQUEST_FAILED));
469   EXPECT_CALL(service_, StartJob(_, _, _, _, _, _, _));
470   EXPECT_CALL(observer_, OnClientError(_));
471   client_->Unregister();
472   EXPECT_TRUE(client_->is_registered());
473   EXPECT_EQ(DM_STATUS_REQUEST_FAILED, client_->status());
474 }
475
476 TEST_F(CloudPolicyClientTest, PolicyFetchWithExtensionPolicy) {
477   Register();
478
479   // Setup the |expected_responses| and |policy_response_|.
480   static const char* kExtensions[] = {
481     "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
482     "bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb",
483     "cccccccccccccccccccccccccccccccc",
484   };
485   typedef std::map<PolicyNamespaceKey, em::PolicyFetchResponse> ResponseMap;
486   ResponseMap expected_responses;
487   std::set<PolicyNamespaceKey> expected_namespaces;
488   PolicyNamespaceKey key(dm_protocol::kChromeUserPolicyType, std::string());
489   // Copy the user policy fetch request.
490   expected_responses[key].CopyFrom(
491       policy_response_.policy_response().response(0));
492   expected_namespaces.insert(key);
493   key.first = dm_protocol::kChromeExtensionPolicyType;
494   for (size_t i = 0; i < arraysize(kExtensions); ++i) {
495     key.second = kExtensions[i];
496     em::PolicyData policy_data;
497     policy_data.set_policy_type(key.first);
498     policy_data.set_settings_entity_id(key.second);
499     expected_responses[key].set_policy_data(policy_data.SerializeAsString());
500     policy_response_.mutable_policy_response()->add_response()->CopyFrom(
501         expected_responses[key]);
502     expected_namespaces.insert(key);
503   }
504
505   // Make a policy fetch.
506   EXPECT_CALL(service_,
507               CreateJob(DeviceManagementRequestJob::TYPE_POLICY_FETCH,
508                         request_context_))
509       .WillOnce(service_.SucceedJob(policy_response_));
510   EXPECT_CALL(service_, StartJob(dm_protocol::kValueRequestPolicy, "", "",
511                                  kDMToken,
512                                  dm_protocol::kValueUserAffiliationNone,
513                                  client_id_, _))
514       .WillOnce(SaveArg<6>(&policy_request_));
515   EXPECT_CALL(observer_, OnPolicyFetched(_));
516   EXPECT_CALL(status_provider_, OnSubmittedSuccessfully());
517   for (size_t i = 0; i < arraysize(kExtensions); ++i) {
518     client_->AddNamespaceToFetch(PolicyNamespaceKey(
519         dm_protocol::kChromeExtensionPolicyType, kExtensions[i]));
520   }
521   client_->FetchPolicy();
522
523   // Verify that the request includes the expected namespaces.
524   ASSERT_TRUE(policy_request_.has_policy_request());
525   const em::DevicePolicyRequest& policy_request =
526       policy_request_.policy_request();
527   ASSERT_EQ(static_cast<int>(1 + arraysize(kExtensions)),
528             policy_request.request_size());
529   for (int i = 0; i < policy_request.request_size(); ++i) {
530     const em::PolicyFetchRequest& fetch_request = policy_request.request(i);
531     ASSERT_TRUE(fetch_request.has_policy_type());
532     std::string entity_id;
533     if (fetch_request.has_settings_entity_id())
534       entity_id = fetch_request.settings_entity_id();
535     PolicyNamespaceKey key(fetch_request.policy_type(), entity_id);
536     EXPECT_EQ(1u, expected_namespaces.erase(key));
537   }
538   EXPECT_TRUE(expected_namespaces.empty());
539
540   // Verify that the client got all the responses mapped to their namespaces.
541   for (ResponseMap::iterator it = expected_responses.begin();
542        it != expected_responses.end(); ++it) {
543     const em::PolicyFetchResponse* response = client_->GetPolicyFor(it->first);
544     ASSERT_TRUE(response);
545     EXPECT_EQ(it->second.SerializeAsString(), response->SerializeAsString());
546   }
547 }
548
549 TEST_F(CloudPolicyClientTest, UploadCertificate) {
550   Register();
551
552   ExpectUploadCertificate();
553   EXPECT_CALL(upload_certificate_observer_, OnUploadComplete(true)).Times(1);
554   CloudPolicyClient::StatusCallback callback = base::Bind(
555       &MockUploadCertificateObserver::OnUploadComplete,
556       base::Unretained(&upload_certificate_observer_));
557   client_->UploadCertificate(kDeviceCertificate, callback);
558   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
559 }
560
561 TEST_F(CloudPolicyClientTest, UploadCertificateEmpty) {
562   Register();
563
564   upload_certificate_response_.clear_cert_upload_response();
565   ExpectUploadCertificate();
566   EXPECT_CALL(upload_certificate_observer_, OnUploadComplete(false)).Times(1);
567   CloudPolicyClient::StatusCallback callback = base::Bind(
568       &MockUploadCertificateObserver::OnUploadComplete,
569       base::Unretained(&upload_certificate_observer_));
570   client_->UploadCertificate(kDeviceCertificate, callback);
571   EXPECT_EQ(DM_STATUS_SUCCESS, client_->status());
572 }
573
574 TEST_F(CloudPolicyClientTest, UploadCertificateFailure) {
575   Register();
576
577   EXPECT_CALL(upload_certificate_observer_, OnUploadComplete(false)).Times(1);
578   EXPECT_CALL(service_,
579               CreateJob(DeviceManagementRequestJob::TYPE_UPLOAD_CERTIFICATE,
580                         request_context_))
581       .WillOnce(service_.FailJob(DM_STATUS_REQUEST_FAILED));
582   EXPECT_CALL(service_, StartJob(_, _, _, _, _, _, _));
583   EXPECT_CALL(observer_, OnClientError(_));
584   CloudPolicyClient::StatusCallback callback = base::Bind(
585       &MockUploadCertificateObserver::OnUploadComplete,
586       base::Unretained(&upload_certificate_observer_));
587   client_->UploadCertificate(kDeviceCertificate, callback);
588   EXPECT_EQ(DM_STATUS_REQUEST_FAILED, client_->status());
589 }
590
591 }  // namespace policy