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

#include "chrome/browser/sessions/session_data_service.h"

#include <memory>

#include "base/functional/callback_forward.h"
#include "base/memory/raw_ptr.h"
#include "base/time/time.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/content_settings/cookie_settings_factory.h"
#include "chrome/browser/defaults.h"
#include "chrome/browser/extensions/extension_special_storage_policy.h"
#include "chrome/browser/lifetime/browser_shutdown.h"
#include "chrome/browser/sessions/session_data_deleter.h"
#include "chrome/browser/ui/browser_list.h"
#include "chrome/test/base/browser_with_test_window_test.h"
#include "chrome/test/base/testing_profile.h"
#include "chrome/test/base/testing_profile_manager.h"
#include "components/content_settings/core/browser/cookie_settings.h"
#include "components/content_settings/core/common/content_settings.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

using testing::_;
using testing::Mock;
using testing::StrictMock;

namespace {
// A test version of SessionDataDeleter that doesn't actually do any deletion.
class TestSessionDataDeleter : public SessionDataDeleter {
 public:
  TestSessionDataDeleter() : SessionDataDeleter(nullptr) {}
  MOCK_METHOD2(DeleteSessionOnlyData, void(bool, base::OnceClosure));
};

// Helper to run the callback received by DeleteSessionOnlyData.
void RunCallback(bool skip_session_cookies, base::OnceClosure callback) {
  std::move(callback).Run();
}
}  // namespace

class SessionDataServiceTest : public BrowserWithTestWindowTest {
 public:
  void SetUp() override {
    BrowserWithTestWindowTest::SetUp();
    auto cookie_settings = CookieSettingsFactory::GetForProfile(profile());
    cookie_settings->SetDefaultCookieSetting(CONTENT_SETTING_SESSION_ONLY);
    profile()->SetExtensionSpecialStoragePolicy(
        base::MakeRefCounted<ExtensionSpecialStoragePolicy>(
            cookie_settings.get()));
    RestartService(CreateDeleter());
  }

  void TearDown() override {
    session_data_service_.reset();
    browser_shutdown::SetTryingToQuit(false);
    BrowserWithTestWindowTest::TearDown();
  }

  std::unique_ptr<StrictMock<TestSessionDataDeleter>> CreateDeleter() {
    return std::make_unique<StrictMock<TestSessionDataDeleter>>();
  }

  // Simulates Chrome being restarted from the SessionDataService's perspective.
  void RestartService(
      std::unique_ptr<StrictMock<TestSessionDataDeleter>> deleter) {
    session_data_deleter_ = deleter.get();
    session_data_service_ =
        std::make_unique<SessionDataService>(profile(), std::move(deleter));
  }

  StrictMock<TestSessionDataDeleter>* deleter() {
    return session_data_deleter_;
  }
  SessionDataService* service() { return session_data_service_.get(); }

 private:
  raw_ptr<StrictMock<TestSessionDataDeleter>, DanglingUntriaged>
      session_data_deleter_;
  std::unique_ptr<SessionDataService> session_data_service_;
};

TEST_F(SessionDataServiceTest, StartCleanup) {
  EXPECT_CALL(*deleter(), DeleteSessionOnlyData(false, _));
  service()->StartCleanup();
  Mock::VerifyAndClearExpectations(deleter());
}

TEST_F(SessionDataServiceTest, CleanupOnWindowClosed) {
  const BrowserList* browser_list = BrowserList::GetInstance();
  EXPECT_EQ(1U, browser_list->size());

  auto new_browser = CreateBrowser(profile(), Browser::TYPE_NORMAL, false);
  EXPECT_EQ(2U, browser_list->size());

  new_browser.reset();
  EXPECT_EQ(1U, browser_list->size());
  Mock::VerifyAndClearExpectations(deleter());

  bool skip_session_cookies = browser_defaults::kBrowserAliveWithNoWindows;
  EXPECT_CALL(*deleter(), DeleteSessionOnlyData(skip_session_cookies, _));
  release_browser();
  EXPECT_EQ(0U, browser_list->size());
  Mock::VerifyAndClearExpectations(deleter());
}

TEST_F(SessionDataServiceTest, CleanupOnWindowClosedWithOtherProfileOpen) {
  const BrowserList* browser_list = BrowserList::GetInstance();
  EXPECT_EQ(1U, browser_list->size());

  auto* new_profile = profile_manager()->CreateTestingProfile("second_profile");
  auto new_browser = CreateBrowser(new_profile, Browser::TYPE_NORMAL, false);
  EXPECT_EQ(2U, browser_list->size());

  bool skip_session_cookies = browser_defaults::kBrowserAliveWithNoWindows;
  EXPECT_CALL(*deleter(), DeleteSessionOnlyData(skip_session_cookies, _));
  release_browser();
  EXPECT_EQ(1U, browser_list->size());
  Mock::VerifyAndClearExpectations(deleter());
}

TEST_F(SessionDataServiceTest, RepeatCleanupAfterNewWindowOpened) {
  // Close browser and expect cleanup.
  bool skip_session_cookies = browser_defaults::kBrowserAliveWithNoWindows;
  EXPECT_CALL(*deleter(), DeleteSessionOnlyData(skip_session_cookies, _));
  release_browser();
  Mock::VerifyAndClearExpectations(deleter());

  // Additional requests for cleanup will be ignored.
  service()->StartCleanup();
  Mock::VerifyAndClearExpectations(deleter());

  // Unless a new browser is opened.
  auto new_browser = CreateBrowser(profile(), Browser::TYPE_NORMAL, false);
  Mock::VerifyAndClearExpectations(deleter());

  // And another cleanup is started.
  EXPECT_CALL(*deleter(), DeleteSessionOnlyData(false, _));
  service()->StartCleanup();
  Mock::VerifyAndClearExpectations(deleter());
}

TEST_F(SessionDataServiceTest, SkipOnShutdown) {
  browser_shutdown::SetTryingToQuit(true);
  service()->StartCleanup();
  Mock::VerifyAndClearExpectations(deleter());

  // No deletion during shutdown but the deletion will continue on startup.
  browser_shutdown::SetTryingToQuit(false);
  auto new_deleter = CreateDeleter();
  EXPECT_CALL(*new_deleter, DeleteSessionOnlyData(true, _));
  RestartService(std::move(new_deleter));
  Mock::VerifyAndClearExpectations(deleter());
}

TEST_F(SessionDataServiceTest, NoContinuedDeletionWithoutSettings) {
  browser_shutdown::SetTryingToQuit(true);
  CookieSettingsFactory::GetForProfile(profile())->SetDefaultCookieSetting(
      CONTENT_SETTING_ALLOW);

  service()->StartCleanup();
  Mock::VerifyAndClearExpectations(deleter());

  // No deletion during shutdown and no deletion on startup without SESSION_ONLY
  // setting.
  browser_shutdown::SetTryingToQuit(false);
  RestartService(CreateDeleter());
  Mock::VerifyAndClearExpectations(deleter());
}

TEST_F(SessionDataServiceTest, ContinueUnfinishedDeletions) {
  EXPECT_CALL(*deleter(), DeleteSessionOnlyData(false, _));
  service()->StartCleanup();
  Mock::VerifyAndClearExpectations(deleter());

  // Deletion is not marked as finished, so it will continue on restart.
  auto new_deleter = CreateDeleter();
  EXPECT_CALL(*new_deleter, DeleteSessionOnlyData(true, _))
      .WillOnce(&RunCallback);
  RestartService(std::move(new_deleter));
  Mock::VerifyAndClearExpectations(deleter());

  // At shutdown, another deletion is started. This time it finishes.
  EXPECT_CALL(*deleter(), DeleteSessionOnlyData(false, _))
      .WillOnce(&RunCallback);
  service()->StartCleanup();
  Mock::VerifyAndClearExpectations(deleter());

  // A finished deletion does not continue after restart.
  RestartService(CreateDeleter());
  Mock::VerifyAndClearExpectations(deleter());
}

TEST_F(SessionDataServiceTest, SkipOnForceSessionState) {
  // No deletion when state should be kept.
  service()->SetForceKeepSessionState();
  service()->StartCleanup();
  Mock::VerifyAndClearExpectations(deleter());

  // Also deletion on restart after state was kept.
  RestartService(CreateDeleter());
  Mock::VerifyAndClearExpectations(deleter());
}
