cloud_external_data_policy_observer_unittest.cc revision cedac228d2dd51db4b79ea1e72c7f249408ee061
1// Copyright 2013 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/chromeos/policy/cloud_external_data_policy_observer.h"
6
7#include <utility>
8#include <vector>
9
10#include "base/file_util.h"
11#include "base/files/file_path.h"
12#include "base/json/json_writer.h"
13#include "base/memory/ref_counted.h"
14#include "base/message_loop/message_loop.h"
15#include "base/message_loop/message_loop_proxy.h"
16#include "base/path_service.h"
17#include "base/run_loop.h"
18#include "base/values.h"
19#include "chrome/browser/chrome_notification_types.h"
20#include "chrome/browser/chromeos/login/users/fake_user_manager.h"
21#include "chrome/browser/chromeos/policy/cloud_external_data_manager_base_test_util.h"
22#include "chrome/browser/chromeos/policy/device_local_account.h"
23#include "chrome/browser/chromeos/policy/device_local_account_external_data_manager.h"
24#include "chrome/browser/chromeos/policy/device_local_account_policy_provider.h"
25#include "chrome/browser/chromeos/policy/device_local_account_policy_service.h"
26#include "chrome/browser/chromeos/policy/proto/chrome_device_policy.pb.h"
27#include "chrome/browser/chromeos/settings/device_settings_service.h"
28#include "chrome/browser/chromeos/settings/device_settings_test_helper.h"
29#include "chrome/browser/profiles/profile.h"
30#include "chrome/common/chrome_paths.h"
31#include "chrome/test/base/testing_profile.h"
32#include "components/policy/core/common/cloud/cloud_policy_core.h"
33#include "components/policy/core/common/cloud/cloud_policy_store.h"
34#include "components/policy/core/common/cloud/mock_cloud_external_data_manager.h"
35#include "components/policy/core/common/cloud/policy_builder.h"
36#include "components/policy/core/common/external_data_fetcher.h"
37#include "components/policy/core/common/mock_configuration_policy_provider.h"
38#include "components/policy/core/common/policy_map.h"
39#include "components/policy/core/common/policy_service.h"
40#include "components/policy/core/common/policy_service_impl.h"
41#include "components/policy/core/common/policy_types.h"
42#include "content/public/browser/notification_details.h"
43#include "content/public/browser/notification_service.h"
44#include "content/public/browser/notification_source.h"
45#include "net/url_request/test_url_fetcher_factory.h"
46#include "net/url_request/url_fetcher_delegate.h"
47#include "net/url_request/url_request_context_getter.h"
48#include "net/url_request/url_request_status.h"
49#include "policy/policy_constants.h"
50#include "policy/proto/cloud_policy.pb.h"
51#include "testing/gmock/include/gmock/gmock.h"
52#include "testing/gtest/include/gtest/gtest.h"
53#include "url/gurl.h"
54
55namespace em = enterprise_management;
56
57using ::testing::Mock;
58using ::testing::Return;
59using ::testing::SaveArg;
60using ::testing::_;
61
62namespace policy {
63
64namespace {
65
66const char kDeviceLocalAccount[] = "device_local_account@localhost";
67
68const char kRegularUserID[] = "user@example.com";
69
70const char kAvatar1URL[] = "http://localhost/avatar1.jpg";
71const char kAvatar2URL[] = "http://localhost/avatar2.jpg";
72
73void ConstructAvatarPolicy(const std::string& file_name,
74                           const std::string& url,
75                           std::string* policy_data,
76                           std::string* policy) {
77  base::FilePath test_data_dir;
78  ASSERT_TRUE(PathService::Get(chrome::DIR_TEST_DATA, &test_data_dir));
79  ASSERT_TRUE(base::ReadFileToString(
80      test_data_dir.Append("chromeos").Append(file_name),
81      policy_data));
82  base::JSONWriter::Write(
83      test::ConstructExternalDataReference(url, *policy_data).get(),
84      policy);
85}
86
87}  // namespace
88
89class CloudExternalDataPolicyObserverTest
90    : public chromeos::DeviceSettingsTestBase,
91      public CloudExternalDataPolicyObserver::Delegate {
92 public:
93  typedef std::pair<std::string, std::string> FetchedCall;
94
95  CloudExternalDataPolicyObserverTest();
96  virtual ~CloudExternalDataPolicyObserverTest();
97
98  // chromeos::DeviceSettingsTestBase:
99  virtual void SetUp() OVERRIDE;
100  virtual void TearDown() OVERRIDE;
101
102  // CloudExternalDataPolicyObserver::Delegate:
103  virtual void OnExternalDataSet(const std::string& policy,
104                                 const std::string& user_id) OVERRIDE;
105  virtual void OnExternalDataCleared(const std::string& policy,
106                                     const std::string& user_id) OVERRIDE;
107  virtual void OnExternalDataFetched(const std::string& policy,
108                                     const std::string& user_id,
109                                     scoped_ptr<std::string> data) OVERRIDE;
110
111  void CreateObserver();
112
113  void ClearObservations();
114
115  void SetDeviceLocalAccountAvatarPolicy(const std::string& account_id,
116                                         const std::string& value);
117
118  void AddDeviceLocalAccount(const std::string& account_id);
119  void RemoveDeviceLocalAccount(const std::string& account_id);
120
121  DeviceLocalAccountPolicyBroker* GetBrokerForDeviceLocalAccountUser();
122
123  void RefreshDeviceLocalAccountPolicy(DeviceLocalAccountPolicyBroker* broker);
124
125  void LogInAsDeviceLocalAccount(const std::string& user_id);
126
127  void SetRegularUserAvatarPolicy(const std::string& value);
128
129  void LogInAsRegularUser();
130
131  const std::string device_local_account_user_id_;
132
133  std::string avatar_policy_1_data_;
134  std::string avatar_policy_2_data_;
135  std::string avatar_policy_1_;
136  std::string avatar_policy_2_;
137
138  chromeos::CrosSettings cros_settings_;
139  chromeos::FakeUserManager user_manager_;
140  scoped_ptr<DeviceLocalAccountPolicyService>
141      device_local_account_policy_service_;
142  net::TestURLFetcherFactory url_fetcher_factory_;
143
144  scoped_ptr<DeviceLocalAccountPolicyProvider>
145      device_local_account_policy_provider_;
146
147  MockCloudExternalDataManager external_data_manager_;
148  MockConfigurationPolicyProvider user_policy_provider_;
149
150  scoped_ptr<TestingProfile> profile_;
151
152  scoped_ptr<CloudExternalDataPolicyObserver> observer_;
153
154  std::vector<std::string> set_calls_;
155  std::vector<std::string> cleared_calls_;
156  std::vector<FetchedCall> fetched_calls_;
157
158  ExternalDataFetcher::FetchCallback fetch_callback_;
159
160 private:
161  DISALLOW_COPY_AND_ASSIGN(CloudExternalDataPolicyObserverTest);
162};
163
164CloudExternalDataPolicyObserverTest::CloudExternalDataPolicyObserverTest()
165    : device_local_account_user_id_(GenerateDeviceLocalAccountUserId(
166          kDeviceLocalAccount,
167          DeviceLocalAccount::TYPE_PUBLIC_SESSION)),
168      cros_settings_(&device_settings_service_) {
169}
170
171CloudExternalDataPolicyObserverTest::~CloudExternalDataPolicyObserverTest() {
172}
173
174void CloudExternalDataPolicyObserverTest::SetUp() {
175  chromeos::DeviceSettingsTestBase::SetUp();
176  device_local_account_policy_service_.reset(
177      new DeviceLocalAccountPolicyService(&device_settings_test_helper_,
178                                          &device_settings_service_,
179                                          &cros_settings_,
180                                          loop_.message_loop_proxy(),
181                                          loop_.message_loop_proxy(),
182                                          loop_.message_loop_proxy(),
183                                          loop_.message_loop_proxy(),
184                                          NULL));
185  url_fetcher_factory_.set_remove_fetcher_on_delete(true);
186
187  EXPECT_CALL(user_policy_provider_, IsInitializationComplete(_))
188      .WillRepeatedly(Return(true));
189  user_policy_provider_.Init();
190
191  ConstructAvatarPolicy("avatar1.jpg",
192                        kAvatar1URL,
193                        &avatar_policy_1_data_,
194                        &avatar_policy_1_);
195  ConstructAvatarPolicy("avatar2.jpg",
196                        kAvatar2URL,
197                        &avatar_policy_2_data_,
198                        &avatar_policy_2_);
199}
200
201void CloudExternalDataPolicyObserverTest::TearDown() {
202  observer_.reset();
203  user_policy_provider_.Shutdown();
204  profile_.reset();
205  if (device_local_account_policy_provider_) {
206    device_local_account_policy_provider_->Shutdown();
207    device_local_account_policy_provider_.reset();
208  }
209  device_local_account_policy_service_->Shutdown();
210  device_local_account_policy_service_.reset();
211  chromeos::DeviceSettingsTestBase::TearDown();
212}
213
214
215void CloudExternalDataPolicyObserverTest::OnExternalDataSet(
216    const std::string& policy,
217    const std::string& user_id) {
218  EXPECT_EQ(key::kUserAvatarImage, policy);
219  set_calls_.push_back(user_id);
220}
221
222void CloudExternalDataPolicyObserverTest::OnExternalDataCleared(
223    const std::string& policy,
224    const std::string& user_id) {
225  EXPECT_EQ(key::kUserAvatarImage, policy);
226  cleared_calls_.push_back(user_id);
227}
228
229void CloudExternalDataPolicyObserverTest::OnExternalDataFetched(
230    const std::string& policy,
231    const std::string& user_id,
232    scoped_ptr<std::string> data) {
233  EXPECT_EQ(key::kUserAvatarImage, policy);
234  fetched_calls_.push_back(make_pair(user_id, std::string()));
235  fetched_calls_.back().second.swap(*data);
236}
237
238void CloudExternalDataPolicyObserverTest::CreateObserver() {
239  observer_.reset(new CloudExternalDataPolicyObserver(
240      &cros_settings_,
241      &user_manager_,
242      device_local_account_policy_service_.get(),
243      key::kUserAvatarImage,
244      this));
245  observer_->Init();
246}
247
248void CloudExternalDataPolicyObserverTest::ClearObservations() {
249  set_calls_.clear();
250  cleared_calls_.clear();
251  fetched_calls_.clear();
252}
253
254void CloudExternalDataPolicyObserverTest::SetDeviceLocalAccountAvatarPolicy(
255    const std::string& account_id,
256    const std::string& value) {
257  UserPolicyBuilder builder;
258  builder.policy_data().set_policy_type(
259      dm_protocol::kChromePublicAccountPolicyType);
260  builder.policy_data().set_settings_entity_id(account_id);
261  builder.policy_data().set_username(account_id);
262  if (!value.empty())
263    builder.payload().mutable_useravatarimage()->set_value(value);
264  builder.Build();
265  device_settings_test_helper_.set_device_local_account_policy_blob(
266      account_id,
267      builder.GetBlob());
268}
269
270void CloudExternalDataPolicyObserverTest::AddDeviceLocalAccount(
271    const std::string& account_id) {
272  em::DeviceLocalAccountInfoProto* account =
273      device_policy_.payload().mutable_device_local_accounts()->add_account();
274  account->set_account_id(account_id);
275  account->set_type(
276      em::DeviceLocalAccountInfoProto::ACCOUNT_TYPE_PUBLIC_SESSION);
277  device_policy_.Build();
278  device_settings_test_helper_.set_policy_blob(device_policy_.GetBlob());
279  ReloadDeviceSettings();
280}
281
282void CloudExternalDataPolicyObserverTest::RemoveDeviceLocalAccount(
283    const std::string& account_id) {
284  em::DeviceLocalAccountsProto* accounts =
285      device_policy_.payload().mutable_device_local_accounts();
286  std::vector<std::string> account_ids;
287  for (int i = 0; i < accounts->account_size(); ++i) {
288    if (accounts->account(i).account_id() != account_id)
289      account_ids.push_back(accounts->account(i).account_id());
290  }
291  accounts->clear_account();
292  for (std::vector<std::string>::const_iterator it = account_ids.begin();
293       it != account_ids.end(); ++it) {
294    em::DeviceLocalAccountInfoProto* account = accounts->add_account();
295    account->set_account_id(*it);
296    account->set_type(
297        em::DeviceLocalAccountInfoProto::ACCOUNT_TYPE_PUBLIC_SESSION);
298  }
299  device_policy_.Build();
300  device_settings_test_helper_.set_policy_blob(device_policy_.GetBlob());
301  ReloadDeviceSettings();
302}
303
304DeviceLocalAccountPolicyBroker*
305    CloudExternalDataPolicyObserverTest::GetBrokerForDeviceLocalAccountUser() {
306  return device_local_account_policy_service_->GetBrokerForUser(
307      device_local_account_user_id_);
308}
309
310void CloudExternalDataPolicyObserverTest::RefreshDeviceLocalAccountPolicy(
311    DeviceLocalAccountPolicyBroker* broker) {
312  broker->core()->store()->Load();
313  device_settings_test_helper_.Flush();
314}
315
316void CloudExternalDataPolicyObserverTest::LogInAsDeviceLocalAccount(
317    const std::string& user_id) {
318  device_local_account_policy_provider_.reset(
319      new DeviceLocalAccountPolicyProvider(
320          user_id,
321          device_local_account_policy_service_.get(),
322          scoped_ptr<PolicyMap>()));
323
324  PolicyServiceImpl::Providers providers;
325  providers.push_back(device_local_account_policy_provider_.get());
326  TestingProfile::Builder builder;
327  builder.SetPolicyService(
328      scoped_ptr<PolicyService>(new PolicyServiceImpl(providers)));
329
330  profile_ = builder.Build();
331  profile_->set_profile_name(user_id);
332
333  user_manager_.AddUser(user_id);
334  content::NotificationService::current()->Notify(
335      chrome::NOTIFICATION_LOGIN_USER_PROFILE_PREPARED,
336      content::NotificationService::AllSources(),
337      content::Details<Profile>(profile_.get()));
338}
339
340void CloudExternalDataPolicyObserverTest::SetRegularUserAvatarPolicy(
341    const std::string& value) {
342  PolicyMap policy_map;
343  if (!value.empty()) {
344    policy_map.Set(
345        key::kUserAvatarImage,
346        POLICY_LEVEL_MANDATORY,
347        POLICY_SCOPE_USER,
348        new base::StringValue(value),
349        external_data_manager_.CreateExternalDataFetcher(
350            key::kUserAvatarImage).release());
351  }
352  user_policy_provider_.UpdateChromePolicy(policy_map);
353}
354
355void CloudExternalDataPolicyObserverTest::LogInAsRegularUser() {
356  PolicyServiceImpl::Providers providers;
357  providers.push_back(&user_policy_provider_);
358  TestingProfile::Builder builder;
359  builder.SetPolicyService(
360      scoped_ptr<PolicyService>(new PolicyServiceImpl(providers)));
361
362  profile_ = builder.Build();
363  profile_->set_profile_name(kRegularUserID);
364
365  user_manager_.AddUser(kRegularUserID);
366  content::NotificationService::current()->Notify(
367      chrome::NOTIFICATION_LOGIN_USER_PROFILE_PREPARED,
368      content::NotificationService::AllSources(),
369      content::Details<Profile>(profile_.get()));
370}
371
372// Verifies that when an external data reference is set for a device-local
373// account, a corresponding notification is emitted and a fetch is started.
374// Further verifies that when the fetch succeeds, a notification containing the
375// external data is emitted.
376TEST_F(CloudExternalDataPolicyObserverTest,
377       ExistingDeviceLocalAccountFetchSuccess) {
378  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, avatar_policy_1_);
379  AddDeviceLocalAccount(kDeviceLocalAccount);
380
381  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
382  ASSERT_TRUE(broker);
383  broker->external_data_manager()->Connect(NULL);
384  base::RunLoop().RunUntilIdle();
385
386  CreateObserver();
387
388  EXPECT_TRUE(cleared_calls_.empty());
389  EXPECT_TRUE(fetched_calls_.empty());
390  ASSERT_EQ(1u, set_calls_.size());
391  EXPECT_EQ(device_local_account_user_id_, set_calls_.front());
392  ClearObservations();
393
394  net::TestURLFetcher* fetcher = url_fetcher_factory_.GetFetcherByID(0);
395  ASSERT_TRUE(fetcher);
396  EXPECT_EQ(GURL(kAvatar1URL), fetcher->GetOriginalURL());
397
398  fetcher->SetResponseString(avatar_policy_1_data_);
399  fetcher->set_status(net::URLRequestStatus(net::URLRequestStatus::SUCCESS,
400                                            net::OK));
401  fetcher->set_response_code(200);
402  fetcher->delegate()->OnURLFetchComplete(fetcher);
403  base::RunLoop().RunUntilIdle();
404
405  EXPECT_TRUE(set_calls_.empty());
406  EXPECT_TRUE(cleared_calls_.empty());
407  ASSERT_EQ(1u, fetched_calls_.size());
408  EXPECT_EQ(device_local_account_user_id_, fetched_calls_.front().first);
409  EXPECT_EQ(avatar_policy_1_data_, fetched_calls_.front().second);
410  ClearObservations();
411
412  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(1));
413}
414
415// Verifies that when an external data reference is set for a device-local
416// account, a corresponding notification is emitted and a fetch is started.
417// Further verifies that when the fetch fails, no notification is emitted.
418TEST_F(CloudExternalDataPolicyObserverTest,
419       ExistingDeviceLocalAccountFetchFailure) {
420  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, avatar_policy_1_);
421  AddDeviceLocalAccount(kDeviceLocalAccount);
422
423  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
424  ASSERT_TRUE(broker);
425  broker->external_data_manager()->Connect(NULL);
426  base::RunLoop().RunUntilIdle();
427
428  CreateObserver();
429
430  EXPECT_TRUE(cleared_calls_.empty());
431  EXPECT_TRUE(fetched_calls_.empty());
432  ASSERT_EQ(1u, set_calls_.size());
433  EXPECT_EQ(device_local_account_user_id_, set_calls_.front());
434  ClearObservations();
435
436  net::TestURLFetcher* fetcher = url_fetcher_factory_.GetFetcherByID(0);
437  ASSERT_TRUE(fetcher);
438  EXPECT_EQ(GURL(kAvatar1URL), fetcher->GetOriginalURL());
439
440  fetcher->set_status(net::URLRequestStatus(net::URLRequestStatus::SUCCESS,
441                                            net::OK));
442  fetcher->set_response_code(400);
443  fetcher->delegate()->OnURLFetchComplete(fetcher);
444  base::RunLoop().RunUntilIdle();
445
446  EXPECT_TRUE(set_calls_.empty());
447  EXPECT_TRUE(cleared_calls_.empty());
448  EXPECT_TRUE(fetched_calls_.empty());
449  ClearObservations();
450
451  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(1));
452}
453
454// Verifies that when the external data reference for a device-local account is
455// initially not set, no notifications are emitted. Further verifies that when
456// the external data reference is then cleared (which is a no-op), again, no
457// notifications are emitted.
458TEST_F(CloudExternalDataPolicyObserverTest,
459       ExistingDeviceLocalAccountClearUnset) {
460  AddDeviceLocalAccount(kDeviceLocalAccount);
461
462  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
463  ASSERT_TRUE(broker);
464  broker->external_data_manager()->Connect(NULL);
465  base::RunLoop().RunUntilIdle();
466
467  CreateObserver();
468
469  EXPECT_TRUE(set_calls_.empty());
470  EXPECT_TRUE(cleared_calls_.empty());
471  EXPECT_TRUE(fetched_calls_.empty());
472  ClearObservations();
473
474  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(0));
475
476  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, "");
477  RefreshDeviceLocalAccountPolicy(broker);
478
479  EXPECT_TRUE(set_calls_.empty());
480  EXPECT_TRUE(cleared_calls_.empty());
481  EXPECT_TRUE(fetched_calls_.empty());
482  ClearObservations();
483
484  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(0));
485}
486
487// Verifies that when the external data reference for a device-local account is
488// initially set, a corresponding notification is emitted and a fetch is
489// started. Further verifies that when the external data reference is then
490// cleared, a corresponding notification is emitted and the fetch is canceled.
491TEST_F(CloudExternalDataPolicyObserverTest,
492       ExistingDeviceLocalAccountClearSet) {
493  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, avatar_policy_1_);
494  AddDeviceLocalAccount(kDeviceLocalAccount);
495
496  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
497  ASSERT_TRUE(broker);
498  broker->external_data_manager()->Connect(NULL);
499  base::RunLoop().RunUntilIdle();
500
501  CreateObserver();
502
503  EXPECT_TRUE(cleared_calls_.empty());
504  EXPECT_TRUE(fetched_calls_.empty());
505  ASSERT_EQ(1u, set_calls_.size());
506  EXPECT_EQ(device_local_account_user_id_, set_calls_.front());
507  ClearObservations();
508
509  net::TestURLFetcher* fetcher = url_fetcher_factory_.GetFetcherByID(0);
510  ASSERT_TRUE(fetcher);
511  EXPECT_EQ(GURL(kAvatar1URL), fetcher->GetOriginalURL());
512
513  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, "");
514  RefreshDeviceLocalAccountPolicy(broker);
515
516  EXPECT_TRUE(set_calls_.empty());
517  EXPECT_TRUE(fetched_calls_.empty());
518  ASSERT_EQ(1u, cleared_calls_.size());
519  EXPECT_EQ(device_local_account_user_id_, cleared_calls_.front());
520  ClearObservations();
521
522  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(0));
523}
524
525// Verifies that when the external data reference for a device-local account is
526// initially not set, no notifications are emitted. Further verifies that when
527// the external data reference is then set, a corresponding notification is
528// emitted and a fetch is started. Also verifies that when the fetch eventually
529// succeeds, a notification containing the external data is emitted.
530TEST_F(CloudExternalDataPolicyObserverTest,
531       ExistingDeviceLocalAccountSetUnset) {
532  AddDeviceLocalAccount(kDeviceLocalAccount);
533
534  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
535  ASSERT_TRUE(broker);
536  broker->external_data_manager()->Connect(NULL);
537  base::RunLoop().RunUntilIdle();
538
539  CreateObserver();
540
541  EXPECT_TRUE(set_calls_.empty());
542  EXPECT_TRUE(cleared_calls_.empty());
543  EXPECT_TRUE(fetched_calls_.empty());
544  ClearObservations();
545
546  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, avatar_policy_1_);
547  RefreshDeviceLocalAccountPolicy(broker);
548
549  EXPECT_TRUE(cleared_calls_.empty());
550  EXPECT_TRUE(fetched_calls_.empty());
551  ASSERT_EQ(1u, set_calls_.size());
552  EXPECT_EQ(device_local_account_user_id_, set_calls_.front());
553  ClearObservations();
554
555  net::TestURLFetcher* fetcher = url_fetcher_factory_.GetFetcherByID(0);
556  ASSERT_TRUE(fetcher);
557  EXPECT_EQ(GURL(kAvatar1URL), fetcher->GetOriginalURL());
558
559  fetcher->SetResponseString(avatar_policy_1_data_);
560  fetcher->set_status(net::URLRequestStatus(net::URLRequestStatus::SUCCESS,
561                                            net::OK));
562  fetcher->set_response_code(200);
563  fetcher->delegate()->OnURLFetchComplete(fetcher);
564  base::RunLoop().RunUntilIdle();
565
566  EXPECT_TRUE(set_calls_.empty());
567  EXPECT_TRUE(cleared_calls_.empty());
568  ASSERT_EQ(1u, fetched_calls_.size());
569  EXPECT_EQ(device_local_account_user_id_, fetched_calls_.front().first);
570  EXPECT_EQ(avatar_policy_1_data_, fetched_calls_.front().second);
571  ClearObservations();
572
573  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(1));
574}
575
576// Verifies that when the external data reference for a device-local account is
577// initially set, a corresponding notification is emitted and a fetch is
578// started. Further verifies that when the external data reference is then
579// updated, a corresponding notification is emitted and the fetch is restarted.
580// Also verifies that when the fetch eventually succeeds, a notification
581// containing the external data is emitted.
582TEST_F(CloudExternalDataPolicyObserverTest, ExistingDeviceLocalAccountSetSet) {
583  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, avatar_policy_1_);
584  AddDeviceLocalAccount(kDeviceLocalAccount);
585
586  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
587  ASSERT_TRUE(broker);
588  broker->external_data_manager()->Connect(NULL);
589  base::RunLoop().RunUntilIdle();
590
591  CreateObserver();
592
593  EXPECT_TRUE(cleared_calls_.empty());
594  EXPECT_TRUE(fetched_calls_.empty());
595  ASSERT_EQ(1u, set_calls_.size());
596  EXPECT_EQ(device_local_account_user_id_, set_calls_.front());
597  ClearObservations();
598
599  net::TestURLFetcher* fetcher = url_fetcher_factory_.GetFetcherByID(0);
600  ASSERT_TRUE(fetcher);
601  EXPECT_EQ(GURL(kAvatar1URL), fetcher->GetOriginalURL());
602
603  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, avatar_policy_2_);
604  RefreshDeviceLocalAccountPolicy(broker);
605
606  EXPECT_TRUE(cleared_calls_.empty());
607  EXPECT_TRUE(fetched_calls_.empty());
608  ASSERT_EQ(1u, set_calls_.size());
609  EXPECT_EQ(device_local_account_user_id_, set_calls_.front());
610  ClearObservations();
611
612  fetcher = url_fetcher_factory_.GetFetcherByID(1);
613  ASSERT_TRUE(fetcher);
614  EXPECT_EQ(GURL(kAvatar2URL), fetcher->GetOriginalURL());
615
616  fetcher->SetResponseString(avatar_policy_2_data_);
617  fetcher->set_status(net::URLRequestStatus(net::URLRequestStatus::SUCCESS,
618                                            net::OK));
619  fetcher->set_response_code(200);
620  fetcher->delegate()->OnURLFetchComplete(fetcher);
621  base::RunLoop().RunUntilIdle();
622
623  EXPECT_TRUE(set_calls_.empty());
624  EXPECT_TRUE(cleared_calls_.empty());
625  ASSERT_EQ(1u, fetched_calls_.size());
626  EXPECT_EQ(device_local_account_user_id_, fetched_calls_.front().first);
627  EXPECT_EQ(avatar_policy_2_data_, fetched_calls_.front().second);
628  ClearObservations();
629
630  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(2));
631}
632
633// Verifies that when the external data reference for a device-local account is
634// initially not set, no notifications are emitted during login into the
635// account. Further verifies that when the external data reference is then set,
636// a corresponding notification is emitted only once and a fetch is started.
637// Also verifies that when the fetch eventually succeeds, a notification
638// containing the external data is emitted, again, only once.
639TEST_F(CloudExternalDataPolicyObserverTest,
640       ExistingDeviceLocalAccountSetAfterLogin) {
641  AddDeviceLocalAccount(kDeviceLocalAccount);
642
643  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
644  ASSERT_TRUE(broker);
645  broker->external_data_manager()->Connect(NULL);
646  base::RunLoop().RunUntilIdle();
647
648  CreateObserver();
649
650  LogInAsDeviceLocalAccount(kDeviceLocalAccount);
651
652  EXPECT_TRUE(set_calls_.empty());
653  EXPECT_TRUE(cleared_calls_.empty());
654  EXPECT_TRUE(fetched_calls_.empty());
655  ClearObservations();
656
657  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, avatar_policy_1_);
658  RefreshDeviceLocalAccountPolicy(broker);
659
660  EXPECT_TRUE(cleared_calls_.empty());
661  EXPECT_TRUE(fetched_calls_.empty());
662  ASSERT_EQ(1u, set_calls_.size());
663  EXPECT_EQ(device_local_account_user_id_, set_calls_.front());
664  ClearObservations();
665
666  net::TestURLFetcher* fetcher = url_fetcher_factory_.GetFetcherByID(0);
667  ASSERT_TRUE(fetcher);
668  EXPECT_EQ(GURL(kAvatar1URL), fetcher->GetOriginalURL());
669
670  fetcher->SetResponseString(avatar_policy_1_data_);
671  fetcher->set_status(net::URLRequestStatus(net::URLRequestStatus::SUCCESS,
672                                            net::OK));
673  fetcher->set_response_code(200);
674  fetcher->delegate()->OnURLFetchComplete(fetcher);
675  base::RunLoop().RunUntilIdle();
676
677  EXPECT_TRUE(set_calls_.empty());
678  EXPECT_TRUE(cleared_calls_.empty());
679  ASSERT_EQ(1u, fetched_calls_.size());
680  EXPECT_EQ(device_local_account_user_id_, fetched_calls_.front().first);
681  EXPECT_EQ(avatar_policy_1_data_, fetched_calls_.front().second);
682  ClearObservations();
683
684  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(1));
685}
686
687// Verifies that when the external data reference for a device-local account is
688// initially not set, no notifications are emitted. Further verifies that when
689// the device-local account is then removed, again, no notifications are sent.
690TEST_F(CloudExternalDataPolicyObserverTest,
691       ExistingDeviceLocalAccountRemoveAccountUnset) {
692  AddDeviceLocalAccount(kDeviceLocalAccount);
693
694  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
695  ASSERT_TRUE(broker);
696  broker->external_data_manager()->Connect(NULL);
697  base::RunLoop().RunUntilIdle();
698
699  CreateObserver();
700
701  EXPECT_TRUE(set_calls_.empty());
702  EXPECT_TRUE(cleared_calls_.empty());
703  EXPECT_TRUE(fetched_calls_.empty());
704  ClearObservations();
705
706  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(0));
707
708  RemoveDeviceLocalAccount(kDeviceLocalAccount);
709
710  EXPECT_TRUE(set_calls_.empty());
711  EXPECT_TRUE(cleared_calls_.empty());
712  EXPECT_TRUE(fetched_calls_.empty());
713  ClearObservations();
714
715  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(0));
716}
717
718// Verifies that when the external data reference for a device-local account is
719// initially set, a corresponding notification is emitted and a fetch is
720// started. Further verifies that when the device-local account is then removed,
721// a notification indicating that the external data reference has been cleared
722// is emitted and the fetch is canceled.
723TEST_F(CloudExternalDataPolicyObserverTest,
724       ExistingDeviceLocalAccountRemoveAccountSet) {
725  SetDeviceLocalAccountAvatarPolicy(kDeviceLocalAccount, avatar_policy_1_);
726  AddDeviceLocalAccount(kDeviceLocalAccount);
727
728  DeviceLocalAccountPolicyBroker* broker = GetBrokerForDeviceLocalAccountUser();
729  ASSERT_TRUE(broker);
730  broker->external_data_manager()->Connect(NULL);
731  base::RunLoop().RunUntilIdle();
732
733  CreateObserver();
734
735  EXPECT_TRUE(cleared_calls_.empty());
736  EXPECT_TRUE(fetched_calls_.empty());
737  ASSERT_EQ(1u, set_calls_.size());
738  EXPECT_EQ(device_local_account_user_id_, set_calls_.front());
739  ClearObservations();
740
741  net::TestURLFetcher* fetcher = url_fetcher_factory_.GetFetcherByID(0);
742  ASSERT_TRUE(fetcher);
743  EXPECT_EQ(GURL(kAvatar1URL), fetcher->GetOriginalURL());
744
745  RemoveDeviceLocalAccount(kDeviceLocalAccount);
746
747  EXPECT_TRUE(set_calls_.empty());
748  EXPECT_TRUE(fetched_calls_.empty());
749  ASSERT_EQ(1u, cleared_calls_.size());
750  EXPECT_EQ(device_local_account_user_id_, cleared_calls_.front());
751  ClearObservations();
752
753  EXPECT_FALSE(url_fetcher_factory_.GetFetcherByID(0));
754}
755
756// Verifies that when an external data reference is set for a regular user and
757// the user logs in, a corresponding notification is emitted and a fetch is
758// started. Further verifies that when the fetch succeeds, a notification
759// containing the external data is emitted.
760TEST_F(CloudExternalDataPolicyObserverTest, RegularUserFetchSuccess) {
761  SetRegularUserAvatarPolicy(avatar_policy_1_);
762
763  CreateObserver();
764
765  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _))
766      .Times(1)
767      .WillOnce(SaveArg<1>(&fetch_callback_));
768
769  LogInAsRegularUser();
770
771  EXPECT_TRUE(cleared_calls_.empty());
772  EXPECT_TRUE(fetched_calls_.empty());
773  ASSERT_EQ(1u, set_calls_.size());
774  EXPECT_EQ(kRegularUserID, set_calls_.front());
775  ClearObservations();
776
777  Mock::VerifyAndClear(&external_data_manager_);
778  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _)).Times(0);
779
780  fetch_callback_.Run(make_scoped_ptr(new std::string(avatar_policy_1_data_)));
781
782  EXPECT_TRUE(set_calls_.empty());
783  EXPECT_TRUE(cleared_calls_.empty());
784  ASSERT_EQ(1u, fetched_calls_.size());
785  EXPECT_EQ(kRegularUserID, fetched_calls_.front().first);
786  EXPECT_EQ(avatar_policy_1_data_, fetched_calls_.front().second);
787  ClearObservations();
788}
789
790// Verifies that when the external data reference for a regular user is not set
791// while the user is logging in, no notifications are emitted. Further verifies
792// that when the external data reference is then cleared (which is a no-op),
793// again, no notifications are emitted.
794TEST_F(CloudExternalDataPolicyObserverTest, RegularUserClearUnset) {
795  CreateObserver();
796
797  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _)).Times(0);
798
799  LogInAsRegularUser();
800
801  EXPECT_TRUE(set_calls_.empty());
802  EXPECT_TRUE(cleared_calls_.empty());
803  EXPECT_TRUE(fetched_calls_.empty());
804  ClearObservations();
805
806  Mock::VerifyAndClear(&external_data_manager_);
807  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _)).Times(0);
808
809  SetRegularUserAvatarPolicy("");
810
811  EXPECT_TRUE(set_calls_.empty());
812  EXPECT_TRUE(cleared_calls_.empty());
813  EXPECT_TRUE(fetched_calls_.empty());
814  ClearObservations();
815}
816
817// Verifies that when the external data reference for a regular user is set
818// while the user is logging in, a corresponding notification is emitted and a
819// fetch is started. Further verifies that when the external data reference is
820// then cleared, a corresponding notification is emitted and no new fetch is
821// started.
822TEST_F(CloudExternalDataPolicyObserverTest, RegularUserClearSet) {
823  SetRegularUserAvatarPolicy(avatar_policy_1_);
824
825  CreateObserver();
826
827  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _))
828      .Times(1)
829      .WillOnce(SaveArg<1>(&fetch_callback_));
830
831  LogInAsRegularUser();
832
833  EXPECT_TRUE(cleared_calls_.empty());
834  EXPECT_TRUE(fetched_calls_.empty());
835  ASSERT_EQ(1u, set_calls_.size());
836  EXPECT_EQ(kRegularUserID, set_calls_.front());
837  ClearObservations();
838
839  Mock::VerifyAndClear(&external_data_manager_);
840  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _)).Times(0);
841
842  SetRegularUserAvatarPolicy("");
843
844  EXPECT_TRUE(set_calls_.empty());
845  EXPECT_TRUE(fetched_calls_.empty());
846  ASSERT_EQ(1u, cleared_calls_.size());
847  EXPECT_EQ(kRegularUserID, cleared_calls_.front());
848  ClearObservations();
849}
850
851
852// Verifies that when the external data reference for a regular user is not set
853// while the user is logging in, no notifications are emitted. Further verifies
854// that when the external data reference is then set, a corresponding
855// notification is emitted and a fetch is started. Also verifies that when the
856// fetch eventually succeeds, a notification containing the external data is
857// emitted.
858TEST_F(CloudExternalDataPolicyObserverTest, RegularUserSetUnset) {
859  CreateObserver();
860
861  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _)).Times(0);
862
863  LogInAsRegularUser();
864
865  EXPECT_TRUE(set_calls_.empty());
866  EXPECT_TRUE(cleared_calls_.empty());
867  EXPECT_TRUE(fetched_calls_.empty());
868  ClearObservations();
869
870  Mock::VerifyAndClear(&external_data_manager_);
871  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _))
872      .Times(1)
873      .WillOnce(SaveArg<1>(&fetch_callback_));
874
875  SetRegularUserAvatarPolicy(avatar_policy_1_);
876
877  EXPECT_TRUE(cleared_calls_.empty());
878  EXPECT_TRUE(fetched_calls_.empty());
879  ASSERT_EQ(1u, set_calls_.size());
880  EXPECT_EQ(kRegularUserID, set_calls_.front());
881  ClearObservations();
882
883  Mock::VerifyAndClear(&external_data_manager_);
884  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _)).Times(0);
885
886  fetch_callback_.Run(make_scoped_ptr(new std::string(avatar_policy_1_data_)));
887
888  EXPECT_TRUE(set_calls_.empty());
889  EXPECT_TRUE(cleared_calls_.empty());
890  ASSERT_EQ(1u, fetched_calls_.size());
891  EXPECT_EQ(kRegularUserID, fetched_calls_.front().first);
892  EXPECT_EQ(avatar_policy_1_data_, fetched_calls_.front().second);
893  ClearObservations();
894}
895
896// Verifies that when the external data reference for a regular user is set
897// while the user is logging in, a corresponding notification is emitted and a
898// fetch is started. Further verifies that when the external data reference is
899// then updated, a corresponding notification is emitted and the fetch is
900// restarted. Also verifies that when the fetch eventually succeeds, a
901// notification containing the external data is emitted.
902TEST_F(CloudExternalDataPolicyObserverTest, RegularUserSetSet) {
903  SetRegularUserAvatarPolicy(avatar_policy_1_);
904
905  CreateObserver();
906
907  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _))
908      .Times(1)
909      .WillOnce(SaveArg<1>(&fetch_callback_));
910
911  LogInAsRegularUser();
912
913  EXPECT_TRUE(cleared_calls_.empty());
914  EXPECT_TRUE(fetched_calls_.empty());
915  ASSERT_EQ(1u, set_calls_.size());
916  EXPECT_EQ(kRegularUserID, set_calls_.front());
917  ClearObservations();
918
919  Mock::VerifyAndClear(&external_data_manager_);
920  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _))
921      .Times(1)
922      .WillOnce(SaveArg<1>(&fetch_callback_));
923
924  SetRegularUserAvatarPolicy(avatar_policy_2_);
925
926  EXPECT_TRUE(cleared_calls_.empty());
927  EXPECT_TRUE(fetched_calls_.empty());
928  ASSERT_EQ(1u, set_calls_.size());
929  EXPECT_EQ(kRegularUserID, set_calls_.front());
930  ClearObservations();
931
932  Mock::VerifyAndClear(&external_data_manager_);
933  EXPECT_CALL(external_data_manager_, Fetch(key::kUserAvatarImage, _)).Times(0);
934
935  fetch_callback_.Run(make_scoped_ptr(new std::string(avatar_policy_2_data_)));
936
937  EXPECT_TRUE(set_calls_.empty());
938  EXPECT_TRUE(cleared_calls_.empty());
939  ASSERT_EQ(1u, fetched_calls_.size());
940  EXPECT_EQ(kRegularUserID, fetched_calls_.front().first);
941  EXPECT_EQ(avatar_policy_2_data_, fetched_calls_.front().second);
942  ClearObservations();
943}
944
945}  // namespace policy
946