OLD | NEW |
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
| 5 #include "base/prefs/pref_service.h" |
5 #include "base/strings/stringprintf.h" | 6 #include "base/strings/stringprintf.h" |
| 7 #include "chrome/browser/browser_process.h" |
| 8 #include "chrome/browser/chromeos/policy/affiliation_test_helper.h" |
6 #include "chrome/browser/chromeos/policy/browser_policy_connector_chromeos.h" | 9 #include "chrome/browser/chromeos/policy/browser_policy_connector_chromeos.h" |
7 #include "chrome/browser/chromeos/policy/device_policy_cros_browser_test.h" | 10 #include "chrome/browser/chromeos/policy/device_policy_cros_browser_test.h" |
8 #include "chrome/browser/chromeos/policy/stub_enterprise_install_attributes.h" | 11 #include "chrome/browser/chromeos/policy/stub_enterprise_install_attributes.h" |
9 #include "chrome/browser/extensions/extension_apitest.h" | 12 #include "chrome/browser/extensions/extension_apitest.h" |
10 #include "chrome/browser/net/url_request_mock_util.h" | 13 #include "chrome/browser/net/url_request_mock_util.h" |
| 14 #include "chrome/test/base/ui_test_utils.h" |
11 #include "chromeos/dbus/fake_session_manager_client.h" | 15 #include "chromeos/dbus/fake_session_manager_client.h" |
12 #include "chromeos/login/user_names.h" | 16 #include "chromeos/login/user_names.h" |
13 #include "components/policy/core/common/mock_configuration_policy_provider.h" | 17 #include "components/policy/core/common/mock_configuration_policy_provider.h" |
14 #include "components/policy/core/common/policy_types.h" | |
15 #include "components/signin/core/account_id/account_id.h" | 18 #include "components/signin/core/account_id/account_id.h" |
| 19 #include "components/user_manager/user_manager.h" |
16 #include "content/public/browser/notification_service.h" | 20 #include "content/public/browser/notification_service.h" |
17 #include "content/public/test/test_utils.h" | 21 #include "content/public/test/test_utils.h" |
18 #include "extensions/browser/api_test_utils.h" | 22 #include "extensions/browser/api_test_utils.h" |
19 #include "extensions/browser/extension_registry.h" | 23 #include "extensions/browser/extension_registry.h" |
20 #include "extensions/browser/test_extension_registry_observer.h" | 24 #include "extensions/browser/test_extension_registry_observer.h" |
| 25 #include "extensions/test/result_catcher.h" |
21 #include "net/test/url_request/url_request_mock_http_job.h" | 26 #include "net/test/url_request/url_request_mock_http_job.h" |
22 #include "policy/policy_constants.h" | 27 #include "policy/policy_constants.h" |
23 | 28 |
24 namespace { | 29 namespace { |
25 | 30 |
26 const char kDeviceId[] = "device_id"; | 31 const char kDeviceId[] = "device_id"; |
27 const base::FilePath::CharType kTestExtensionDir[] = | 32 const base::FilePath::CharType kTestExtensionDir[] = |
28 FILE_PATH_LITERAL("extensions/api_test/enterprise_device_attributes"); | 33 FILE_PATH_LITERAL("extensions/api_test/enterprise_device_attributes"); |
29 const base::FilePath::CharType kUpdateManifestFileName[] = | 34 const base::FilePath::CharType kUpdateManifestFileName[] = |
30 FILE_PATH_LITERAL("update_manifest.xml"); | 35 FILE_PATH_LITERAL("update_manifest.xml"); |
31 | 36 |
| 37 const char kAffiliatedUserEmail[] = "user@example.com"; |
| 38 const char kAffiliationID[] = "some-affiliation-id"; |
| 39 const char kAnotherAffiliationID[] = "another-affiliation-id"; |
| 40 |
32 // The managed_storage extension has a key defined in its manifest, so that | 41 // The managed_storage extension has a key defined in its manifest, so that |
33 // its extension ID is well-known and the policy system can push policies for | 42 // its extension ID is well-known and the policy system can push policies for |
34 // the extension. | 43 // the extension. |
35 const char kTestExtensionID[] = "nbiliclbejdndfpchgkbmfoppjplbdok"; | 44 const char kTestExtensionID[] = "nbiliclbejdndfpchgkbmfoppjplbdok"; |
36 | 45 |
| 46 struct Params { |
| 47 explicit Params(bool affiliated) : affiliated_(affiliated) {} |
| 48 bool affiliated_; |
| 49 }; |
| 50 |
37 } // namespace | 51 } // namespace |
38 | 52 |
39 namespace extensions { | 53 namespace extensions { |
40 | 54 |
41 class EnterpriseDeviceAttributesTest : public ExtensionApiTest { | 55 class EnterpriseDeviceAttributesTest : |
| 56 public ExtensionApiTest, |
| 57 public ::testing::WithParamInterface<Params> { |
42 public: | 58 public: |
43 explicit EnterpriseDeviceAttributesTest(const std::string& domain) | 59 EnterpriseDeviceAttributesTest() { |
44 : fake_session_manager_client_(new chromeos::FakeSessionManagerClient), | 60 set_exit_when_last_browser_closes(false); |
45 test_domain_(domain) {} | 61 set_chromeos_user_ = false; |
| 62 } |
46 | 63 |
47 protected: | 64 protected: |
| 65 // ExtensionApiTest |
| 66 void SetUpCommandLine(base::CommandLine* command_line) override { |
| 67 ExtensionApiTest::SetUpCommandLine(command_line); |
| 68 policy::affiliation_test_helper:: |
| 69 AppendCommandLineSwitchesForLoginManager(command_line); |
| 70 } |
| 71 |
48 void SetUpInProcessBrowserTestFixture() override { | 72 void SetUpInProcessBrowserTestFixture() override { |
| 73 ExtensionApiTest::SetUpInProcessBrowserTestFixture(); |
| 74 |
| 75 chromeos::FakeSessionManagerClient* fake_session_manager_client = |
| 76 new chromeos::FakeSessionManagerClient; |
49 chromeos::DBusThreadManager::GetSetterForTesting()->SetSessionManagerClient( | 77 chromeos::DBusThreadManager::GetSetterForTesting()->SetSessionManagerClient( |
50 make_scoped_ptr(fake_session_manager_client_)); | 78 scoped_ptr<chromeos::SessionManagerClient>( |
51 ExtensionApiTest::SetUpInProcessBrowserTestFixture(); | 79 fake_session_manager_client)); |
| 80 |
| 81 std::set<std::string> device_affiliation_ids; |
| 82 device_affiliation_ids.insert(kAffiliationID); |
| 83 policy::affiliation_test_helper::SetDeviceAffiliationID( |
| 84 &test_helper_, fake_session_manager_client, device_affiliation_ids); |
| 85 |
| 86 std::set<std::string> user_affiliation_ids; |
| 87 if (GetParam().affiliated_) { |
| 88 user_affiliation_ids.insert(kAffiliationID); |
| 89 } else { |
| 90 user_affiliation_ids.insert(kAnotherAffiliationID); |
| 91 } |
| 92 policy::UserPolicyBuilder user_policy; |
| 93 policy::affiliation_test_helper::SetUserAffiliationIDs( |
| 94 &user_policy, fake_session_manager_client, |
| 95 affiliated_account_id_.GetUserEmail(), user_affiliation_ids); |
52 | 96 |
53 // Set up fake install attributes. | 97 // Set up fake install attributes. |
54 scoped_ptr<policy::StubEnterpriseInstallAttributes> attributes( | 98 scoped_ptr<policy::StubEnterpriseInstallAttributes> attributes( |
55 new policy::StubEnterpriseInstallAttributes()); | 99 new policy::StubEnterpriseInstallAttributes()); |
56 | 100 |
57 attributes->SetDomain(test_domain_); | 101 attributes->SetRegistrationUser(affiliated_account_id_.GetUserEmail()); |
58 attributes->SetRegistrationUser( | |
59 chromeos::login::StubAccountId().GetUserEmail()); | |
60 policy::BrowserPolicyConnectorChromeOS::SetInstallAttributesForTesting( | 102 policy::BrowserPolicyConnectorChromeOS::SetInstallAttributesForTesting( |
61 attributes.release()); | 103 attributes.release()); |
62 | 104 |
63 test_helper_.InstallOwnerKey(); | 105 test_helper_.InstallOwnerKey(); |
64 // Init the device policy. | 106 // Init the device policy. |
65 policy::DevicePolicyBuilder* device_policy = test_helper_.device_policy(); | 107 policy::DevicePolicyBuilder* device_policy = test_helper_.device_policy(); |
66 device_policy->SetDefaultSigningKey(); | 108 device_policy->SetDefaultSigningKey(); |
67 device_policy->policy_data().set_directory_api_id(kDeviceId); | 109 device_policy->policy_data().set_directory_api_id(kDeviceId); |
68 device_policy->Build(); | 110 device_policy->Build(); |
69 | 111 |
70 fake_session_manager_client_->set_device_policy(device_policy->GetBlob()); | 112 fake_session_manager_client->set_device_policy(device_policy->GetBlob()); |
71 fake_session_manager_client_->OnPropertyChangeComplete(true); | 113 fake_session_manager_client->OnPropertyChangeComplete(true); |
72 | 114 |
73 // Init the user policy provider. | 115 // Init the user policy provider. |
74 EXPECT_CALL(policy_provider_, IsInitializationComplete(testing::_)) | 116 EXPECT_CALL(policy_provider_, IsInitializationComplete(testing::_)) |
75 .WillRepeatedly(testing::Return(true)); | 117 .WillRepeatedly(testing::Return(true)); |
76 policy_provider_.SetAutoRefresh(); | 118 policy_provider_.SetAutoRefresh(); |
77 policy::BrowserPolicyConnector::SetPolicyProviderForTesting( | 119 policy::BrowserPolicyConnector::SetPolicyProviderForTesting( |
78 &policy_provider_); | 120 &policy_provider_); |
79 } | 121 } |
80 | 122 |
81 void SetUpOnMainThread() override { | 123 void SetUpOnMainThread() override { |
| 124 const base::ListValue* users = |
| 125 g_browser_process->local_state()->GetList("LoggedInUsers"); |
| 126 if (!users->empty()) { |
| 127 policy::affiliation_test_helper::LoginUser( |
| 128 affiliated_account_id_.GetUserEmail()); |
| 129 } |
| 130 |
82 ExtensionApiTest::SetUpOnMainThread(); | 131 ExtensionApiTest::SetUpOnMainThread(); |
83 | |
84 // Enable the URLRequestMock, which is required for force-installing the | |
85 // test extension through policy. | |
86 content::BrowserThread::PostTask( | |
87 content::BrowserThread::IO, FROM_HERE, | |
88 base::Bind(chrome_browser_net::SetUrlRequestMocksEnabled, true)); | |
89 | |
90 SetPolicy(); | |
91 } | 132 } |
92 | 133 |
93 private: | |
94 void SetPolicy() { | 134 void SetPolicy() { |
95 // Extensions that are force-installed come from an update URL, which | 135 // Extensions that are force-installed come from an update URL, which |
96 // defaults to the webstore. Use a mock URL for this test with an update | 136 // defaults to the webstore. Use a mock URL for this test with an update |
97 // manifest that includes the crx file of the test extension. | 137 // manifest that includes the crx file of the test extension. |
98 base::FilePath update_manifest_path = | 138 base::FilePath update_manifest_path = |
99 base::FilePath(kTestExtensionDir).Append(kUpdateManifestFileName); | 139 base::FilePath(kTestExtensionDir).Append(kUpdateManifestFileName); |
100 GURL update_manifest_url(net::URLRequestMockHTTPJob::GetMockUrl( | 140 GURL update_manifest_url(net::URLRequestMockHTTPJob::GetMockUrl( |
101 update_manifest_path.MaybeAsASCII())); | 141 update_manifest_path.MaybeAsASCII())); |
102 | 142 |
103 scoped_ptr<base::ListValue> forcelist(new base::ListValue); | 143 scoped_ptr<base::ListValue> forcelist(new base::ListValue); |
104 forcelist->AppendString(base::StringPrintf( | 144 forcelist->AppendString(base::StringPrintf( |
105 "%s;%s", kTestExtensionID, update_manifest_url.spec().c_str())); | 145 "%s;%s", kTestExtensionID, update_manifest_url.spec().c_str())); |
106 | 146 |
107 policy::PolicyMap policy; | 147 policy::PolicyMap policy; |
108 policy.Set(policy::key::kExtensionInstallForcelist, | 148 policy.Set(policy::key::kExtensionInstallForcelist, |
109 policy::POLICY_LEVEL_MANDATORY, policy::POLICY_SCOPE_MACHINE, | 149 policy::POLICY_LEVEL_MANDATORY, policy::POLICY_SCOPE_MACHINE, |
110 policy::POLICY_SOURCE_CLOUD, forcelist.release(), nullptr); | 150 policy::POLICY_SOURCE_CLOUD, forcelist.release(), nullptr); |
111 | 151 |
112 // Set the policy and wait until the extension is installed. | 152 // Set the policy and wait until the extension is installed. |
113 extensions::TestExtensionRegistryObserver observer( | 153 extensions::TestExtensionRegistryObserver observer( |
114 ExtensionRegistry::Get(profile())); | 154 ExtensionRegistry::Get(profile())); |
115 policy_provider_.UpdateChromePolicy(policy); | 155 policy_provider_.UpdateChromePolicy(policy); |
116 observer.WaitForExtensionLoaded(); | 156 observer.WaitForExtensionLoaded(); |
117 } | 157 } |
118 | 158 |
119 chromeos::FakeSessionManagerClient* const fake_session_manager_client_; | 159 // Load |page_url| in |browser| and wait for PASSED or FAILED notification. |
| 160 // The functionality of this function is reduced functionality of |
| 161 // RunExtensionSubtest(), but we don't use it here because it requires |
| 162 // function InProcessBrowserTest::browser() to return non-NULL pointer. |
| 163 // Unfortunately it returns the value which is set in constructor and can't be |
| 164 // modified. Because on login flow there is no browser, the function |
| 165 // InProcessBrowserTest::browser() always returns NULL. Besides this we need |
| 166 // only very little functionality from RunExtensionSubtest(). Thus so that |
| 167 // don't make RunExtensionSubtest() to complex we just introduce a new |
| 168 // function. |
| 169 bool TestExtension(Browser* browser, const std::string& page_url) { |
| 170 DCHECK(!page_url.empty()) << "page_url cannot be empty"; |
| 171 |
| 172 extensions::ResultCatcher catcher; |
| 173 ui_test_utils::NavigateToURL(browser, GURL(page_url)); |
| 174 |
| 175 if (!catcher.GetNextResult()) { |
| 176 message_ = catcher.message(); |
| 177 return false; |
| 178 } |
| 179 return true; |
| 180 } |
| 181 |
| 182 const AccountId affiliated_account_id_ = |
| 183 AccountId::FromUserEmail(kAffiliatedUserEmail); |
| 184 |
| 185 private: |
120 policy::MockConfigurationPolicyProvider policy_provider_; | 186 policy::MockConfigurationPolicyProvider policy_provider_; |
121 policy::DevicePolicyCrosTestHelper test_helper_; | 187 policy::DevicePolicyCrosTestHelper test_helper_; |
122 const std::string test_domain_; | |
123 }; | 188 }; |
124 | 189 |
125 // Creates affiliated user before browser initializes. | 190 IN_PROC_BROWSER_TEST_P(EnterpriseDeviceAttributesTest, PRE_Success) { |
126 class EnterpriseDeviceAttributesAffiliatedTest | 191 policy::affiliation_test_helper::PreLoginUser( |
127 : public EnterpriseDeviceAttributesTest { | 192 affiliated_account_id_.GetUserEmail()); |
128 public: | 193 } |
129 EnterpriseDeviceAttributesAffiliatedTest() | |
130 : EnterpriseDeviceAttributesTest("gmail.com") {} | |
131 }; | |
132 | 194 |
133 // Creates non-affiliated user before browser init. | 195 IN_PROC_BROWSER_TEST_P(EnterpriseDeviceAttributesTest, Success) { |
134 class EnterpriseDeviceAttributesNonAffiliatedTest | 196 content::BrowserThread::PostTask( |
135 : public EnterpriseDeviceAttributesTest { | 197 content::BrowserThread::IO, FROM_HERE, |
136 public: | 198 base::Bind(chrome_browser_net::SetUrlRequestMocksEnabled, true)); |
137 EnterpriseDeviceAttributesNonAffiliatedTest() | |
138 : EnterpriseDeviceAttributesTest("example.com") {} | |
139 }; | |
140 | 199 |
141 // Tests the case of an affiliated user and pre-installed extension. Fetches | 200 SetPolicy(); |
142 // the valid cloud directory device id. | 201 |
143 IN_PROC_BROWSER_TEST_F(EnterpriseDeviceAttributesAffiliatedTest, Success) { | 202 EXPECT_EQ(GetParam().affiliated_, user_manager::UserManager::Get()-> |
| 203 FindUser(affiliated_account_id_)->is_affiliated()); |
| 204 |
| 205 // Device ID is available only for affiliated user. |
| 206 std::string device_id = GetParam().affiliated_ ? kDeviceId : ""; |
| 207 |
144 // Pass the expected value (device_id) to test. | 208 // Pass the expected value (device_id) to test. |
145 ASSERT_TRUE(RunExtensionSubtest( | 209 ASSERT_TRUE(TestExtension(CreateBrowser(profile()), |
146 "", base::StringPrintf("chrome-extension://%s/basic.html?%s", | 210 base::StringPrintf("chrome-extension://%s/basic.html?%s", |
147 kTestExtensionID, kDeviceId))) | 211 kTestExtensionID, device_id.c_str()))) |
148 << message_; | 212 << message_; |
149 } | 213 } |
150 | 214 |
151 // Test the case of non-affiliated user and pre-installed by policy extension. | |
152 // Extension API is available, but fetches the empty string. | |
153 IN_PROC_BROWSER_TEST_F(EnterpriseDeviceAttributesNonAffiliatedTest, | |
154 EmptyString) { | |
155 // Pass the expected value (empty string) to test. | |
156 ASSERT_TRUE(RunExtensionSubtest( | |
157 "", base::StringPrintf("chrome-extension://%s/basic.html?%s", | |
158 kTestExtensionID, ""))) | |
159 << message_; | |
160 } | |
161 | |
162 // Ensure that extensions that are not pre-installed by policy throw an install | 215 // Ensure that extensions that are not pre-installed by policy throw an install |
163 // warning if they request the enterprise.deviceAttributes permission in the | 216 // warning if they request the enterprise.deviceAttributes permission in the |
164 // manifest and that such extensions don't see the | 217 // manifest and that such extensions don't see the |
165 // chrome.enterprise.deviceAttributes namespace. | 218 // chrome.enterprise.deviceAttributes namespace. |
166 IN_PROC_BROWSER_TEST_F( | 219 IN_PROC_BROWSER_TEST_F( |
167 ExtensionApiTest, | 220 ExtensionApiTest, |
168 EnterpriseDeviceAttributesIsRestrictedToPolicyExtension) { | 221 EnterpriseDeviceAttributesIsRestrictedToPolicyExtension) { |
169 ASSERT_TRUE(RunExtensionSubtest("enterprise_device_attributes", | 222 ASSERT_TRUE(RunExtensionSubtest("enterprise_device_attributes", |
170 "api_not_available.html", | 223 "api_not_available.html", |
171 kFlagIgnoreManifestWarnings)); | 224 kFlagIgnoreManifestWarnings)); |
172 | 225 |
173 base::FilePath extension_path = | 226 base::FilePath extension_path = |
174 test_data_dir_.AppendASCII("enterprise_device_attributes"); | 227 test_data_dir_.AppendASCII("enterprise_device_attributes"); |
175 extensions::ExtensionRegistry* registry = | 228 extensions::ExtensionRegistry* registry = |
176 extensions::ExtensionRegistry::Get(profile()); | 229 extensions::ExtensionRegistry::Get(profile()); |
177 const extensions::Extension* extension = | 230 const extensions::Extension* extension = |
178 GetExtensionByPath(registry->enabled_extensions(), extension_path); | 231 GetExtensionByPath(registry->enabled_extensions(), extension_path); |
179 ASSERT_FALSE(extension->install_warnings().empty()); | 232 ASSERT_FALSE(extension->install_warnings().empty()); |
180 EXPECT_EQ( | 233 EXPECT_EQ( |
181 "'enterprise.deviceAttributes' is not allowed for specified install " | 234 "'enterprise.deviceAttributes' is not allowed for specified install " |
182 "location.", | 235 "location.", |
183 extension->install_warnings()[0].message); | 236 extension->install_warnings()[0].message); |
184 } | 237 } |
185 | 238 |
| 239 // Both cases of affiliated and non-affiliated on the device user are tested. |
| 240 INSTANTIATE_TEST_CASE_P(AffiliationCheck, |
| 241 EnterpriseDeviceAttributesTest, |
| 242 ::testing::Values(Params(true), Params(false))); |
186 } // namespace extensions | 243 } // namespace extensions |
OLD | NEW |