Commit d936cdf7 authored by Tony de Luna's avatar Tony de Luna Committed by Commit Bot

ErrorScreen. Test that certificate manager dialog opens.

This CL:
- Refactors HelpAppTestHelper::Waiter to a general dialog window waiter.
- Renames HelpAppTestHelper to ScopedHelpAppForTest.
- Adds a test fixture that sets up a kiosk session for error screen
  tests.
- Adds a test that verifies that clicking on the "Manage certificates"
  button in the error screen opens a certificate manager window.

Bug: 959340
Change-Id: I92a9121872ff28d9c1752c222343cfc643f18501
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1612599
Commit-Queue: Tony De Luna <tonydeluna@chromium.org>
Reviewed-by: default avatarToni Baržić <tbarzic@chromium.org>
Cr-Commit-Position: refs/heads/master@{#661111}
parent cea2b789
......@@ -2194,8 +2194,10 @@ static_library("test_support") {
"login/screens/mock_welcome_screen.h",
"login/screens/recommend_apps/fake_recommend_apps_fetcher_delegate.cc",
"login/screens/recommend_apps/fake_recommend_apps_fetcher_delegate.h",
"login/test/help_app_test_helper.cc",
"login/test/help_app_test_helper.h",
"login/test/dialog_window_waiter.cc",
"login/test/dialog_window_waiter.h",
"login/test/scoped_help_app_for_test.cc",
"login/test/scoped_help_app_for_test.h",
"login/test/test_condition_waiter.h",
"login/test/test_predicate_waiter.cc",
"login/test/test_predicate_waiter.h",
......
......@@ -5,28 +5,51 @@
#include "base/run_loop.h"
#include "base/strings/strcat.h"
#include "base/test/bind_test_util.h"
#include "chrome/browser/chrome_notification_types.h"
#include "chrome/browser/chromeos/app_mode/fake_cws.h"
#include "chrome/browser/chromeos/login/app_launch_controller.h"
#include "chrome/browser/chromeos/login/login_wizard.h"
#include "chrome/browser/chromeos/login/mixin_based_in_process_browser_test.h"
#include "chrome/browser/chromeos/login/screens/error_screen.h"
#include "chrome/browser/chromeos/login/test/device_state_mixin.h"
#include "chrome/browser/chromeos/login/test/dialog_window_waiter.h"
#include "chrome/browser/chromeos/login/test/embedded_test_server_mixin.h"
#include "chrome/browser/chromeos/login/test/js_checker.h"
#include "chrome/browser/chromeos/login/test/login_manager_mixin.h"
#include "chrome/browser/chromeos/login/test/login_screen_tester.h"
#include "chrome/browser/chromeos/login/test/oobe_screen_waiter.h"
#include "chrome/browser/chromeos/login/wizard_controller.h"
#include "chrome/browser/ui/webui/chromeos/login/app_launch_splash_screen_handler.h"
#include "chrome/browser/ui/webui/chromeos/login/error_screen_handler.h"
#include "chrome/browser/ui/webui/chromeos/login/welcome_screen_handler.h"
#include "chrome/grit/generated_resources.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chromeos/dbus/session_manager/fake_session_manager_client.h"
#include "chromeos/dbus/session_manager/session_manager_client.h"
#include "chromeos/dbus/shill/shill_profile_client.h"
#include "chromeos/network/network_state_test_helper.h"
#include "components/policy/proto/chrome_device_policy.pb.h"
#include "components/user_manager/user_manager.h"
#include "content/public/test/test_utils.h"
#include "net/dns/mock_host_resolver.h"
#include "third_party/cros_system_api/dbus/shill/dbus-constants.h"
#include "ui/base/l10n/l10n_util.h"
namespace em = enterprise_management;
namespace chromeos {
namespace {
// This is a simple test app that creates an app window and immediately closes
// it again. Webstore data json is in
// chrome/test/data/chromeos/app_mode/webstore/inlineinstall/
// detail/ggaeimfdpnmlhdhpcikgoblffmkckdmn
constexpr char kTestKioskAppId[] = "ggaeimfdpnmlhdhpcikgoblffmkckdmn";
constexpr char kTestKioskAccountId[] = "enterprise-kiosk-app@localhost";
constexpr char kTestUser[] = "test-user1@gmail.com";
constexpr char kWifiServiceName[] = "stub_wifi";
constexpr char kWifiNetworkName[] = "wifi-test-network";
......@@ -218,4 +241,103 @@ IN_PROC_BROWSER_TEST_F(GuestErrorScreenTest, GuestLogin) {
EXPECT_TRUE(user_manager->IsLoggedInAsGuest());
}
class KioskErrorScreenTest : public MixinBasedInProcessBrowserTest {
public:
KioskErrorScreenTest() = default;
~KioskErrorScreenTest() override = default;
void SetUpInProcessBrowserTestFixture() override {
host_resolver()->AddRule("*", "127.0.0.1");
AppLaunchController::SkipSplashWaitForTesting();
AppLaunchController::SetNetworkWaitForTesting(0);
fake_cws_.Init(embedded_test_server());
fake_cws_.SetUpdateCrx(kTestKioskAppId,
base::StrCat({kTestKioskAppId, ".crx"}), "1.0.0");
AddKioskAppToDevicePolicy();
MixinBasedInProcessBrowserTest::SetUpInProcessBrowserTestFixture();
}
void SetUpOnMainThread() override {
network_helper_ = std::make_unique<NetworkStateTestHelper>(
/*use_default_devices_and_services=*/false);
network_helper_->service_test()->AddService(
kWifiServiceName, "wifi_guid", kWifiNetworkName, shill::kTypeWifi,
shill::kStateOffline, /*visible=*/true);
apps_loaded_waiter_ =
std::make_unique<content::WindowedNotificationObserver>(
chrome::NOTIFICATION_KIOSK_APPS_LOADED,
content::NotificationService::AllSources());
MixinBasedInProcessBrowserTest::SetUpOnMainThread();
}
void TearDownOnMainThread() override {
network_helper_.reset();
apps_loaded_waiter_.reset();
MixinBasedInProcessBrowserTest::TearDownOnMainThread();
}
protected:
content::WindowedNotificationObserver* apps_loaded_waiter() {
return apps_loaded_waiter_.get();
}
private:
void AddKioskAppToDevicePolicy() {
std::unique_ptr<ScopedDevicePolicyUpdate> device_policy_update =
device_state_.RequestDevicePolicyUpdate();
em::DeviceLocalAccountsProto* const device_local_accounts =
device_policy_update->policy_payload()->mutable_device_local_accounts();
em::DeviceLocalAccountInfoProto* const account =
device_local_accounts->add_account();
account->set_account_id(kTestKioskAccountId);
account->set_type(em::DeviceLocalAccountInfoProto::ACCOUNT_TYPE_KIOSK_APP);
account->mutable_kiosk_app()->set_app_id(kTestKioskAppId);
device_policy_update.reset();
std::unique_ptr<ScopedUserPolicyUpdate> device_local_account_policy_update =
device_state_.RequestDeviceLocalAccountPolicyUpdate(
kTestKioskAccountId);
device_local_account_policy_update.reset();
}
std::unique_ptr<NetworkStateTestHelper> network_helper_;
std::unique_ptr<content::WindowedNotificationObserver> apps_loaded_waiter_;
FakeCWS fake_cws_;
DeviceStateMixin device_state_{
&mixin_host_, DeviceStateMixin::State::OOBE_COMPLETED_CLOUD_ENROLLED};
EmbeddedTestServerSetupMixin embedded_test_server_setup_{
&mixin_host_, embedded_test_server()};
LoginManagerMixin login_manager_{&mixin_host_, {}};
DISALLOW_COPY_AND_ASSIGN(KioskErrorScreenTest);
};
// Verify that certificate manager dialog opens.
IN_PROC_BROWSER_TEST_F(KioskErrorScreenTest, OpenCertificateConfig) {
apps_loaded_waiter()->Wait();
EXPECT_TRUE(test::LoginScreenTester().LaunchApp(kTestKioskAppId));
OobeScreenWaiter(ErrorScreenView::kScreenId).Wait();
DialogWindowWaiter waiter(
l10n_util::GetStringUTF16(IDS_CERTIFICATE_MANAGER_TITLE));
test::OobeJS().ClickOnPath({"error-message-md-configure-certs-button"});
waiter.Wait();
}
} // namespace chromeos
......@@ -16,10 +16,11 @@
#include "base/task/post_task.h"
#include "base/test/bind_test_util.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/chromeos/login/test/help_app_test_helper.h"
#include "chrome/browser/chromeos/login/test/dialog_window_waiter.h"
#include "chrome/browser/chromeos/login/test/js_checker.h"
#include "chrome/browser/chromeos/login/test/oobe_base_test.h"
#include "chrome/browser/chromeos/login/test/oobe_screen_waiter.h"
#include "chrome/browser/chromeos/login/test/scoped_help_app_for_test.h"
#include "chrome/browser/chromeos/login/test/webview_content_extractor.h"
#include "chrome/browser/chromeos/login/ui/login_display_host.h"
#include "chrome/browser/chromeos/login/wizard_controller.h"
......@@ -27,6 +28,7 @@
#include "chrome/browser/profiles/profile_manager.h"
#include "chrome/browser/ui/webui/chromeos/login/eula_screen_handler.h"
#include "chrome/browser/ui/webui/chromeos/login/oobe_ui.h"
#include "chrome/grit/generated_resources.h"
#include "chrome/installer/util/google_update_settings.h"
#include "chromeos/dbus/cryptohome/fake_cryptohome_client.h"
#include "components/guest_view/browser/guest_view_manager.h"
......@@ -40,6 +42,7 @@
#include "net/test/embedded_test_server/embedded_test_server.h"
#include "net/test/embedded_test_server/http_request.h"
#include "net/test/embedded_test_server/http_response.h"
#include "ui/base/l10n/l10n_util.h"
#include "url/gurl.h"
using net::test_server::BasicHttpResponse;
......@@ -354,10 +357,11 @@ IN_PROC_BROWSER_TEST_F(EulaTest, LearnMore) {
ShowEulaScreen();
// Load HelperApp extension.
HelpAppTestHelper scoped_helper;
ScopedHelpAppForTest scoped_help_app;
// Start listening for help dialog creation.
HelpAppTestHelper::Waiter waiter;
DialogWindowWaiter waiter(
l10n_util::GetStringUTF16(IDS_LOGIN_OOBE_HELP_DIALOG_TITLE));
NonPolymerOobeJS().TapOnPath({"oobe-eula-md", "learn-more"});
......@@ -366,4 +370,5 @@ IN_PROC_BROWSER_TEST_F(EulaTest, LearnMore) {
}
} // namespace
} // namespace chromeos
// Copyright 2019 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/chromeos/login/test/dialog_window_waiter.h"
#include "ui/aura/env.h"
#include "ui/aura/window.h"
#include "ui/views/widget/widget.h"
namespace chromeos {
DialogWindowWaiter::DialogWindowWaiter(const base::string16& dialog_title)
: dialog_title_(dialog_title) {
aura::Env::GetInstance()->AddObserver(this);
}
DialogWindowWaiter::~DialogWindowWaiter() {
aura::Env::GetInstance()->RemoveObserver(this);
window_observer_.RemoveAll();
// Explicitly close any help app dialogs still open to prevent flaky errors in
// browser tests. Remove when crbug.com/951828 is fixed.
for (aura::Window* dialog_window : dialog_windows_)
views::Widget::GetWidgetForNativeView(dialog_window)->CloseNow();
}
void DialogWindowWaiter::Wait() {
run_loop_.Run();
}
void DialogWindowWaiter::OnWindowInitialized(aura::Window* window) {
DCHECK(!window_observer_.IsObserving(window));
window_observer_.Add(window);
}
void DialogWindowWaiter::OnWindowDestroyed(aura::Window* window) {
if (window_observer_.IsObserving(window))
window_observer_.Remove(window);
dialog_windows_.erase(window);
}
void DialogWindowWaiter::OnWindowVisibilityChanged(aura::Window* window,
bool visible) {
if (window->GetTitle() != dialog_title_)
return;
dialog_windows_.insert(window);
if (visible) {
run_loop_.Quit();
}
}
} // namespace chromeos
// Copyright 2019 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_CHROMEOS_LOGIN_TEST_DIALOG_WINDOW_WAITER_H_
#define CHROME_BROWSER_CHROMEOS_LOGIN_TEST_DIALOG_WINDOW_WAITER_H_
#include <set>
#include "base/macros.h"
#include "base/run_loop.h"
#include "base/scoped_observer.h"
#include "ui/aura/env_observer.h"
#include "ui/aura/window_observer.h"
namespace chromeos {
// Waits for a dialog window to open and become visible.
//
// Starts listening for window creation events on construction. |Wait| blocks
// until the expected dialog window is visible. |Wait| returns immediately if
// the expected dialog window is already visible when |Wait| is called.
//
// DialogWindowWaiter is single-use. It can only wait for one dialog to be
// opened per lifetime.
class DialogWindowWaiter : public aura::EnvObserver,
public aura::WindowObserver {
public:
// Starts listening for a dialog window to open with title |dialog_title|.
explicit DialogWindowWaiter(const base::string16& dialog_title);
~DialogWindowWaiter() override;
// Blocks until a dialog with title |dialog_title| becomes visible. All calls
// to |Wait| return immediately after the dialog becomes visible during this
// object's lifetime.
void Wait();
// aura::EnvObserver
void OnWindowInitialized(aura::Window* window) override;
// aura::WindowObserver
void OnWindowVisibilityChanged(aura::Window* window, bool visible) override;
void OnWindowDestroyed(aura::Window* window) override;
private:
// The title of the expected dialog window.
base::string16 dialog_title_;
base::RunLoop run_loop_;
std::set<aura::Window*> dialog_windows_;
ScopedObserver<aura::Window, DialogWindowWaiter> window_observer_{this};
DISALLOW_COPY_AND_ASSIGN(DialogWindowWaiter);
};
} // namespace chromeos
#endif // CHROME_BROWSER_CHROMEOS_LOGIN_TEST_DIALOG_WINDOW_WAITER_H_
// Copyright 2019 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_CHROMEOS_LOGIN_TEST_HELP_APP_TEST_HELPER_H_
#define CHROME_BROWSER_CHROMEOS_LOGIN_TEST_HELP_APP_TEST_HELPER_H_
#include <set>
#include "base/macros.h"
#include "base/run_loop.h"
#include "base/scoped_observer.h"
#include "ui/aura/env_observer.h"
#include "ui/aura/window_observer.h"
namespace chromeos {
// Provides utilies for launching and interacting with HelpApp dialogs in tests.
class HelpAppTestHelper {
public:
// Waits for a HelpApp dialog to open and become visible.
//
// Starts listening for window creation events on construction. |Wait| blocks
// until a HelpApp window is visible. |Wait| returns immediately if a HelpApp
// window is already visible when |Wait| is called.
//
// HelpAppTestHelper::Waiter is single-use. It can only wait for one HelpApp
// dialog to be opened per lifetime.
class Waiter : public aura::EnvObserver, public aura::WindowObserver {
public:
Waiter();
~Waiter() override;
// Blocks until a HelpApp dialog becomes visible. Once a HelpApp dialog
// becomes visible during this object's lifetime, all calls to |Wait| return
// immediately.
void Wait();
// aura::EnvObserver
void OnWindowInitialized(aura::Window* window) override;
// aura::WindowObserver
void OnWindowVisibilityChanged(aura::Window* window, bool visible) override;
void OnWindowDestroyed(aura::Window* window) override;
private:
bool IsHelpAppDialog(aura::Window* window);
base::RunLoop run_loop_;
std::set<aura::Window*> dialog_windows_;
ScopedObserver<aura::Window, Waiter> window_observer_{this};
bool help_app_dialog_opened_ = false;
DISALLOW_COPY_AND_ASSIGN(Waiter);
};
HelpAppTestHelper();
virtual ~HelpAppTestHelper();
// Performs setup to allow HelpApp dialogs to open in tests.
void SetUpHelpAppForTest();
// TODO(tonydeluna): Add utilities for interacting with the contents of the
// help dialogs.
DISALLOW_COPY_AND_ASSIGN(HelpAppTestHelper);
};
} // namespace chromeos
#endif // CHROME_BROWSER_CHROMEOS_LOGIN_TEST_HELP_APP_TEST_HELPER_H_
......@@ -89,5 +89,12 @@ bool LoginScreenTester::WaitForUiUpdate(int64_t previous_update_count) {
return success;
}
bool LoginScreenTester::LaunchApp(const std::string& app_id) {
ash::mojom::LoginScreenTestApiAsyncWaiter login_screen(test_api_.get());
bool success;
login_screen.LaunchApp(app_id, &success);
return success;
}
} // namespace test
} // namespace chromeos
......@@ -41,6 +41,9 @@ class LoginScreenTester {
// |previous_update_count|. Returns true on success, false on error.
bool WaitForUiUpdate(int64_t previous_update_count);
// Starts kiosk app.
bool LaunchApp(const std::string& app_id);
private:
ash::mojom::LoginScreenTestApiPtr test_api_;
......
......@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/chromeos/login/test/help_app_test_helper.h"
#include "chrome/browser/chromeos/login/test/scoped_help_app_for_test.h"
#include "base/files/file_path.h"
#include "base/path_service.h"
......@@ -11,73 +11,15 @@
#include "chrome/browser/chromeos/profiles/profile_helper.h"
#include "chrome/browser/extensions/chrome_test_extension_loader.h"
#include "chrome/common/chrome_paths.h"
#include "chrome/grit/generated_resources.h"
#include "ui/aura/env.h"
#include "ui/aura/window.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/views/widget/widget.h"
namespace chromeos {
///////////////////////////////////////////////////////////////////////////////
// HelpAppTestHelper::Waiter
///////////////////////////////////////////////////////////////////////////////
HelpAppTestHelper::Waiter::Waiter() {
aura::Env::GetInstance()->AddObserver(this);
}
HelpAppTestHelper::Waiter::~Waiter() {
aura::Env::GetInstance()->RemoveObserver(this);
window_observer_.RemoveAll();
// Explicitly close any help app dialogs still open to prevent flaky errors in
// browser tests. Remove when crbug.com/951828 is fixed.
for (aura::Window* dialog_window : dialog_windows_)
views::Widget::GetWidgetForNativeView(dialog_window)->CloseNow();
}
void HelpAppTestHelper::Waiter::Wait() {
if (!help_app_dialog_opened_)
run_loop_.Run();
}
void HelpAppTestHelper::Waiter::OnWindowInitialized(aura::Window* window) {
DCHECK(!window_observer_.IsObserving(window));
window_observer_.Add(window);
}
void HelpAppTestHelper::Waiter::OnWindowDestroyed(aura::Window* window) {
if (window_observer_.IsObserving(window))
window_observer_.Remove(window);
dialog_windows_.erase(window);
}
void HelpAppTestHelper::Waiter::OnWindowVisibilityChanged(aura::Window* window,
bool visible) {
if (!IsHelpAppDialog(window))
return;
dialog_windows_.insert(window);
if (visible) {
help_app_dialog_opened_ = true;
run_loop_.Quit();
}
}
bool HelpAppTestHelper::Waiter::IsHelpAppDialog(aura::Window* window) {
return window->GetTitle() ==
l10n_util::GetStringUTF16(IDS_LOGIN_OOBE_HELP_DIALOG_TITLE);
}
///////////////////////////////////////////////////////////////////////////////
// HelpAppTestHelper
///////////////////////////////////////////////////////////////////////////////
HelpAppTestHelper::HelpAppTestHelper() {
ScopedHelpAppForTest::ScopedHelpAppForTest() {
auto reset = GetScopedSigninScreenPolicyProviderDisablerForTesting();
base::FilePath test_data_dir;
base::PathService::Get(chrome::DIR_TEST_DATA, &test_data_dir);
extensions::ChromeTestExtensionLoader loader(
ProfileHelper::GetSigninProfile());
loader.set_allow_incognito_access(true);
......@@ -92,7 +34,7 @@ HelpAppTestHelper::HelpAppTestHelper() {
HelpAppLauncher::SetExtensionIdForTest(extension->id().c_str());
}
HelpAppTestHelper::~HelpAppTestHelper() {
ScopedHelpAppForTest::~ScopedHelpAppForTest() {
HelpAppLauncher::SetExtensionIdForTest(nullptr);
}
......
// Copyright 2019 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_CHROMEOS_LOGIN_TEST_SCOPED_HELP_APP_FOR_TEST_H_
#define CHROME_BROWSER_CHROMEOS_LOGIN_TEST_SCOPED_HELP_APP_FOR_TEST_H_
#include "base/macros.h"
namespace chromeos {
// An object that loads a test version of the HelpApp extension for use in
// tests. While this object is in scope |HelpAppLauncher| sends requests to the
// loaded test HelpApp extension. When this object goes out of scope
// |HelpAppLauncher| reverts to sending requests to the production extension.
class ScopedHelpAppForTest {
public:
ScopedHelpAppForTest();
virtual ~ScopedHelpAppForTest();
DISALLOW_COPY_AND_ASSIGN(ScopedHelpAppForTest);
};
} // namespace chromeos
#endif // CHROME_BROWSER_CHROMEOS_LOGIN_TEST_SCOPED_HELP_APP_FOR_TEST_H_
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment