chromium/chrome/browser/ui/views/toolbar/chrome_labs/chrome_labs_unittest.cc

// Copyright 2020 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <vector>

#include "base/memory/raw_ptr.h"
#include "base/test/metrics/histogram_tester.h"
#include "base/test/scoped_feature_list.h"
#include "base/test/task_environment.h"
#include "base/time/time.h"
#include "chrome/browser/about_flags.h"
#include "chrome/browser/ui/toolbar/chrome_labs/chrome_labs_model.h"
#include "chrome/browser/ui/toolbar/chrome_labs/chrome_labs_prefs.h"
#include "chrome/browser/ui/toolbar/chrome_labs/chrome_labs_utils.h"
#include "chrome/browser/ui/ui_features.h"
#include "chrome/browser/ui/views/frame/browser_view.h"
#include "chrome/browser/ui/views/frame/test_with_browser_view.h"
#include "chrome/browser/ui/views/toolbar/chrome_labs/chrome_labs_bubble_view.h"
#include "chrome/browser/ui/views/toolbar/chrome_labs/chrome_labs_button.h"
#include "chrome/browser/ui/views/toolbar/chrome_labs/chrome_labs_coordinator.h"
#include "chrome/browser/ui/views/toolbar/chrome_labs/chrome_labs_item_view.h"
#include "chrome/browser/ui/views/toolbar/chrome_labs/chrome_labs_view_controller.h"
#include "chrome/browser/ui/views/toolbar/toolbar_view.h"
#include "chrome/browser/unexpire_flags.h"
#include "chrome/test/base/testing_browser_process.h"
#include "components/flags_ui/feature_entry_macros.h"
#include "components/flags_ui/flags_state.h"
#include "components/flags_ui/pref_service_flags_storage.h"
#include "components/user_education/views/new_badge_label.h"
#include "components/version_info/channel.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/events/event_utils.h"
#include "ui/views/controls/button/md_text_button.h"
#include "ui/views/controls/combobox/combobox.h"
#include "ui/views/test/button_test_api.h"
#include "ui/views/test/combobox_test_api.h"
#include "ui/views/test/widget_test.h"
#include "ui/views/widget/widget.h"

#if BUILDFLAG(IS_CHROMEOS_ASH)
#include "base/memory/ptr_util.h"
#include "chrome/browser/ash/ownership/owner_settings_service_ash.h"
#include "chrome/browser/ash/ownership/owner_settings_service_ash_factory.h"
#include "chrome/browser/ash/settings/about_flags.h"
#include "chromeos/ash/components/cryptohome/cryptohome_parameters.h"
#include "chromeos/ash/components/dbus/session_manager/fake_session_manager_client.h"
#include "components/user_manager/user_manager.h"
#endif

#if BUILDFLAG(GOOGLE_CHROME_BRANDING) && !BUILDFLAG(IS_CHROMEOS_ASH)
#include "chrome/test/base/scoped_channel_override.h"
#endif

#if !BUILDFLAG(IS_CHROMEOS_ASH) || !BUILDFLAG(GOOGLE_CHROME_BRANDING)

namespace {

const char kFirstTestFeatureId[] =;
const char kTestFeatureWithVariationId[] =;
const char kThirdTestFeatureId[] =;
const char kExpiredFlagTestFeatureId[] =;

BASE_FEATURE();
BASE_FEATURE();
BASE_FEATURE();

BASE_FEATURE();

const flags_ui::FeatureEntry::FeatureParam kTestVariationOther2[] =;
const flags_ui::FeatureEntry::FeatureVariation kTestVariations2[] =;

std::vector<LabInfo> TestLabInfo() {}

}  // namespace

class ChromeLabsCoordinatorTest : public TestWithBrowserView {};

TEST_F(ChromeLabsCoordinatorTest, ShowBubbleTest) {}

// This test checks the new badge shows and that after 8 days the new badge is
// not showing anymore.
TEST_F(ChromeLabsCoordinatorTest, NewBadgeTest) {}

#if BUILDFLAG(IS_CHROMEOS_ASH)

// OwnerFlagsStorage on build bots works the same way as the non-owner version
// since we don't have the session manager daemon to write and sign the proto
// blob. This test just opens and closes the bubble to make sure there are no
// crashes.
TEST_F(ChromeLabsCoordinatorTest, ShowBubbleWhenUserIsOwner) {
  chrome_labs_coordinator_->Show(
      ChromeLabsCoordinator::ShowUserType::kChromeOsOwnerUserType);
  views::test::WidgetDestroyedWaiter destroyed_waiter(
      chrome_labs_coordinator_->GetChromeLabsBubbleView()->GetWidget());
  chrome_labs_coordinator_->Hide();
  destroyed_waiter.Wait();
  chrome_labs_coordinator_->Show(
      ChromeLabsCoordinator::ShowUserType::kChromeOsOwnerUserType);
}

#endif  // BUILDFLAG(IS_CHROMEOS_ASH)

class ChromeLabsViewControllerTest : public TestWithBrowserView {};

class ChromeLabsFeatureTest : public ChromeLabsViewControllerTest,
                              public testing::WithParamInterface<int> {};

#if !BUILDFLAG(IS_CHROMEOS_ASH)
// This test checks that selecting an option through the combobox on a lab will
// enable the corresponding option on the feature.
TEST_P(ChromeLabsFeatureTest, ChangeSelectedOption) {}

// For FeatureEntries of type FEATURE_VALUE, the option at index 1 corresponds
// to "Enabled" and the option at index 2 corresponds to "Disabled". For
// FeatureEntries of type FEATURE_WITH_PARAMS_VALUE, the option at index 1
// corresponds to "Enabled" and the option at index 2 corresponds to the first
// additional parameter.
INSTANTIATE_TEST_SUITE_P();

// This test checks that selecting row 0 will reset the feature to it's Default
// state.
TEST_F(ChromeLabsViewControllerTest, ResetToDefault) {}

#endif  // !BUILDFLAG(IS_CHROMEOS_ASH)

// Ash versions of the above tests.
#if BUILDFLAG(IS_CHROMEOS_ASH)

namespace ash {

class ChromeLabsAshFeatureTest : public ChromeLabsFeatureTest {
 public:
  ChromeLabsAshFeatureTest() {
    SessionManagerClient::InitializeFakeInMemory();
    FakeSessionManagerClient::Get()->set_supports_browser_restart(true);
  }
};

TEST_P(ChromeLabsAshFeatureTest, ChangeSelectedOption) {
  int row = GetParam();
  std::unique_ptr<ChromeLabsViewController> view_controller =
      CreateViewController();

  // FeatureEntry of type FEATURE_VALUE
  ChromeLabsItemView* lab_item = first_lab_item();
  views::Combobox* lab_item_combobox =
      lab_item->GetLabStateComboboxForTesting();

  lab_item_combobox->SetSelectedRow(row);

  const flags_ui::FeatureEntry* feature_entry = lab_item->GetFeatureEntry();

  EXPECT_TRUE(IsSelected(row, feature_entry, GetFlagsStorage()));

  // FeatureEntry of type FEATURE_WITH_PARAMS_VALUE
  ChromeLabsItemView* lab_item_with_params = second_lab_item();
  views::Combobox* lab_item_with_params_combobox =
      lab_item_with_params->GetLabStateComboboxForTesting();
  lab_item_with_params_combobox->SetSelectedRow(row);

  const flags_ui::FeatureEntry* feature_entry_with_params =
      lab_item_with_params->GetFeatureEntry();
  EXPECT_TRUE(IsSelected(row, feature_entry_with_params, GetFlagsStorage()));

  // Make sure flags have been set since ChromeOS should apply flags through
  // the session manager.
  AccountId user_id =
      user_manager::UserManager::Get()->GetActiveUser()->GetAccountId();
  std::vector<std::string> raw_flags;
  FakeSessionManagerClient* session_manager = FakeSessionManagerClient::Get();
  view_controller->RestartToApplyFlagsForTesting();
  const bool has_user_flags = session_manager->GetFlagsForUser(
      cryptohome::CreateAccountIdentifierFromAccountId(user_id), &raw_flags);
  EXPECT_TRUE(has_user_flags);
}

INSTANTIATE_TEST_SUITE_P(All, ChromeLabsAshFeatureTest, testing::Values(1, 2));

TEST_F(ChromeLabsViewControllerTest, ResetToDefault) {
  std::unique_ptr<ChromeLabsViewController> view_controller =
      CreateViewController();

  ChromeLabsItemView* lab_item = first_lab_item();
  views::Combobox* lab_item_combobox =
      lab_item->GetLabStateComboboxForTesting();

  // Selects an option and then attempts to reset the lab to Default by
  // selecting 0.
  const flags_ui::FeatureEntry* feature_entry = lab_item->GetFeatureEntry();
  lab_item_combobox->SetSelectedRow(1);

  EXPECT_FALSE(IsDefault(feature_entry, GetFlagsStorage()));
  lab_item_combobox->SetSelectedRow(0);
  EXPECT_TRUE(IsDefault(feature_entry, GetFlagsStorage()));
}

}  // namespace ash

#endif  // BUILDFLAG(IS_CHROMEOS_ASH)

// This test checks that only the two features that are supported on the current
// platform and do not have expired flags are added to the bubble.
TEST_F(ChromeLabsViewControllerTest, OnlyCompatibleFeaturesShow) {}

// This test checks that the restart prompt becomes visible when a lab state is
// changed.
TEST_F(ChromeLabsViewControllerTest, RestartPromptShows) {}

// This test checks that the restart prompt does not show when the lab state has
// not changed.
// TODO(elainechien): This currently only works for default. This will be
// changed to work for all states. See design doc in crbug/1145666.
TEST_F(ChromeLabsViewControllerTest, SelectDefaultTwiceNoRestart) {}

// TODO(crbug.com/40719879)
#if !BUILDFLAG(IS_CHROMEOS_LACROS)
// TODO(b/185480535): Fix the test for WebUIFeedback
TEST_F(ChromeLabsViewControllerTest, DISABLED_ShowFeedbackPage) {}
#endif

// This test checks that experiments that are removed from the model will be
// removed from the PrefService when updating new badge prefs.
TEST_F(ChromeLabsViewControllerTest, CleanUpNewBadgePrefsTest) {}

#endif  // !BUILDFLAG(IS_CHROMEOS_ASH) || !BUILDFLAG(GOOGLE_CHROME_BRANDING)