Disable view source for Developer Tools.
[chromium-blink-merge.git] / chrome / browser / chromeos / policy / network_configuration_updater_unittest.cc
blobdcb55edfac60dcb38eb1b4b80a453594935e220a
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.
5 #include "base/bind.h"
6 #include "base/bind_helpers.h"
7 #include "base/callback.h"
8 #include "base/files/file_path.h"
9 #include "base/memory/scoped_ptr.h"
10 #include "base/run_loop.h"
11 #include "base/values.h"
12 #include "chrome/browser/chromeos/login/user.h"
13 #include "chrome/browser/chromeos/policy/device_network_configuration_updater.h"
14 #include "chrome/browser/chromeos/policy/user_network_configuration_updater.h"
15 #include "chrome/browser/chromeos/settings/cros_settings.h"
16 #include "chrome/browser/chromeos/settings/device_settings_service.h"
17 #include "chrome/browser/chromeos/settings/stub_cros_settings_provider.h"
18 #include "chromeos/network/fake_network_device_handler.h"
19 #include "chromeos/network/mock_managed_network_configuration_handler.h"
20 #include "chromeos/network/onc/mock_certificate_importer.h"
21 #include "chromeos/network/onc/onc_test_utils.h"
22 #include "chromeos/network/onc/onc_utils.h"
23 #include "components/onc/onc_constants.h"
24 #include "components/policy/core/common/external_data_fetcher.h"
25 #include "components/policy/core/common/mock_configuration_policy_provider.h"
26 #include "components/policy/core/common/policy_map.h"
27 #include "components/policy/core/common/policy_service_impl.h"
28 #include "content/public/test/test_browser_thread_bundle.h"
29 #include "content/public/test/test_utils.h"
30 #include "net/base/test_data_directory.h"
31 #include "net/cert/x509_certificate.h"
32 #include "net/test/cert_test_util.h"
33 #include "policy/policy_constants.h"
34 #include "testing/gmock/include/gmock/gmock.h"
35 #include "testing/gtest/include/gtest/gtest.h"
37 using testing::AnyNumber;
38 using testing::AtLeast;
39 using testing::Mock;
40 using testing::Ne;
41 using testing::Return;
42 using testing::StrictMock;
43 using testing::_;
45 namespace policy {
47 namespace {
49 const char kFakeUserEmail[] = "fake email";
50 const char kFakeUsernameHash[] = "fake hash";
52 class FakeUser : public chromeos::User {
53 public:
54 FakeUser() : User(kFakeUserEmail) {
55 set_display_email(kFakeUserEmail);
56 set_username_hash(kFakeUsernameHash);
58 virtual ~FakeUser() {}
60 // User overrides
61 virtual UserType GetType() const OVERRIDE {
62 return USER_TYPE_REGULAR;
65 private:
66 DISALLOW_COPY_AND_ASSIGN(FakeUser);
69 class FakeWebTrustedCertsObserver
70 : public UserNetworkConfigurationUpdater::WebTrustedCertsObserver {
71 public:
72 virtual void OnTrustAnchorsChanged(
73 const net::CertificateList& trust_anchors) OVERRIDE {
74 trust_anchors_ = trust_anchors;
76 net::CertificateList trust_anchors_;
79 class FakeNetworkDeviceHandler : public chromeos::FakeNetworkDeviceHandler {
80 public:
81 FakeNetworkDeviceHandler() : allow_roaming_(false) {}
83 virtual void SetCellularAllowRoaming(bool allow_roaming) OVERRIDE {
84 allow_roaming_ = allow_roaming;
87 bool allow_roaming_;
90 const char kFakeONC[] =
91 "{ \"NetworkConfigurations\": ["
92 " { \"GUID\": \"{485d6076-dd44-6b6d-69787465725f5040}\","
93 " \"Type\": \"WiFi\","
94 " \"Name\": \"My WiFi Network\","
95 " \"WiFi\": {"
96 " \"SSID\": \"ssid-none\","
97 " \"Security\": \"None\" }"
98 " }"
99 " ],"
100 " \"GlobalNetworkConfiguration\": {"
101 " \"AllowOnlyPolicyNetworksToAutoconnect\": true,"
102 " },"
103 " \"Certificates\": ["
104 " { \"GUID\": \"{f998f760-272b-6939-4c2beffe428697ac}\","
105 " \"PKCS12\": \"abc\","
106 " \"Type\": \"Client\" }"
107 " ],"
108 " \"Type\": \"UnencryptedConfiguration\""
109 "}";
111 std::string ValueToString(const base::Value& value) {
112 std::stringstream str;
113 str << value;
114 return str.str();
117 void AppendAll(const base::ListValue& from, base::ListValue* to) {
118 for (base::ListValue::const_iterator it = from.begin(); it != from.end();
119 ++it) {
120 to->Append((*it)->DeepCopy());
124 // Matcher to match base::Value.
125 MATCHER_P(IsEqualTo,
126 value,
127 std::string(negation ? "isn't" : "is") + " equal to " +
128 ValueToString(*value)) {
129 return value->Equals(&arg);
132 MATCHER(IsEmpty, std::string(negation ? "isn't" : "is") + " empty.") {
133 return arg.empty();
136 ACTION_P(SetCertificateList, list) {
137 if (arg2)
138 *arg2 = list;
139 return true;
142 } // namespace
144 class NetworkConfigurationUpdaterTest : public testing::Test {
145 protected:
146 NetworkConfigurationUpdaterTest() {
149 virtual void SetUp() OVERRIDE {
150 EXPECT_CALL(provider_, IsInitializationComplete(_))
151 .WillRepeatedly(Return(true));
152 provider_.Init();
153 PolicyServiceImpl::Providers providers;
154 providers.push_back(&provider_);
155 policy_service_.reset(new PolicyServiceImpl(providers));
157 scoped_ptr<base::DictionaryValue> fake_toplevel_onc =
158 chromeos::onc::ReadDictionaryFromJson(kFakeONC);
160 base::ListValue* network_configs = NULL;
161 fake_toplevel_onc->GetListWithoutPathExpansion(
162 onc::toplevel_config::kNetworkConfigurations, &network_configs);
163 AppendAll(*network_configs, &fake_network_configs_);
165 base::DictionaryValue* global_config = NULL;
166 fake_toplevel_onc->GetDictionaryWithoutPathExpansion(
167 onc::toplevel_config::kGlobalNetworkConfiguration, &global_config);
168 fake_global_network_config_.MergeDictionary(global_config);
170 base::ListValue* certs = NULL;
171 fake_toplevel_onc->GetListWithoutPathExpansion(
172 onc::toplevel_config::kCertificates, &certs);
173 AppendAll(*certs, &fake_certificates_);
175 certificate_importer_ =
176 new StrictMock<chromeos::onc::MockCertificateImporter>();
177 certificate_importer_owned_.reset(certificate_importer_);
180 virtual void TearDown() OVERRIDE {
181 network_configuration_updater_.reset();
182 provider_.Shutdown();
183 base::RunLoop().RunUntilIdle();
186 void UpdateProviderPolicy(const PolicyMap& policy) {
187 provider_.UpdateChromePolicy(policy);
188 base::RunLoop().RunUntilIdle();
191 UserNetworkConfigurationUpdater*
192 CreateNetworkConfigurationUpdaterForUserPolicy(
193 bool allow_trusted_certs_from_policy) {
194 UserNetworkConfigurationUpdater* updater =
195 UserNetworkConfigurationUpdater::CreateForUserPolicy(
196 allow_trusted_certs_from_policy,
197 fake_user_,
198 certificate_importer_owned_.Pass(),
199 policy_service_.get(),
200 &network_config_handler_).release();
201 network_configuration_updater_.reset(updater);
202 return updater;
205 void CreateNetworkConfigurationUpdaterForDevicePolicy() {
206 network_configuration_updater_ =
207 DeviceNetworkConfigurationUpdater::CreateForDevicePolicy(
208 certificate_importer_owned_.Pass(),
209 policy_service_.get(),
210 &network_config_handler_,
211 &network_device_handler_,
212 chromeos::CrosSettings::Get());
215 base::ListValue fake_network_configs_;
216 base::DictionaryValue fake_global_network_config_;
217 base::ListValue fake_certificates_;
218 StrictMock<chromeos::MockManagedNetworkConfigurationHandler>
219 network_config_handler_;
220 FakeNetworkDeviceHandler network_device_handler_;
222 // Not used directly. Required for CrosSettings.
223 chromeos::ScopedTestDeviceSettingsService scoped_device_settings_service_;
224 chromeos::ScopedTestCrosSettings scoped_cros_settings_;
226 // Ownership of certificate_importer_owned_ is passed to the
227 // NetworkConfigurationUpdater. When that happens, |certificate_importer_|
228 // continues to point to that instance but |certificate_importer_owned_| is
229 // released.
230 StrictMock<chromeos::onc::MockCertificateImporter>* certificate_importer_;
231 scoped_ptr<chromeos::onc::CertificateImporter> certificate_importer_owned_;
233 StrictMock<MockConfigurationPolicyProvider> provider_;
234 scoped_ptr<PolicyServiceImpl> policy_service_;
235 FakeUser fake_user_;
237 scoped_ptr<NetworkConfigurationUpdater> network_configuration_updater_;
238 content::TestBrowserThreadBundle thread_bundle_;
241 TEST_F(NetworkConfigurationUpdaterTest, CellularAllowRoaming) {
242 // Ignore networ config updates.
243 EXPECT_CALL(network_config_handler_, SetPolicy(_, _, _, _)).Times(AtLeast(1));
244 EXPECT_CALL(*certificate_importer_, ImportCertificates(_, _, _))
245 .Times(AtLeast(1));
247 // Setup the DataRoaming device setting.
248 chromeos::CrosSettings* cros_settings = chromeos::CrosSettings::Get();
249 chromeos::CrosSettingsProvider* device_settings_provider =
250 cros_settings->GetProvider(chromeos::kSignedDataRoamingEnabled);
251 cros_settings->RemoveSettingsProvider(device_settings_provider);
252 delete device_settings_provider;
253 chromeos::StubCrosSettingsProvider* stub_settings_provider =
254 new chromeos::StubCrosSettingsProvider;
255 cros_settings->AddSettingsProvider(stub_settings_provider);
257 chromeos::CrosSettings::Get()->Set(chromeos::kSignedDataRoamingEnabled,
258 base::FundamentalValue(false));
259 EXPECT_FALSE(network_device_handler_.allow_roaming_);
261 CreateNetworkConfigurationUpdaterForDevicePolicy();
262 chromeos::CrosSettings::Get()->Set(chromeos::kSignedDataRoamingEnabled,
263 base::FundamentalValue(true));
264 EXPECT_TRUE(network_device_handler_.allow_roaming_);
266 chromeos::CrosSettings::Get()->Set(chromeos::kSignedDataRoamingEnabled,
267 base::FundamentalValue(false));
268 EXPECT_FALSE(network_device_handler_.allow_roaming_);
271 TEST_F(NetworkConfigurationUpdaterTest, PolicyIsValidatedAndRepaired) {
272 scoped_ptr<base::DictionaryValue> onc_repaired =
273 chromeos::onc::test_utils::ReadTestDictionary(
274 "repaired_toplevel_partially_invalid.onc");
276 base::ListValue* network_configs_repaired = NULL;
277 onc_repaired->GetListWithoutPathExpansion(
278 onc::toplevel_config::kNetworkConfigurations, &network_configs_repaired);
279 ASSERT_TRUE(network_configs_repaired);
281 base::DictionaryValue* global_config_repaired = NULL;
282 onc_repaired->GetDictionaryWithoutPathExpansion(
283 onc::toplevel_config::kGlobalNetworkConfiguration,
284 &global_config_repaired);
285 ASSERT_TRUE(global_config_repaired);
287 std::string onc_policy =
288 chromeos::onc::test_utils::ReadTestData("toplevel_partially_invalid.onc");
289 PolicyMap policy;
290 policy.Set(key::kOpenNetworkConfiguration,
291 POLICY_LEVEL_MANDATORY,
292 POLICY_SCOPE_USER,
293 new base::StringValue(onc_policy),
294 NULL);
295 UpdateProviderPolicy(policy);
297 EXPECT_CALL(network_config_handler_,
298 SetPolicy(onc::ONC_SOURCE_USER_POLICY,
300 IsEqualTo(network_configs_repaired),
301 IsEqualTo(global_config_repaired)));
302 EXPECT_CALL(*certificate_importer_,
303 ImportCertificates(_, onc::ONC_SOURCE_USER_POLICY, _));
305 CreateNetworkConfigurationUpdaterForUserPolicy(
306 false /* do not allow trusted certs from policy */ );
309 TEST_F(NetworkConfigurationUpdaterTest,
310 DoNotAllowTrustedCertificatesFromPolicy) {
311 net::CertificateList cert_list;
312 cert_list =
313 net::CreateCertificateListFromFile(net::GetTestCertsDirectory(),
314 "ok_cert.pem",
315 net::X509Certificate::FORMAT_AUTO);
316 ASSERT_EQ(1u, cert_list.size());
318 EXPECT_CALL(network_config_handler_,
319 SetPolicy(onc::ONC_SOURCE_USER_POLICY, _, _, _));
320 EXPECT_CALL(*certificate_importer_, ImportCertificates(_, _, _))
321 .WillRepeatedly(SetCertificateList(cert_list));
323 UserNetworkConfigurationUpdater* updater =
324 CreateNetworkConfigurationUpdaterForUserPolicy(
325 false /* do not allow trusted certs from policy */);
327 // Certificates with the "Web" trust flag set should not be forwarded to
328 // observers.
329 FakeWebTrustedCertsObserver observer;
330 updater->AddTrustedCertsObserver(&observer);
332 base::RunLoop().RunUntilIdle();
334 net::CertificateList trust_anchors;
335 updater->GetWebTrustedCertificates(&trust_anchors);
336 EXPECT_TRUE(trust_anchors.empty());
338 EXPECT_TRUE(observer.trust_anchors_.empty());
339 updater->RemoveTrustedCertsObserver(&observer);
342 TEST_F(NetworkConfigurationUpdaterTest,
343 AllowTrustedCertificatesFromPolicyInitially) {
344 // Ignore network configuration changes.
345 EXPECT_CALL(network_config_handler_, SetPolicy(_, _, _, _))
346 .Times(AnyNumber());
348 net::CertificateList cert_list;
349 cert_list =
350 net::CreateCertificateListFromFile(net::GetTestCertsDirectory(),
351 "ok_cert.pem",
352 net::X509Certificate::FORMAT_AUTO);
353 ASSERT_EQ(1u, cert_list.size());
355 EXPECT_CALL(*certificate_importer_,
356 ImportCertificates(_, onc::ONC_SOURCE_USER_POLICY, _))
357 .WillRepeatedly(SetCertificateList(cert_list));
359 UserNetworkConfigurationUpdater* updater =
360 CreateNetworkConfigurationUpdaterForUserPolicy(
361 true /* allow trusted certs from policy */);
363 base::RunLoop().RunUntilIdle();
365 // Certificates with the "Web" trust flag set will be returned.
366 net::CertificateList trust_anchors;
367 updater->GetWebTrustedCertificates(&trust_anchors);
368 EXPECT_EQ(1u, trust_anchors.size());
371 TEST_F(NetworkConfigurationUpdaterTest,
372 AllowTrustedCertificatesFromPolicyOnUpdate) {
373 // Ignore network configuration changes.
374 EXPECT_CALL(network_config_handler_, SetPolicy(_, _, _, _))
375 .Times(AnyNumber());
377 // Start with an empty certificate list.
378 EXPECT_CALL(*certificate_importer_,
379 ImportCertificates(_, onc::ONC_SOURCE_USER_POLICY, _))
380 .WillRepeatedly(SetCertificateList(net::CertificateList()));
382 UserNetworkConfigurationUpdater* updater =
383 CreateNetworkConfigurationUpdaterForUserPolicy(
384 true /* allow trusted certs from policy */);
386 FakeWebTrustedCertsObserver observer;
387 updater->AddTrustedCertsObserver(&observer);
389 base::RunLoop().RunUntilIdle();
391 // Verify that the returned certificate list is empty.
392 Mock::VerifyAndClearExpectations(certificate_importer_);
394 net::CertificateList trust_anchors;
395 updater->GetWebTrustedCertificates(&trust_anchors);
396 EXPECT_TRUE(trust_anchors.empty());
398 EXPECT_TRUE(observer.trust_anchors_.empty());
400 // Now use a non-empty certificate list to test the observer notification.
401 net::CertificateList cert_list;
402 cert_list =
403 net::CreateCertificateListFromFile(net::GetTestCertsDirectory(),
404 "ok_cert.pem",
405 net::X509Certificate::FORMAT_AUTO);
406 ASSERT_EQ(1u, cert_list.size());
408 EXPECT_CALL(*certificate_importer_,
409 ImportCertificates(_, onc::ONC_SOURCE_USER_POLICY, _))
410 .WillOnce(SetCertificateList(cert_list));
412 // Change to any non-empty policy, so that updates are triggered. The actual
413 // content of the policy is irrelevant.
414 PolicyMap policy;
415 policy.Set(key::kOpenNetworkConfiguration,
416 POLICY_LEVEL_MANDATORY,
417 POLICY_SCOPE_USER,
418 new base::StringValue(kFakeONC),
419 NULL);
420 UpdateProviderPolicy(policy);
421 base::RunLoop().RunUntilIdle();
423 // Certificates with the "Web" trust flag set will be returned and forwarded
424 // to observers.
426 net::CertificateList trust_anchors;
427 updater->GetWebTrustedCertificates(&trust_anchors);
428 EXPECT_EQ(1u, trust_anchors.size());
430 EXPECT_EQ(1u, observer.trust_anchors_.size());
432 updater->RemoveTrustedCertsObserver(&observer);
435 class NetworkConfigurationUpdaterTestWithParam
436 : public NetworkConfigurationUpdaterTest,
437 public testing::WithParamInterface<const char*> {
438 protected:
439 // Returns the currently tested ONC source.
440 onc::ONCSource CurrentONCSource() {
441 if (GetParam() == key::kOpenNetworkConfiguration)
442 return onc::ONC_SOURCE_USER_POLICY;
443 DCHECK(GetParam() == key::kDeviceOpenNetworkConfiguration);
444 return onc::ONC_SOURCE_DEVICE_POLICY;
447 // Returns the expected username hash to push policies to
448 // ManagedNetworkConfigurationHandler.
449 std::string ExpectedUsernameHash() {
450 if (GetParam() == key::kOpenNetworkConfiguration)
451 return kFakeUsernameHash;
452 return std::string();
455 void CreateNetworkConfigurationUpdater() {
456 if (GetParam() == key::kOpenNetworkConfiguration) {
457 CreateNetworkConfigurationUpdaterForUserPolicy(
458 false /* do not allow trusted certs from policy */);
459 } else {
460 CreateNetworkConfigurationUpdaterForDevicePolicy();
465 TEST_P(NetworkConfigurationUpdaterTestWithParam, InitialUpdates) {
466 PolicyMap policy;
467 policy.Set(GetParam(), POLICY_LEVEL_MANDATORY, POLICY_SCOPE_USER,
468 new base::StringValue(kFakeONC), NULL);
469 UpdateProviderPolicy(policy);
471 EXPECT_CALL(network_config_handler_,
472 SetPolicy(CurrentONCSource(),
473 ExpectedUsernameHash(),
474 IsEqualTo(&fake_network_configs_),
475 IsEqualTo(&fake_global_network_config_)));
476 EXPECT_CALL(*certificate_importer_,
477 ImportCertificates(
478 IsEqualTo(&fake_certificates_), CurrentONCSource(), _));
480 CreateNetworkConfigurationUpdater();
484 TEST_P(NetworkConfigurationUpdaterTestWithParam, PolicyChange) {
485 // Ignore the initial updates.
486 EXPECT_CALL(network_config_handler_, SetPolicy(_, _, _, _)).Times(AtLeast(1));
487 EXPECT_CALL(*certificate_importer_, ImportCertificates(_, _, _))
488 .Times(AtLeast(1));
489 CreateNetworkConfigurationUpdater();
490 Mock::VerifyAndClearExpectations(&network_config_handler_);
491 Mock::VerifyAndClearExpectations(certificate_importer_);
493 // The Updater should update if policy changes.
494 EXPECT_CALL(network_config_handler_,
495 SetPolicy(CurrentONCSource(),
497 IsEqualTo(&fake_network_configs_),
498 IsEqualTo(&fake_global_network_config_)));
499 EXPECT_CALL(*certificate_importer_,
500 ImportCertificates(
501 IsEqualTo(&fake_certificates_), CurrentONCSource(), _));
503 PolicyMap policy;
504 policy.Set(GetParam(), POLICY_LEVEL_MANDATORY, POLICY_SCOPE_USER,
505 new base::StringValue(kFakeONC), NULL);
506 UpdateProviderPolicy(policy);
507 Mock::VerifyAndClearExpectations(&network_config_handler_);
508 Mock::VerifyAndClearExpectations(certificate_importer_);
510 // Another update is expected if the policy goes away.
511 EXPECT_CALL(network_config_handler_,
512 SetPolicy(CurrentONCSource(), _, IsEmpty(), IsEmpty()));
513 EXPECT_CALL(*certificate_importer_,
514 ImportCertificates(IsEmpty(), CurrentONCSource(), _));
516 policy.Erase(GetParam());
517 UpdateProviderPolicy(policy);
520 INSTANTIATE_TEST_CASE_P(NetworkConfigurationUpdaterTestWithParamInstance,
521 NetworkConfigurationUpdaterTestWithParam,
522 testing::Values(key::kDeviceOpenNetworkConfiguration,
523 key::kOpenNetworkConfiguration));
525 } // namespace policy