#include "chrome/browser/profiles/profile.h"
#include <stddef.h>
#include <memory>
#include "base/check.h"
#include "base/command_line.h"
#include "base/containers/contains.h"
#include "base/files/file_path.h"
#include "base/files/file_util.h"
#include "base/files/scoped_temp_dir.h"
#include "base/functional/bind.h"
#include "base/json/json_reader.h"
#include "base/memory/raw_ptr.h"
#include "base/memory/ref_counted.h"
#include "base/memory/weak_ptr.h"
#include "base/no_destructor.h"
#include "base/path_service.h"
#include "base/run_loop.h"
#include "base/scoped_multi_source_observation.h"
#include "base/synchronization/waitable_event.h"
#include "base/task/sequenced_task_runner.h"
#include "base/task/single_thread_task_runner.h"
#include "base/task/thread_pool/thread_pool_instance.h"
#include "base/test/bind.h"
#include "base/test/metrics/histogram_tester.h"
#include "base/test/scoped_feature_list.h"
#include "base/threading/thread_restrictions.h"
#include "base/values.h"
#include "base/version.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "chrome/browser/browser_features.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/profiles/chrome_version_service.h"
#include "chrome/browser/profiles/keep_alive/profile_keep_alive_types.h"
#include "chrome/browser/profiles/keep_alive/scoped_profile_keep_alive.h"
#include "chrome/browser/profiles/profile_destroyer.h"
#include "chrome/browser/profiles/profile_impl.h"
#include "chrome/browser/profiles/profile_manager.h"
#include "chrome/browser/profiles/profile_observer.h"
#include "chrome/browser/profiles/profile_test_util.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/browser_list.h"
#include "chrome/browser/ui/tabs/tab_strip_model.h"
#include "chrome/browser/ui/test/test_browser_closed_waiter.h"
#include "chrome/common/chrome_constants.h"
#include "chrome/common/chrome_paths.h"
#include "chrome/common/pref_names.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chrome/test/base/profile_destruction_waiter.h"
#include "chrome/test/base/testing_profile.h"
#include "chrome/test/base/ui_test_utils.h"
#include "components/keep_alive_registry/keep_alive_types.h"
#include "components/keep_alive_registry/scoped_keep_alive.h"
#include "components/prefs/pref_service.h"
#include "components/profile_metrics/browser_profile_type.h"
#include "components/version_info/version_info.h"
#include "content/public/browser/browser_task_traits.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/storage_partition.h"
#include "content/public/test/browser_test.h"
#include "content/public/test/test_utils.h"
#include "extensions/buildflags/buildflags.h"
#include "mojo/public/cpp/bindings/remote.h"
#include "net/base/load_flags.h"
#include "net/base/net_errors.h"
#include "net/dns/mock_host_resolver.h"
#include "net/net_buildflags.h"
#include "net/test/embedded_test_server/embedded_test_server.h"
#include "net/test/url_request/url_request_failed_job.h"
#include "net/traffic_annotation/network_traffic_annotation_test_helper.h"
#include "services/network/public/cpp/features.h"
#include "services/network/public/cpp/resource_request.h"
#include "services/network/public/cpp/simple_url_loader.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "url/gurl.h"
#include "url/url_constants.h"
#if BUILDFLAG(IS_CHROMEOS_ASH)
#include "ash/constants/ash_switches.h"
#include "chrome/browser/ash/profiles/profile_helper.h"
#endif
#if BUILDFLAG(ENABLE_EXTENSIONS)
#include "extensions/browser/extension_protocols.h"
#include "extensions/browser/extension_registry.h"
#include "extensions/common/extension.h"
#include "extensions/common/extension_builder.h"
#endif
#if BUILDFLAG(IS_CHROMEOS_LACROS)
#include "base/strings/utf_string_conversions.h"
#include "chrome/browser/profiles/profile_attributes_entry.h"
#include "chrome/browser/profiles/profile_attributes_storage.h"
#include "chromeos/crosapi/mojom/crosapi.mojom.h"
#include "chromeos/startup/browser_init_params.h"
#include "chromeos/startup/browser_params_proxy.h"
#include "components/account_id/account_id.h"
#endif
#if BUILDFLAG(ENABLE_SESSION_SERVICE)
#include "chrome/browser/sessions/exit_type_service.h"
#endif
namespace {
class SimpleURLLoaderHelper { … };
class MockProfileDelegate : public Profile::Delegate { … };
void CreatePrefsFileInDirectory(const base::FilePath& directory_path) { … }
void CheckChromeVersion(Profile* profile, bool is_new) { … }
void FlushTaskRunner(base::SequencedTaskRunner* runner) { … }
void SpinThreads() { … }
}
class ProfileBrowserTest : public InProcessBrowserTest { … };
#if BUILDFLAG(IS_CHROMEOS_ASH) || BUILDFLAG(IS_MAC)
#define MAYBE_CreateNewProfileSynchronous …
#else
#define MAYBE_CreateNewProfileSynchronous …
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, MAYBE_CreateNewProfileSynchronous) { … }
#if BUILDFLAG(IS_MAC) || (BUILDFLAG(IS_CHROMEOS) && defined(NDEBUG))
#define MAYBE_CreateOldProfileSynchronous …
#else
#define MAYBE_CreateOldProfileSynchronous …
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, MAYBE_CreateOldProfileSynchronous) { … }
#if BUILDFLAG(IS_CHROMEOS_ASH) || BUILDFLAG(IS_MAC)
#define MAYBE_CreateNewProfileAsynchronous …
#else
#define MAYBE_CreateNewProfileAsynchronous …
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, MAYBE_CreateNewProfileAsynchronous) { … }
#if BUILDFLAG(IS_CHROMEOS_ASH) || BUILDFLAG(IS_MAC)
#define MAYBE_CreateOldProfileAsynchronous …
#else
#define MAYBE_CreateOldProfileAsynchronous …
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, MAYBE_CreateOldProfileAsynchronous) { … }
#if BUILDFLAG(IS_CHROMEOS_ASH) || BUILDFLAG(IS_MAC)
#define MAYBE_ProfileReadmeCreated …
#else
#define MAYBE_ProfileReadmeCreated …
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, MAYBE_ProfileReadmeCreated) { … }
#if BUILDFLAG(IS_WIN) || BUILDFLAG(IS_OZONE)
namespace {
std::string GetExitTypePreferenceFromDisk(Profile* profile) { … }
}
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest,
WritesProfilesSynchronouslyOnEndSession) { … }
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest,
SimpleURLLoaderUsingMainContextDuringShutdown) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest,
SimpleURLLoaderUsingMainContextDuringIncognitoTeardown) { … }
#if BUILDFLAG(ENABLE_EXTENSIONS)
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest,
ExtensionURLLoaderFactoryAfterIncognitoTeardown) { … }
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, DiskCacheDirOverride) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, LastSelectedDirectory) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, CreateNonPrimaryOTR) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, CreateTwoNonPrimaryOTRs) { … }
class ProfileBrowserTestWithoutDestroyProfile : public ProfileBrowserTest { … };
#if BUILDFLAG(IS_CHROMEOS)
#define MAYBE_DestroyRegularProfileBeforeOTRs …
#else
#define MAYBE_DestroyRegularProfileBeforeOTRs …
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTestWithoutDestroyProfile,
MAYBE_DestroyRegularProfileBeforeOTRs) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, DestroyOnOTRProfileAmongMany) { … }
#if !BUILDFLAG(IS_CHROMEOS_ASH)
class ProfileBrowserTestWithDestroyProfile : public ProfileBrowserTest { … };
#if !BUILDFLAG(IS_CHROMEOS_LACROS)
IN_PROC_BROWSER_TEST_F(ProfileBrowserTestWithDestroyProfile,
OTRProfileKeepsRegularProfileAlive) { … }
#endif
#if BUILDFLAG(IS_CHROMEOS_LACROS)
IN_PROC_BROWSER_TEST_F(ProfileBrowserTestWithDestroyProfile,
LacrosSecondaryProfilesDestroyOnBrowserClose) {
Profile* main_profile = browser()->profile();
ASSERT_TRUE(Profile::IsMainProfilePath(main_profile->GetPath()));
ProfileManager* profile_manager = g_browser_process->profile_manager();
Profile& secondary_profile = profiles::testing::CreateProfileSync(
profile_manager, profile_manager->GenerateNextProfileDirectoryPath());
ASSERT_FALSE(Profile::IsMainProfilePath(secondary_profile.GetPath()));
Browser* secondary_browser = CreateBrowser(&secondary_profile);
Browser* main_browser = browser();
EXPECT_TRUE(profile_manager->HasKeepAliveForTesting(
main_profile, ProfileKeepAliveOrigin::kLacrosMainProfile));
EXPECT_FALSE(profile_manager->HasKeepAliveForTesting(
&secondary_profile, ProfileKeepAliveOrigin::kLacrosMainProfile));
ProfileDestructionWaiter main_waiter(main_profile);
ProfileDestructionWaiter secondary_waiter(&secondary_profile);
CloseBrowserSynchronously(secondary_browser);
CloseBrowserSynchronously(main_browser);
base::RunLoop().RunUntilIdle();
EXPECT_FALSE(profile_manager->HasKeepAliveForTesting(
main_profile, ProfileKeepAliveOrigin::kBrowserWindow));
EXPECT_TRUE(profile_manager->HasKeepAliveForTesting(
main_profile, ProfileKeepAliveOrigin::kLacrosMainProfile));
EXPECT_FALSE(main_waiter.destroyed());
EXPECT_TRUE(secondary_waiter.destroyed());
}
#endif
#endif
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, TestGetAllOffTheRecordProfiles) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, TestIsSameOrParent) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest,
TestCreatingBrowserUsingNonPrimaryOffTheRecordProfile) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, TestProfileTypes) { … }
#if !BUILDFLAG(IS_ANDROID) && !BUILDFLAG(IS_CHROMEOS_ASH)
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, UnderOneMinute) { … }
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest, OneHour) { … }
#endif
#if BUILDFLAG(IS_CHROMEOS_LACROS)
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest,
IsMainProfileReturnsFalseForNonDefaultPaths) {
base::ScopedAllowBlockingForTesting allow_blocking;
base::ScopedTempDir temp_dir;
ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
{
base::FilePath profile_path = temp_dir.GetPath().Append("1Default");
std::unique_ptr<Profile> profile(
CreateProfile(profile_path, nullptr,
Profile::CreateMode::kSynchronous));
EXPECT_FALSE(profile->IsMainProfile());
FlushIoTaskRunnerAndSpinThreads();
}
FlushIoTaskRunnerAndSpinThreads();
}
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest,
IsMainProfileReturnsTrueForPublicSessions) {
base::ScopedAllowBlockingForTesting allow_blocking;
base::ScopedTempDir temp_dir;
ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
{
base::FilePath profile_path =
temp_dir.GetPath().Append(chrome::kInitialProfile);
std::unique_ptr<Profile> profile(
CreateProfile(profile_path, nullptr,
Profile::CreateMode::kSynchronous));
crosapi::mojom::BrowserInitParamsPtr init_params =
crosapi::mojom::BrowserInitParams::New();
init_params->session_type = crosapi::mojom::SessionType::kPublicSession;
chromeos::BrowserInitParams::SetInitParamsForTests(std::move(init_params));
EXPECT_EQ(chromeos::BrowserParamsProxy::Get()->SessionType(),
crosapi::mojom::SessionType::kPublicSession);
EXPECT_TRUE(profile->IsMainProfile());
FlushIoTaskRunnerAndSpinThreads();
}
FlushIoTaskRunnerAndSpinThreads();
}
IN_PROC_BROWSER_TEST_F(ProfileBrowserTest,
IsMainProfileReturnsTrueForWebKioskSession) {
base::ScopedAllowBlockingForTesting allow_blocking;
base::ScopedTempDir temp_dir;
ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
{
base::FilePath profile_path =
temp_dir.GetPath().Append(chrome::kInitialProfile);
std::unique_ptr<Profile> profile(
CreateProfile(profile_path, nullptr,
Profile::CreateMode::kSynchronous));
crosapi::mojom::BrowserInitParamsPtr init_params =
crosapi::mojom::BrowserInitParams::New();
init_params->session_type = crosapi::mojom::SessionType::kWebKioskSession;
chromeos::BrowserInitParams::SetInitParamsForTests(std::move(init_params));
EXPECT_EQ(chromeos::BrowserParamsProxy::Get()->SessionType(),
crosapi::mojom::SessionType::kWebKioskSession);
EXPECT_TRUE(profile->IsMainProfile());
FlushIoTaskRunnerAndSpinThreads();
}
FlushIoTaskRunnerAndSpinThreads();
}
IN_PROC_BROWSER_TEST_F(
ProfileBrowserTest,
IsMainProfileReturnsTrueForMainProfileInRegularSessions) {
const base::FilePath profile_path =
browser()->profile()->GetPath().DirName().Append(chrome::kInitialProfile);
Profile* profile =
g_browser_process->profile_manager()->GetProfileByPath(profile_path);
EXPECT_TRUE(profile->IsMainProfile());
}
IN_PROC_BROWSER_TEST_F(
ProfileBrowserTest,
IsMainProfileReturnsFalseForOTRProfileInRegularSessions) {
const base::FilePath profile_path =
browser()->profile()->GetPath().DirName().Append(chrome::kInitialProfile);
Profile* profile =
g_browser_process->profile_manager()->GetProfileByPath(profile_path);
EXPECT_FALSE(profile->GetPrimaryOTRProfile(true)
->IsMainProfile());
}
#endif