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 <algorithm> 6 #include <cstdlib> 7 #include <map> 8 #include <sstream> 9 #include <string> 10 #include <vector> 11 12 #include "base/basictypes.h" 13 #include "base/file_util.h" 14 #include "base/files/file_path.h" 15 #include "base/json/json_reader.h" 16 #include "base/logging.h" 17 #include "base/memory/scoped_ptr.h" 18 #include "base/memory/scoped_vector.h" 19 #include "base/memory/weak_ptr.h" 20 #include "base/prefs/pref_service.h" 21 #include "base/run_loop.h" 22 #include "base/stl_util.h" 23 #include "base/strings/string_util.h" 24 #include "base/strings/utf_string_conversions.h" 25 #include "base/values.h" 26 #include "chrome/browser/browser_process.h" 27 #include "chrome/browser/profiles/profile.h" 28 #include "chrome/browser/search_engines/template_url_service_factory.h" 29 #include "chrome/browser/ui/browser.h" 30 #include "chrome/browser/ui/tabs/tab_strip_model.h" 31 #include "chrome/test/base/in_process_browser_test.h" 32 #include "chrome/test/base/ui_test_utils.h" 33 #include "components/policy/core/browser/browser_policy_connector.h" 34 #include "components/policy/core/common/external_data_fetcher.h" 35 #include "components/policy/core/common/external_data_manager.h" 36 #include "components/policy/core/common/mock_configuration_policy_provider.h" 37 #include "components/policy/core/common/policy_details.h" 38 #include "components/policy/core/common/policy_map.h" 39 #include "components/policy/core/common/schema.h" 40 #include "content/public/browser/web_contents.h" 41 #include "content/public/test/browser_test_utils.h" 42 #include "policy/policy_constants.h" 43 #include "testing/gmock/include/gmock/gmock.h" 44 #include "testing/gtest/include/gtest/gtest.h" 45 #include "url/gurl.h" 46 47 using testing::Return; 48 using testing::_; 49 50 namespace policy { 51 52 namespace { 53 54 const char kMainSettingsPage[] = "chrome://settings-frame"; 55 56 const char kCrosSettingsPrefix[] = "cros."; 57 58 std::string GetPolicyName(const std::string& policy_name_decorated) { 59 const size_t offset = policy_name_decorated.find('.'); 60 if (offset != std::string::npos) 61 return policy_name_decorated.substr(0, offset); 62 return policy_name_decorated; 63 } 64 65 // Contains the details of a single test case verifying that the controlled 66 // setting indicators for a pref affected by a policy work correctly. This is 67 // part of the data loaded from chrome/test/data/policy/policy_test_cases.json. 68 class IndicatorTestCase { 69 public: 70 IndicatorTestCase(const base::DictionaryValue& policy, 71 const std::string& value, 72 bool readonly) 73 : policy_(policy.DeepCopy()), value_(value), readonly_(readonly) {} 74 ~IndicatorTestCase() {} 75 76 const base::DictionaryValue& policy() const { return *policy_; } 77 78 const std::string& value() const { return value_; } 79 80 bool readonly() const { return readonly_; } 81 82 private: 83 scoped_ptr<base::DictionaryValue> policy_; 84 std::string value_; 85 bool readonly_; 86 87 DISALLOW_COPY_AND_ASSIGN(IndicatorTestCase); 88 }; 89 90 // Contains the testing details for a single pref affected by a policy. This is 91 // part of the data loaded from chrome/test/data/policy/policy_test_cases.json. 92 class PrefMapping { 93 public: 94 PrefMapping(const std::string& pref, 95 bool is_local_state, 96 bool check_for_mandatory, 97 bool check_for_recommended, 98 const std::string& indicator_test_setup_js, 99 const std::string& indicator_selector) 100 : pref_(pref), 101 is_local_state_(is_local_state), 102 check_for_mandatory_(check_for_mandatory), 103 check_for_recommended_(check_for_recommended), 104 indicator_test_setup_js_(indicator_test_setup_js), 105 indicator_selector_(indicator_selector) {} 106 ~PrefMapping() {} 107 108 const std::string& pref() const { return pref_; } 109 110 bool is_local_state() const { return is_local_state_; } 111 112 bool check_for_mandatory() const { return check_for_mandatory_; } 113 114 bool check_for_recommended() const { return check_for_recommended_; } 115 116 const std::string& indicator_test_setup_js() const { 117 return indicator_test_setup_js_; 118 } 119 120 const std::string& indicator_selector() const { 121 return indicator_selector_; 122 } 123 124 const ScopedVector<IndicatorTestCase>& indicator_test_cases() const { 125 return indicator_test_cases_; 126 } 127 void AddIndicatorTestCase(IndicatorTestCase* test_case) { 128 indicator_test_cases_.push_back(test_case); 129 } 130 131 private: 132 const std::string pref_; 133 const bool is_local_state_; 134 const bool check_for_mandatory_; 135 const bool check_for_recommended_; 136 const std::string indicator_test_setup_js_; 137 const std::string indicator_selector_; 138 ScopedVector<IndicatorTestCase> indicator_test_cases_; 139 140 DISALLOW_COPY_AND_ASSIGN(PrefMapping); 141 }; 142 143 // Contains the testing details for a single policy. This is part of the data 144 // loaded from chrome/test/data/policy/policy_test_cases.json. 145 class PolicyTestCase { 146 public: 147 PolicyTestCase(const std::string& name, 148 bool is_official_only, 149 bool can_be_recommended, 150 const std::string& indicator_selector) 151 : name_(name), 152 is_official_only_(is_official_only), 153 can_be_recommended_(can_be_recommended), 154 indicator_selector_(indicator_selector) {} 155 ~PolicyTestCase() {} 156 157 const std::string& name() const { return name_; } 158 159 bool is_official_only() const { return is_official_only_; } 160 161 bool can_be_recommended() const { return can_be_recommended_; } 162 163 bool IsOsSupported() const { 164 #if defined(OS_WIN) 165 const std::string os("win"); 166 #elif defined(OS_MACOSX) 167 const std::string os("mac"); 168 #elif defined(OS_CHROMEOS) 169 const std::string os("chromeos"); 170 #elif defined(OS_LINUX) 171 const std::string os("linux"); 172 #else 173 #error "Unknown platform" 174 #endif 175 return std::find(supported_os_.begin(), supported_os_.end(), os) != 176 supported_os_.end(); 177 } 178 void AddSupportedOs(const std::string& os) { supported_os_.push_back(os); } 179 180 bool IsSupported() const { 181 #if !defined(OFFICIAL_BUILD) 182 if (is_official_only()) 183 return false; 184 #endif 185 return IsOsSupported(); 186 } 187 188 const base::DictionaryValue& test_policy() const { return test_policy_; } 189 void SetTestPolicy(const base::DictionaryValue& policy) { 190 test_policy_.Clear(); 191 test_policy_.MergeDictionary(&policy); 192 } 193 194 const ScopedVector<PrefMapping>& pref_mappings() const { 195 return pref_mappings_; 196 } 197 void AddPrefMapping(PrefMapping* pref_mapping) { 198 pref_mappings_.push_back(pref_mapping); 199 } 200 201 const std::string& indicator_selector() const { return indicator_selector_; } 202 203 private: 204 std::string name_; 205 bool is_official_only_; 206 bool can_be_recommended_; 207 std::vector<std::string> supported_os_; 208 base::DictionaryValue test_policy_; 209 ScopedVector<PrefMapping> pref_mappings_; 210 std::string indicator_selector_; 211 212 DISALLOW_COPY_AND_ASSIGN(PolicyTestCase); 213 }; 214 215 // Parses all policy test cases and makes then available in a map. 216 class PolicyTestCases { 217 public: 218 typedef std::vector<PolicyTestCase*> PolicyTestCaseVector; 219 typedef std::map<std::string, PolicyTestCaseVector> PolicyTestCaseMap; 220 typedef PolicyTestCaseMap::const_iterator iterator; 221 222 PolicyTestCases() { 223 base::FilePath path = ui_test_utils::GetTestFilePath( 224 base::FilePath(FILE_PATH_LITERAL("policy")), 225 base::FilePath(FILE_PATH_LITERAL("policy_test_cases.json"))); 226 std::string json; 227 if (!base::ReadFileToString(path, &json)) { 228 ADD_FAILURE(); 229 return; 230 } 231 int error_code = -1; 232 std::string error_string; 233 base::DictionaryValue* dict = NULL; 234 scoped_ptr<base::Value> value(base::JSONReader::ReadAndReturnError( 235 json, base::JSON_PARSE_RFC, &error_code, &error_string)); 236 if (!value.get() || !value->GetAsDictionary(&dict)) { 237 ADD_FAILURE() << "Error parsing policy_test_cases.json: " << error_string; 238 return; 239 } 240 Schema chrome_schema = Schema::Wrap(GetChromeSchemaData()); 241 if (!chrome_schema.valid()) { 242 ADD_FAILURE(); 243 return; 244 } 245 for (base::DictionaryValue::Iterator it(*dict); !it.IsAtEnd(); 246 it.Advance()) { 247 const std::string policy_name = GetPolicyName(it.key()); 248 if (!chrome_schema.GetKnownProperty(policy_name).valid()) 249 continue; 250 PolicyTestCase* policy_test_case = GetPolicyTestCase(dict, it.key()); 251 if (policy_test_case) 252 policy_test_cases_[policy_name].push_back(policy_test_case); 253 } 254 } 255 256 ~PolicyTestCases() { 257 for (iterator policy = policy_test_cases_.begin(); 258 policy != policy_test_cases_.end(); 259 ++policy) { 260 for (PolicyTestCaseVector::const_iterator test_case = 261 policy->second.begin(); 262 test_case != policy->second.end(); 263 ++test_case) { 264 delete *test_case; 265 } 266 } 267 } 268 269 const PolicyTestCaseVector* Get(const std::string& name) const { 270 const iterator it = policy_test_cases_.find(name); 271 return it == end() ? NULL : &it->second; 272 } 273 274 const PolicyTestCaseMap& map() const { return policy_test_cases_; } 275 iterator begin() const { return policy_test_cases_.begin(); } 276 iterator end() const { return policy_test_cases_.end(); } 277 278 private: 279 PolicyTestCase* GetPolicyTestCase(const base::DictionaryValue* tests, 280 const std::string& name) { 281 const base::DictionaryValue* policy_test_dict = NULL; 282 if (!tests->GetDictionaryWithoutPathExpansion(name, &policy_test_dict)) 283 return NULL; 284 bool is_official_only = false; 285 policy_test_dict->GetBoolean("official_only", &is_official_only); 286 bool can_be_recommended = false; 287 policy_test_dict->GetBoolean("can_be_recommended", &can_be_recommended); 288 std::string indicator_selector; 289 policy_test_dict->GetString("indicator_selector", &indicator_selector); 290 PolicyTestCase* policy_test_case = new PolicyTestCase(name, 291 is_official_only, 292 can_be_recommended, 293 indicator_selector); 294 const base::ListValue* os_list = NULL; 295 if (policy_test_dict->GetList("os", &os_list)) { 296 for (size_t i = 0; i < os_list->GetSize(); ++i) { 297 std::string os; 298 if (os_list->GetString(i, &os)) 299 policy_test_case->AddSupportedOs(os); 300 } 301 } 302 const base::DictionaryValue* policy = NULL; 303 if (policy_test_dict->GetDictionary("test_policy", &policy)) 304 policy_test_case->SetTestPolicy(*policy); 305 const base::ListValue* pref_mappings = NULL; 306 if (policy_test_dict->GetList("pref_mappings", &pref_mappings)) { 307 for (size_t i = 0; i < pref_mappings->GetSize(); ++i) { 308 const base::DictionaryValue* pref_mapping_dict = NULL; 309 std::string pref; 310 if (!pref_mappings->GetDictionary(i, &pref_mapping_dict) || 311 !pref_mapping_dict->GetString("pref", &pref)) { 312 ADD_FAILURE() << "Malformed pref_mappings entry in " 313 << "policy_test_cases.json."; 314 continue; 315 } 316 bool is_local_state = false; 317 pref_mapping_dict->GetBoolean("local_state", &is_local_state); 318 bool check_for_mandatory = true; 319 pref_mapping_dict->GetBoolean("check_for_mandatory", 320 &check_for_mandatory); 321 bool check_for_recommended = true; 322 pref_mapping_dict->GetBoolean("check_for_recommended", 323 &check_for_recommended); 324 std::string indicator_test_setup_js; 325 pref_mapping_dict->GetString("indicator_test_setup_js", 326 &indicator_test_setup_js); 327 std::string indicator_selector; 328 pref_mapping_dict->GetString("indicator_selector", &indicator_selector); 329 PrefMapping* pref_mapping = new PrefMapping(pref, 330 is_local_state, 331 check_for_mandatory, 332 check_for_recommended, 333 indicator_test_setup_js, 334 indicator_selector); 335 const base::ListValue* indicator_tests = NULL; 336 if (pref_mapping_dict->GetList("indicator_tests", &indicator_tests)) { 337 for (size_t i = 0; i < indicator_tests->GetSize(); ++i) { 338 const base::DictionaryValue* indicator_test_dict = NULL; 339 const base::DictionaryValue* policy = NULL; 340 if (!indicator_tests->GetDictionary(i, &indicator_test_dict) || 341 !indicator_test_dict->GetDictionary("policy", &policy)) { 342 ADD_FAILURE() << "Malformed indicator_tests entry in " 343 << "policy_test_cases.json."; 344 continue; 345 } 346 std::string value; 347 indicator_test_dict->GetString("value", &value); 348 bool readonly = false; 349 indicator_test_dict->GetBoolean("readonly", &readonly); 350 pref_mapping->AddIndicatorTestCase( 351 new IndicatorTestCase(*policy, value, readonly)); 352 } 353 } 354 policy_test_case->AddPrefMapping(pref_mapping); 355 } 356 } 357 return policy_test_case; 358 } 359 360 PolicyTestCaseMap policy_test_cases_; 361 362 DISALLOW_COPY_AND_ASSIGN(PolicyTestCases); 363 }; 364 365 // Returns a pseudo-random integer distributed in [0, range). 366 int GetRandomNumber(int range) { 367 return rand() % range; 368 } 369 370 // Splits all known policies into subsets of the given |chunk_size|. The 371 // policies are shuffled so that there is no correlation between their initial 372 // alphabetic ordering and the assignment to chunks. This ensures that the 373 // expected number of policies with long-running test cases is equal for each 374 // subset. The shuffle algorithm uses a fixed seed, ensuring that no randomness 375 // is introduced into the testing process. 376 std::vector<std::vector<std::string> > SplitPoliciesIntoChunks(int chunk_size) { 377 Schema chrome_schema = Schema::Wrap(GetChromeSchemaData()); 378 if (!chrome_schema.valid()) 379 ADD_FAILURE(); 380 381 std::vector<std::string> policies; 382 for (Schema::Iterator it = chrome_schema.GetPropertiesIterator(); 383 !it.IsAtEnd(); it.Advance()) { 384 policies.push_back(it.key()); 385 } 386 387 // Use a fixed random seed to obtain a reproducible shuffle. 388 srand(1); 389 std::random_shuffle(policies.begin(), policies.end(), GetRandomNumber); 390 391 std::vector<std::vector<std::string> > chunks; 392 std::vector<std::string>::const_iterator it = policies.begin(); 393 const std::vector<std::string>::const_iterator end = policies.end(); 394 for ( ; end - it >= chunk_size; it += chunk_size) 395 chunks.push_back(std::vector<std::string>(it, it + chunk_size)); 396 if (it != end) 397 chunks.push_back(std::vector<std::string>(it, end)); 398 return chunks; 399 } 400 401 void VerifyControlledSettingIndicators(Browser* browser, 402 const std::string& selector, 403 const std::string& value, 404 const std::string& controlled_by, 405 bool readonly) { 406 std::stringstream javascript; 407 javascript << "var nodes = document.querySelectorAll(" 408 << " 'span.controlled-setting-indicator" 409 << selector.c_str() << "');" 410 << "var indicators = [];" 411 << "for (var i = 0; i < nodes.length; i++) {" 412 << " var node = nodes[i];" 413 << " var indicator = {};" 414 << " indicator.value = node.value || '';" 415 << " indicator.controlledBy = node.controlledBy || '';" 416 << " indicator.readOnly = node.readOnly || false;" 417 << " indicator.visible =" 418 << " window.getComputedStyle(node).display != 'none';" 419 << " indicators.push(indicator)" 420 << "}" 421 << "domAutomationController.send(JSON.stringify(indicators));"; 422 content::WebContents* contents = 423 browser->tab_strip_model()->GetActiveWebContents(); 424 std::string json; 425 // Retrieve the state of all controlled setting indicators matching the 426 // |selector| as JSON. 427 ASSERT_TRUE(content::ExecuteScriptAndExtractString(contents, javascript.str(), 428 &json)); 429 scoped_ptr<base::Value> value_ptr(base::JSONReader::Read(json)); 430 const base::ListValue* indicators = NULL; 431 ASSERT_TRUE(value_ptr.get()); 432 ASSERT_TRUE(value_ptr->GetAsList(&indicators)); 433 // Verify that controlled setting indicators representing |value| are visible 434 // and have the correct state while those not representing |value| are 435 // invisible. 436 if (!controlled_by.empty()) { 437 EXPECT_GT(indicators->GetSize(), 0u) 438 << "Expected to find at least one controlled setting indicator."; 439 } 440 bool have_visible_indicators = false; 441 for (base::ListValue::const_iterator indicator = indicators->begin(); 442 indicator != indicators->end(); ++indicator) { 443 const base::DictionaryValue* properties = NULL; 444 ASSERT_TRUE((*indicator)->GetAsDictionary(&properties)); 445 std::string indicator_value; 446 std::string indicator_controlled_by; 447 bool indicator_readonly; 448 bool indicator_visible; 449 EXPECT_TRUE(properties->GetString("value", &indicator_value)); 450 EXPECT_TRUE(properties->GetString("controlledBy", 451 &indicator_controlled_by)); 452 EXPECT_TRUE(properties->GetBoolean("readOnly", &indicator_readonly)); 453 EXPECT_TRUE(properties->GetBoolean("visible", &indicator_visible)); 454 if (!controlled_by.empty() && (indicator_value == value)) { 455 EXPECT_EQ(controlled_by, indicator_controlled_by); 456 EXPECT_EQ(readonly, indicator_readonly); 457 EXPECT_TRUE(indicator_visible); 458 have_visible_indicators = true; 459 } else { 460 EXPECT_FALSE(indicator_visible); 461 } 462 } 463 if (!controlled_by.empty()) { 464 EXPECT_TRUE(have_visible_indicators) 465 << "Expected to find at least one visible controlled setting " 466 << "indicator."; 467 } 468 } 469 470 } // namespace 471 472 typedef InProcessBrowserTest PolicyPrefsTestCoverageTest; 473 474 IN_PROC_BROWSER_TEST_F(PolicyPrefsTestCoverageTest, AllPoliciesHaveATestCase) { 475 // Verifies that all known policies have a test case in the JSON file. 476 // This test fails when a policy is added to 477 // components/policy/resources/policy_templates.json but a test case is not 478 // added to chrome/test/data/policy/policy_test_cases.json. 479 Schema chrome_schema = Schema::Wrap(GetChromeSchemaData()); 480 ASSERT_TRUE(chrome_schema.valid()); 481 482 PolicyTestCases policy_test_cases; 483 for (Schema::Iterator it = chrome_schema.GetPropertiesIterator(); 484 !it.IsAtEnd(); it.Advance()) { 485 EXPECT_TRUE(ContainsKey(policy_test_cases.map(), it.key())) 486 << "Missing policy test case for: " << it.key(); 487 } 488 } 489 490 // Base class for tests that change policy. 491 class PolicyPrefsTest : public InProcessBrowserTest { 492 protected: 493 virtual void SetUpInProcessBrowserTestFixture() OVERRIDE { 494 EXPECT_CALL(provider_, IsInitializationComplete(_)) 495 .WillRepeatedly(Return(true)); 496 BrowserPolicyConnector::SetPolicyProviderForTesting(&provider_); 497 } 498 499 virtual void SetUpOnMainThread() OVERRIDE { 500 ui_test_utils::WaitForTemplateURLServiceToLoad( 501 TemplateURLServiceFactory::GetForProfile(browser()->profile())); 502 } 503 504 virtual void TearDownOnMainThread() OVERRIDE { 505 ClearProviderPolicy(); 506 } 507 508 void ClearProviderPolicy() { 509 provider_.UpdateChromePolicy(PolicyMap()); 510 base::RunLoop().RunUntilIdle(); 511 } 512 513 void SetProviderPolicy(const base::DictionaryValue& policies, 514 PolicyLevel level) { 515 PolicyMap policy_map; 516 for (base::DictionaryValue::Iterator it(policies); 517 !it.IsAtEnd(); it.Advance()) { 518 const PolicyDetails* policy_details = GetChromePolicyDetails(it.key()); 519 ASSERT_TRUE(policy_details); 520 policy_map.Set( 521 it.key(), 522 level, 523 POLICY_SCOPE_USER, 524 it.value().DeepCopy(), 525 policy_details->max_external_data_size ? 526 new ExternalDataFetcher(base::WeakPtr<ExternalDataManager>(), 527 it.key()) : 528 NULL); 529 } 530 provider_.UpdateChromePolicy(policy_map); 531 base::RunLoop().RunUntilIdle(); 532 } 533 534 MockConfigurationPolicyProvider provider_; 535 }; 536 537 // Verifies that policies make their corresponding preferences become managed, 538 // and that the user can't override that setting. 539 IN_PROC_BROWSER_TEST_F(PolicyPrefsTest, PolicyToPrefsMapping) { 540 PrefService* local_state = g_browser_process->local_state(); 541 PrefService* user_prefs = browser()->profile()->GetPrefs(); 542 543 const PolicyTestCases test_cases; 544 for (PolicyTestCases::iterator policy = test_cases.begin(); 545 policy != test_cases.end(); 546 ++policy) { 547 for (PolicyTestCases::PolicyTestCaseVector::const_iterator test_case = 548 policy->second.begin(); 549 test_case != policy->second.end(); 550 ++test_case) { 551 const ScopedVector<PrefMapping>& pref_mappings = 552 (*test_case)->pref_mappings(); 553 if (!(*test_case)->IsSupported() || pref_mappings.empty()) 554 continue; 555 556 LOG(INFO) << "Testing policy: " << policy->first; 557 558 for (ScopedVector<PrefMapping>::const_iterator pref_mapping = 559 pref_mappings.begin(); 560 pref_mapping != pref_mappings.end(); 561 ++pref_mapping) { 562 // Skip Chrome OS preferences that use a different backend and cannot be 563 // retrieved through the prefs mechanism. 564 if (StartsWithASCII((*pref_mapping)->pref(), kCrosSettingsPrefix, true)) 565 continue; 566 567 // Skip preferences that should not be checked when the policy is set to 568 // a mandatory value. 569 if (!(*pref_mapping)->check_for_mandatory()) 570 continue; 571 572 PrefService* prefs = 573 (*pref_mapping)->is_local_state() ? local_state : user_prefs; 574 // The preference must have been registered. 575 const PrefService::Preference* pref = 576 prefs->FindPreference((*pref_mapping)->pref().c_str()); 577 ASSERT_TRUE(pref); 578 579 // Verify that setting the policy overrides the pref. 580 ClearProviderPolicy(); 581 prefs->ClearPref((*pref_mapping)->pref().c_str()); 582 EXPECT_TRUE(pref->IsDefaultValue()); 583 EXPECT_TRUE(pref->IsUserModifiable()); 584 EXPECT_FALSE(pref->IsUserControlled()); 585 EXPECT_FALSE(pref->IsManaged()); 586 587 SetProviderPolicy((*test_case)->test_policy(), POLICY_LEVEL_MANDATORY); 588 EXPECT_FALSE(pref->IsDefaultValue()); 589 EXPECT_FALSE(pref->IsUserModifiable()); 590 EXPECT_FALSE(pref->IsUserControlled()); 591 EXPECT_TRUE(pref->IsManaged()); 592 } 593 } 594 } 595 } 596 597 class PolicyPrefIndicatorTest 598 : public PolicyPrefsTest, 599 public testing::WithParamInterface<std::vector<std::string> > { 600 }; 601 602 // Verifies that controlled setting indicators correctly show whether a pref's 603 // value is recommended or enforced by a corresponding policy. 604 IN_PROC_BROWSER_TEST_P(PolicyPrefIndicatorTest, CheckPolicyIndicators) { 605 const PolicyTestCases test_cases; 606 PrefService* local_state = g_browser_process->local_state(); 607 PrefService* user_prefs = browser()->profile()->GetPrefs(); 608 609 ui_test_utils::NavigateToURL(browser(), GURL(kMainSettingsPage)); 610 611 for (std::vector<std::string>::const_iterator policy = GetParam().begin(); 612 policy != GetParam().end(); 613 ++policy) { 614 const std::vector<PolicyTestCase*>* policy_test_cases = 615 test_cases.Get(*policy); 616 ASSERT_TRUE(policy_test_cases) << "PolicyTestCase not found for " 617 << *policy; 618 for (std::vector<PolicyTestCase*>::const_iterator test_case = 619 policy_test_cases->begin(); 620 test_case != policy_test_cases->end(); 621 ++test_case) { 622 PolicyTestCase* policy_test_case = *test_case; 623 if (!policy_test_case->IsSupported()) 624 continue; 625 const ScopedVector<PrefMapping>& pref_mappings = 626 policy_test_case->pref_mappings(); 627 if (policy_test_case->indicator_selector().empty()) { 628 bool has_pref_indicator_tests = false; 629 for (ScopedVector<PrefMapping>::const_iterator pref_mapping = 630 pref_mappings.begin(); 631 pref_mapping != pref_mappings.end(); 632 ++pref_mapping) { 633 if (!(*pref_mapping)->indicator_test_cases().empty()) { 634 has_pref_indicator_tests = true; 635 break; 636 } 637 } 638 if (!has_pref_indicator_tests) 639 continue; 640 } 641 642 LOG(INFO) << "Testing policy: " << *policy; 643 644 if (!policy_test_case->indicator_selector().empty()) { 645 // Check that no controlled setting indicator is visible when no value 646 // is set by policy. 647 ClearProviderPolicy(); 648 VerifyControlledSettingIndicators( 649 browser(), 650 policy_test_case->indicator_selector(), 651 std::string(), 652 std::string(), 653 false); 654 // Check that the appropriate controlled setting indicator is shown when 655 // a value is enforced by policy. 656 SetProviderPolicy(policy_test_case->test_policy(), 657 POLICY_LEVEL_MANDATORY); 658 VerifyControlledSettingIndicators( 659 browser(), 660 policy_test_case->indicator_selector(), 661 std::string(), 662 "policy", 663 false); 664 } 665 666 for (ScopedVector<PrefMapping>::const_iterator 667 pref_mapping = pref_mappings.begin(); 668 pref_mapping != pref_mappings.end(); 669 ++pref_mapping) { 670 const ScopedVector<IndicatorTestCase>& indicator_test_cases = 671 (*pref_mapping)->indicator_test_cases(); 672 if (indicator_test_cases.empty()) 673 continue; 674 675 if (!(*pref_mapping)->indicator_test_setup_js().empty()) { 676 ASSERT_TRUE(content::ExecuteScript( 677 browser()->tab_strip_model()->GetActiveWebContents(), 678 (*pref_mapping)->indicator_test_setup_js())); 679 } 680 681 std::string indicator_selector = (*pref_mapping)->indicator_selector(); 682 if (indicator_selector.empty()) 683 indicator_selector = "[pref=\"" + (*pref_mapping)->pref() + "\"]"; 684 for (ScopedVector<IndicatorTestCase>::const_iterator 685 indicator_test_case = indicator_test_cases.begin(); 686 indicator_test_case != indicator_test_cases.end(); 687 ++indicator_test_case) { 688 // Check that no controlled setting indicator is visible when no value 689 // is set by policy. 690 ClearProviderPolicy(); 691 VerifyControlledSettingIndicators(browser(), 692 indicator_selector, 693 std::string(), 694 std::string(), 695 false); 696 697 if ((*pref_mapping)->check_for_mandatory()) { 698 // Check that the appropriate controlled setting indicator is shown 699 // when a value is enforced by policy. 700 SetProviderPolicy((*indicator_test_case)->policy(), 701 POLICY_LEVEL_MANDATORY); 702 703 VerifyControlledSettingIndicators( 704 browser(), 705 indicator_selector, 706 (*indicator_test_case)->value(), 707 "policy", 708 (*indicator_test_case)->readonly()); 709 } 710 711 if (!policy_test_case->can_be_recommended() || 712 !(*pref_mapping)->check_for_recommended()) { 713 continue; 714 } 715 716 PrefService* prefs = 717 (*pref_mapping)->is_local_state() ? local_state : user_prefs; 718 // The preference must have been registered. 719 const PrefService::Preference* pref = 720 prefs->FindPreference((*pref_mapping)->pref().c_str()); 721 ASSERT_TRUE(pref); 722 723 // Check that the appropriate controlled setting indicator is shown 724 // when a value is recommended by policy and the user has not 725 // overridden the recommendation. 726 SetProviderPolicy((*indicator_test_case)->policy(), 727 POLICY_LEVEL_RECOMMENDED); 728 VerifyControlledSettingIndicators(browser(), 729 indicator_selector, 730 (*indicator_test_case)->value(), 731 "recommended", 732 (*indicator_test_case)->readonly()); 733 // Check that the appropriate controlled setting indicator is shown 734 // when a value is recommended by policy and the user has overridden 735 // the recommendation. 736 prefs->Set((*pref_mapping)->pref().c_str(), *pref->GetValue()); 737 VerifyControlledSettingIndicators(browser(), 738 indicator_selector, 739 (*indicator_test_case)->value(), 740 "hasRecommendation", 741 (*indicator_test_case)->readonly()); 742 prefs->ClearPref((*pref_mapping)->pref().c_str()); 743 } 744 } 745 } 746 } 747 } 748 749 INSTANTIATE_TEST_CASE_P(PolicyPrefIndicatorTestInstance, 750 PolicyPrefIndicatorTest, 751 testing::ValuesIn(SplitPoliciesIntoChunks(10))); 752 753 } // namespace policy 754