blob: f7a3cb7afebed71fd20a6aa4c0f6bfeecbcd8c7e [file] [log] [blame]
// Copyright 2017 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_UI_BLOCKED_CONTENT_SAFE_BROWSING_TRIGGERED_POPUP_BLOCKER_H_
#define CHROME_BROWSER_UI_BLOCKED_CONTENT_SAFE_BROWSING_TRIGGERED_POPUP_BLOCKER_H_
#include <memory>
#include "base/feature_list.h"
#include "base/macros.h"
#include "base/optional.h"
#include "base/scoped_observer.h"
#include "components/safe_browsing/db/util.h"
#include "components/subresource_filter/content/browser/subresource_filter_observer.h"
#include "components/subresource_filter/content/browser/subresource_filter_observer_manager.h"
#include "content/public/browser/web_contents_observer.h"
namespace content {
struct OpenURLParams;
class WebContents;
} // namespace content
namespace user_prefs {
class PrefRegistrySyncable;
}
extern const base::Feature kAbusiveExperienceEnforce;
constexpr char kAbusiveEnforceMessage[] =
"Chrome prevented this site from opening a new tab or window. Learn more "
"at https://www.chromestatus.com/feature/5243055179300864";
constexpr char kAbusiveWarnMessage[] =
"Chrome might start preventing this site from opening new tabs or "
"windows in the future. Learn more at "
"https://www.chromestatus.com/feature/5243055179300864";
// This class observes main frame navigation checks incoming from safe browsing
// (currently implemented by the subresource_filter component). For navigations
// which match the ABUSIVE safe browsing list, this class will help the popup
// tab helper in applying a stronger policy for blocked popups.
class SafeBrowsingTriggeredPopupBlocker
: public content::WebContentsObserver,
public subresource_filter::SubresourceFilterObserver {
public:
// This enum backs a histogram. Please append new entries to the end, and
// update enums.xml when making changes.
enum class Action : int {
// User committed a navigation to a non-error page.
kNavigation,
// Safe Browsing considered this page abusive and the page should be warned.
// Logged at navigation commit.
kWarningSite,
// Safe Browsing considered this page abusive and the page should be be
// blocked against. Logged at navigation commit.
kEnforcedSite,
// The popup blocker called into this object to ask if the strong blocking
// should be applied.
kConsidered,
// This object responded to the popup blocker in the affirmative, and the
// popup was blocked.
kBlocked,
// Add new entries before this one
kCount
};
static void RegisterProfilePrefs(user_prefs::PrefRegistrySyncable* registry);
static std::unique_ptr<SafeBrowsingTriggeredPopupBlocker> MaybeCreate(
content::WebContents* web_contents);
~SafeBrowsingTriggeredPopupBlocker() override;
bool ShouldApplyStrongPopupBlocker(
const content::OpenURLParams* open_url_params);
private:
// The |web_contents| and |observer_manager| are expected to be
// non-nullptr.
SafeBrowsingTriggeredPopupBlocker(
content::WebContents* web_contents,
subresource_filter::SubresourceFilterObserverManager* observer_manager);
// content::WebContentsObserver:
void DidFinishNavigation(
content::NavigationHandle* navigation_handle) override;
// subresource_filter::SubresourceFilterObserver:
void OnSafeBrowsingChecksComplete(
content::NavigationHandle* navigation_handle,
const SafeBrowsingCheckResults& results) override;
void OnSubresourceFilterGoingAway() override;
// Enabled state is governed by both a feature flag and a pref (which can be
// controlled by enterprise policy).
static bool IsEnabled(const content::WebContents* web_contents);
// Data scoped to a single page. Will be reset at navigation commit.
class PageData {
public:
PageData();
// Logs UMA in the destructor based on the number of popups blocked.
~PageData();
void inc_num_popups_blocked() { ++num_popups_blocked_; }
void set_is_triggered(bool is_triggered) { is_triggered_ = is_triggered; }
bool is_triggered() const { return is_triggered_; }
private:
// How many popups are blocked in this page.
int num_popups_blocked_ = 0;
// Whether the current committed page load should trigger the stronger popup
// blocker.
bool is_triggered_ = false;
DISALLOW_COPY_AND_ASSIGN(PageData);
};
ScopedObserver<subresource_filter::SubresourceFilterObserverManager,
subresource_filter::SubresourceFilterObserver>
scoped_observer_;
// Whether the next main frame navigation that commits should trigger the
// stronger popup blocker in enforce or warn mode.
base::Optional<safe_browsing::SubresourceFilterLevel>
level_for_next_committed_navigation_;
// Should never be nullptr.
std::unique_ptr<PageData> current_page_data_;
DISALLOW_COPY_AND_ASSIGN(SafeBrowsingTriggeredPopupBlocker);
};
#endif // CHROME_BROWSER_UI_BLOCKED_CONTENT_SAFE_BROWSING_TRIGGERED_POPUP_BLOCKER_H_