Merge pull request #16080 from brave/android_safebrowsing_safetynet
Android safebrowsing safetynet
This commit is contained in:
@@ -3,6 +3,7 @@ import("//build/config/android/rules.gni")
|
||||
|
||||
declare_args() {
|
||||
brave_android_developer_options_code = ""
|
||||
brave_safebrowsing_api_key = ""
|
||||
}
|
||||
|
||||
java_cpp_enum("brave_android_java_enums_srcjar") {
|
||||
@@ -17,5 +18,6 @@ java_cpp_template("brave_config_java") {
|
||||
defines = [
|
||||
"BRAVE_ANDROID_DEVELOPER_OPTIONS_CODE=\"$brave_android_developer_options_code\"",
|
||||
"BRAVE_ANDROID_P3A_ENABLED=$brave_p3a_enabled",
|
||||
"BRAVE_SAFEBROWSING_API_KEY=\"$brave_safebrowsing_api_key\"",
|
||||
]
|
||||
}
|
||||
|
||||
@@ -277,6 +277,7 @@ brave_java_sources = [
|
||||
"../../brave/android/java/org/chromium/chrome/browser/rewards/BraveRewardsTipFailureFragment.java",
|
||||
"../../brave/android/java/org/chromium/chrome/browser/rewards/BraveRewardsTippingPanelFragment.java",
|
||||
"../../brave/android/java/org/chromium/chrome/browser/safe_browsing/settings/BraveStandardProtectionSettingsFragment.java",
|
||||
"../../brave/android/java/org/chromium/chrome/browser/safe_browsing/settings/NoGooglePlayServicesDialog.java",
|
||||
"../../brave/android/java/org/chromium/chrome/browser/searchwidget/SearchWidgetProviderActivity.java",
|
||||
"../../brave/android/java/org/chromium/chrome/browser/set_default_browser/BraveSetDefaultBrowserUtils.java",
|
||||
"../../brave/android/java/org/chromium/chrome/browser/set_default_browser/OnBraveSetDefaultBrowserListener.java",
|
||||
|
||||
@@ -16,6 +16,7 @@ public abstract class BraveFeatureList {
|
||||
public static final String BRAVE_BACKGROUND_VIDEO_PLAYBACK = "BraveBackgroundVideoPlayback";
|
||||
public static final String BRAVE_BACKGROUND_VIDEO_PLAYBACK_INTERNAL =
|
||||
"brave-background-video-playback";
|
||||
public static final String BRAVE_ANDROID_SAFE_BROWSING = "BraveAndroidSafeBrowsing";
|
||||
public static final String BRAVE_VPN_LINK_SUBSCRIPTION_ANDROID_UI =
|
||||
"BraveVPNLinkSubscriptionAndroidUI";
|
||||
}
|
||||
|
||||
@@ -80,6 +80,7 @@ import org.chromium.chrome.R;
|
||||
import org.chromium.chrome.browser.ApplicationLifetime;
|
||||
import org.chromium.chrome.browser.BraveAdFreeCalloutDialogFragment;
|
||||
import org.chromium.chrome.browser.BraveAdaptiveCaptchaUtils;
|
||||
import org.chromium.chrome.browser.BraveConfig;
|
||||
import org.chromium.chrome.browser.BraveFeatureUtil;
|
||||
import org.chromium.chrome.browser.BraveHelper;
|
||||
import org.chromium.chrome.browser.BraveRelaunchUtils;
|
||||
@@ -146,6 +147,8 @@ import org.chromium.chrome.browser.privacy.settings.BravePrivacySettings;
|
||||
import org.chromium.chrome.browser.profiles.Profile;
|
||||
import org.chromium.chrome.browser.rate.RateDialogFragment;
|
||||
import org.chromium.chrome.browser.rate.RateUtils;
|
||||
import org.chromium.chrome.browser.safe_browsing.SafeBrowsingBridge;
|
||||
import org.chromium.chrome.browser.safe_browsing.SafeBrowsingState;
|
||||
import org.chromium.chrome.browser.set_default_browser.BraveSetDefaultBrowserUtils;
|
||||
import org.chromium.chrome.browser.set_default_browser.OnBraveSetDefaultBrowserListener;
|
||||
import org.chromium.chrome.browser.settings.BraveNewsPreferences;
|
||||
@@ -182,6 +185,8 @@ import org.chromium.chrome.browser.vpn.wireguard.WireguardConfigUtils;
|
||||
import org.chromium.components.browser_ui.settings.SettingsLauncher;
|
||||
import org.chromium.components.embedder_support.util.UrlConstants;
|
||||
import org.chromium.components.embedder_support.util.UrlUtilities;
|
||||
import org.chromium.components.safe_browsing.BraveSafeBrowsingApiHandler;
|
||||
import org.chromium.components.safe_browsing.SafeBrowsingApiBridge;
|
||||
import org.chromium.components.search_engines.TemplateUrl;
|
||||
import org.chromium.components.user_prefs.UserPrefs;
|
||||
import org.chromium.content_public.browser.WebContents;
|
||||
@@ -204,7 +209,8 @@ import java.util.concurrent.CopyOnWriteArrayList;
|
||||
@JNINamespace("chrome::android")
|
||||
public abstract class BraveActivity<C extends ChromeActivityComponent> extends ChromeActivity
|
||||
implements BrowsingDataBridge.OnClearBrowsingDataListener, BraveVpnObserver,
|
||||
OnBraveSetDefaultBrowserListener, ConnectionErrorHandler, PrefObserver {
|
||||
OnBraveSetDefaultBrowserListener, ConnectionErrorHandler, PrefObserver,
|
||||
BraveSafeBrowsingApiHandler.BraveSafeBrowsingApiHandlerDelegate {
|
||||
public static final String ADD_FUNDS_URL = "brave://rewards/#add-funds";
|
||||
public static final String BRAVE_REWARDS_SETTINGS_URL = "brave://rewards/";
|
||||
public static final String BRAVE_REWARDS_SETTINGS_WALLET_VERIFICATION_URL =
|
||||
@@ -235,6 +241,8 @@ public abstract class BraveActivity<C extends ChromeActivityComponent> extends C
|
||||
private static final List<String> yandexRegions =
|
||||
Arrays.asList("AM", "AZ", "BY", "KG", "KZ", "MD", "RU", "TJ", "TM", "UZ");
|
||||
|
||||
private BraveSafeBrowsingApiHandler mBraveSafeBrowsingApiHandler;
|
||||
|
||||
private String mPurchaseToken = "";
|
||||
private String mProductId = "";
|
||||
private boolean mIsVerification;
|
||||
@@ -293,6 +301,15 @@ public abstract class BraveActivity<C extends ChromeActivityComponent> extends C
|
||||
}
|
||||
updateWalletBadgeVisibility();
|
||||
}
|
||||
boolean safeBrowsingFlagEnabled =
|
||||
ChromeFeatureList.isEnabled(BraveFeatureList.BRAVE_ANDROID_SAFE_BROWSING);
|
||||
boolean safeBrowsingPrefEnabled =
|
||||
SafeBrowsingBridge.getSafeBrowsingState() != SafeBrowsingState.NO_SAFE_BROWSING;
|
||||
if (safeBrowsingFlagEnabled && safeBrowsingPrefEnabled) {
|
||||
mBraveSafeBrowsingApiHandler.initSafeBrowsing();
|
||||
} else if (!safeBrowsingFlagEnabled && safeBrowsingPrefEnabled) {
|
||||
SafeBrowsingBridge.setSafeBrowsingState(SafeBrowsingState.NO_SAFE_BROWSING);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -765,6 +782,18 @@ public abstract class BraveActivity<C extends ChromeActivityComponent> extends C
|
||||
|
||||
PostTask.postTask(
|
||||
TaskTraits.BEST_EFFORT_MAY_BLOCK, () -> { BraveStatsUtil.removeShareStatsFile(); });
|
||||
if (mBraveSafeBrowsingApiHandler == null) {
|
||||
mBraveSafeBrowsingApiHandler =
|
||||
new BraveSafeBrowsingApiHandler(this, BraveConfig.SAFEBROWSING_API_KEY, this);
|
||||
SafeBrowsingApiBridge.setHandler(mBraveSafeBrowsingApiHandler);
|
||||
SafeBrowsingApiBridge.ensureInitialized();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPause() {
|
||||
super.onPause();
|
||||
mBraveSafeBrowsingApiHandler.shutdownSafeBrowsing();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -788,6 +817,11 @@ public abstract class BraveActivity<C extends ChromeActivityComponent> extends C
|
||||
maybeSolveAdaptiveCaptcha();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void turnSafeBrowsingOff() {
|
||||
SafeBrowsingBridge.setSafeBrowsingState(SafeBrowsingState.NO_SAFE_BROWSING);
|
||||
}
|
||||
|
||||
public void maybeSolveAdaptiveCaptcha() {
|
||||
String captchaID = UserPrefs.get(Profile.getLastUsedRegularProfile())
|
||||
.getString(BravePref.SCHEDULED_CAPTCHA_ID);
|
||||
|
||||
+21
-1
@@ -13,11 +13,13 @@ import androidx.preference.ListPreference;
|
||||
import androidx.preference.Preference;
|
||||
import androidx.preference.PreferenceCategory;
|
||||
|
||||
import org.chromium.base.BraveFeatureList;
|
||||
import org.chromium.base.ContextUtils;
|
||||
import org.chromium.base.Log;
|
||||
import org.chromium.brave_shields.mojom.CookieListOptInPageAndroidHandler;
|
||||
import org.chromium.chrome.R;
|
||||
import org.chromium.chrome.browser.BraveConfig;
|
||||
import org.chromium.chrome.browser.flags.ChromeFeatureList;
|
||||
import org.chromium.chrome.browser.metrics.UmaSessionStats;
|
||||
import org.chromium.chrome.browser.preferences.BravePref;
|
||||
import org.chromium.chrome.browser.preferences.BravePrefServiceBridge;
|
||||
@@ -27,6 +29,7 @@ import org.chromium.chrome.browser.preferences.website.BraveShieldsContentSettin
|
||||
import org.chromium.chrome.browser.privacy.settings.PrivacyPreferencesManagerImpl;
|
||||
import org.chromium.chrome.browser.privacy.settings.PrivacySettings;
|
||||
import org.chromium.chrome.browser.profiles.Profile;
|
||||
import org.chromium.chrome.browser.safe_browsing.settings.NoGooglePlayServicesDialog;
|
||||
import org.chromium.chrome.browser.settings.BraveDialogPreference;
|
||||
import org.chromium.chrome.browser.settings.BravePreferenceDialogFragment;
|
||||
import org.chromium.chrome.browser.settings.BraveWebrtcPolicyPreference;
|
||||
@@ -38,6 +41,7 @@ import org.chromium.components.browser_ui.settings.ChromeSwitchPreference;
|
||||
import org.chromium.components.browser_ui.settings.SettingsUtils;
|
||||
import org.chromium.components.prefs.PrefService;
|
||||
import org.chromium.components.user_prefs.UserPrefs;
|
||||
import org.chromium.gms.ChromiumPlayServicesAvailability;
|
||||
import org.chromium.mojo.bindings.ConnectionErrorHandler;
|
||||
import org.chromium.mojo.system.MojoException;
|
||||
|
||||
@@ -276,7 +280,23 @@ public class BravePrivacySettings extends PrivacySettings implements ConnectionE
|
||||
removePreferenceIfPresent(PREF_SYNC_AND_SERVICES_LINK);
|
||||
removePreferenceIfPresent(PREF_NETWORK_PREDICTIONS);
|
||||
removePreferenceIfPresent(PREF_PRIVACY_SANDBOX);
|
||||
removePreferenceIfPresent(PREF_SAFE_BROWSING);
|
||||
if (!ChromeFeatureList.isEnabled(BraveFeatureList.BRAVE_ANDROID_SAFE_BROWSING)) {
|
||||
removePreferenceIfPresent(PREF_SAFE_BROWSING);
|
||||
} else {
|
||||
Preference preference = getPreferenceScreen().findPreference(PREF_SAFE_BROWSING);
|
||||
if (preference != null) {
|
||||
preference.setOnPreferenceClickListener((pref) -> {
|
||||
if (!ChromiumPlayServicesAvailability.isGooglePlayServicesAvailable(
|
||||
getActivity())) {
|
||||
NoGooglePlayServicesDialog.create(getContext()).show();
|
||||
// Don't show the menu if Google Play Services are not available
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
if (mCookieListOptInPageAndroidHandler != null) {
|
||||
mCookieListOptInPageAndroidHandler.shouldShowDialog(shouldShowDialog -> {
|
||||
|
||||
+66
@@ -0,0 +1,66 @@
|
||||
/* Copyright (c) 2022 The Brave Authors. All rights reserved.
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
* You can obtain one at https://mozilla.org/MPL/2.0/. */
|
||||
|
||||
package org.chromium.chrome.browser.safe_browsing.settings;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.res.Resources;
|
||||
|
||||
import org.chromium.components.browser_ui.modaldialog.AppModalPresenter;
|
||||
import org.chromium.ui.modaldialog.DialogDismissalCause;
|
||||
import org.chromium.ui.modaldialog.ModalDialogManager;
|
||||
import org.chromium.ui.modaldialog.ModalDialogManager.ModalDialogType;
|
||||
import org.chromium.ui.modaldialog.ModalDialogProperties;
|
||||
import org.chromium.ui.modaldialog.ModalDialogProperties.Controller;
|
||||
import org.chromium.ui.modelutil.PropertyModel;
|
||||
|
||||
/**
|
||||
* Dialog to notify that the user is not protected by Safe Browsing as Google Play Services are not
|
||||
* available.
|
||||
*/
|
||||
public class NoGooglePlayServicesDialog {
|
||||
private Context mContext;
|
||||
private ModalDialogManager mManager;
|
||||
private PropertyModel mModel;
|
||||
|
||||
public static NoGooglePlayServicesDialog create(Context context) {
|
||||
return new NoGooglePlayServicesDialog(context);
|
||||
}
|
||||
|
||||
private NoGooglePlayServicesDialog(Context context) {
|
||||
mContext = context;
|
||||
}
|
||||
|
||||
/** Show this dialog in the context of its enclosing activity. */
|
||||
public void show() {
|
||||
Resources resources = mContext.getResources();
|
||||
PropertyModel.Builder builder =
|
||||
new PropertyModel.Builder(ModalDialogProperties.ALL_KEYS)
|
||||
.with(ModalDialogProperties.CONTROLLER, makeController())
|
||||
.with(ModalDialogProperties.TITLE, resources,
|
||||
R.string.safe_browsing_no_google_play_services_dialog_title)
|
||||
.with(ModalDialogProperties.MESSAGE_PARAGRAPH_1,
|
||||
resources.getString(
|
||||
R.string.safe_browsing_no_google_play_services_dialog_message))
|
||||
.with(ModalDialogProperties.POSITIVE_BUTTON_TEXT, resources, R.string.ok);
|
||||
mModel = builder.build();
|
||||
mManager = new ModalDialogManager(new AppModalPresenter(mContext), ModalDialogType.APP);
|
||||
mManager.showDialog(mModel, ModalDialogType.APP);
|
||||
}
|
||||
|
||||
private Controller makeController() {
|
||||
return new ModalDialogProperties.Controller() {
|
||||
@Override
|
||||
public void onClick(PropertyModel model, int buttonType) {
|
||||
mManager.dismissDialog(mModel, DialogDismissalCause.POSITIVE_BUTTON_CLICKED);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDismiss(PropertyModel model, int dismissalCause) {
|
||||
mManager.destroy();
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
+15
-1
@@ -58,6 +58,7 @@
|
||||
|
||||
#if BUILDFLAG(IS_ANDROID)
|
||||
#include "brave/browser/android/preferences/features.h"
|
||||
#include "brave/browser/android/safe_browsing/features.h"
|
||||
#endif
|
||||
|
||||
using brave_shields::features::kBraveAdblockCnameUncloaking;
|
||||
@@ -83,6 +84,7 @@ using ntp_background_images::features::kBraveNTPSuperReferralWallpaper;
|
||||
|
||||
#if BUILDFLAG(IS_ANDROID)
|
||||
using preferences::features::kBraveBackgroundVideoPlayback;
|
||||
using safe_browsing::features::kBraveAndroidSafeBrowsing;
|
||||
#endif
|
||||
|
||||
namespace flag_descriptions {
|
||||
@@ -400,6 +402,10 @@ constexpr char kBraveBackgroundVideoPlaybackDescription[] =
|
||||
"Enables play audio from video in background when tab is not active or "
|
||||
"device screen is turned off. Try to switch to desktop mode if this "
|
||||
"feature is not working.";
|
||||
constexpr char kBraveAndroidSafeBrowsingName[] = "Safe Browsing";
|
||||
constexpr char kBraveAndroidSafeBrowsingDescription[] =
|
||||
"Enables Google Safe Browsing for determining whether a URL has been "
|
||||
"marked as a known threat.";
|
||||
#endif
|
||||
} // namespace
|
||||
|
||||
@@ -563,8 +569,15 @@ constexpr char kBraveBackgroundVideoPlaybackDescription[] =
|
||||
flag_descriptions::kBraveBackgroundVideoPlaybackDescription, \
|
||||
kOsAndroid, \
|
||||
FEATURE_VALUE_TYPE(kBraveBackgroundVideoPlayback)},
|
||||
#define BRAVE_SAFE_BROWSING_ANDROID \
|
||||
{"brave-safe-browsing", \
|
||||
flag_descriptions::kBraveAndroidSafeBrowsingName, \
|
||||
flag_descriptions::kBraveAndroidSafeBrowsingDescription, \
|
||||
kOsAndroid, \
|
||||
FEATURE_VALUE_TYPE(kBraveAndroidSafeBrowsing)},
|
||||
#else
|
||||
#define BRAVE_BACKGROUND_VIDEO_PLAYBACK_ANDROID
|
||||
#define BRAVE_SAFE_BROWSING_ANDROID
|
||||
#endif // BUILDFLAG(IS_ANDROID)
|
||||
|
||||
#define BRAVE_ABOUT_FLAGS_FEATURE_ENTRIES \
|
||||
@@ -727,4 +740,5 @@ constexpr char kBraveBackgroundVideoPlaybackDescription[] =
|
||||
BRAVE_FEDERATED_FEATURE_ENTRIES \
|
||||
PLAYLIST_FEATURE_ENTRIES \
|
||||
BRAVE_VERTICAL_TABS_FEATURE_ENTRY \
|
||||
BRAVE_BACKGROUND_VIDEO_PLAYBACK_ANDROID
|
||||
BRAVE_BACKGROUND_VIDEO_PLAYBACK_ANDROID \
|
||||
BRAVE_SAFE_BROWSING_ANDROID
|
||||
|
||||
@@ -17,6 +17,7 @@ source_set("android_browser_process") {
|
||||
deps = [
|
||||
"//base",
|
||||
"//brave/browser/android/preferences",
|
||||
"//brave/browser/android/safe_browsing",
|
||||
"//brave/browser/brave_ads/android:jni_headers",
|
||||
"//brave/build/android:jni_headers",
|
||||
"//brave/components/brave_ads/browser",
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
# Copyright (c) 2022 The Brave Authors. All rights reserved.
|
||||
# This Source Code Form is subject to the terms of the Mozilla Public
|
||||
# License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
# You can obtain one at https://mozilla.org/MPL/2.0/.
|
||||
|
||||
import("//build/config/android/rules.gni")
|
||||
|
||||
source_set("safe_browsing") {
|
||||
sources = [
|
||||
"features.cc",
|
||||
"features.h",
|
||||
]
|
||||
|
||||
deps = [ "//base" ]
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
/* Copyright (c) 2022 The Brave Authors. All rights reserved.
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
* You can obtain one at https://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "brave/browser/android/safe_browsing/features.h"
|
||||
|
||||
#include "base/feature_list.h"
|
||||
|
||||
namespace safe_browsing {
|
||||
namespace features {
|
||||
|
||||
BASE_FEATURE(kBraveAndroidSafeBrowsing,
|
||||
"BraveAndroidSafeBrowsing",
|
||||
base::FEATURE_DISABLED_BY_DEFAULT);
|
||||
|
||||
} // namespace features
|
||||
} // namespace safe_browsing
|
||||
@@ -0,0 +1,19 @@
|
||||
/* Copyright (c) 2022 The Brave Authors. All rights reserved.
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
* You can obtain one at https://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef BRAVE_BROWSER_ANDROID_SAFE_BROWSING_FEATURES_H_
|
||||
#define BRAVE_BROWSER_ANDROID_SAFE_BROWSING_FEATURES_H_
|
||||
|
||||
#include "base/feature_list.h"
|
||||
|
||||
namespace safe_browsing {
|
||||
namespace features {
|
||||
|
||||
BASE_DECLARE_FEATURE(kBraveAndroidSafeBrowsing);
|
||||
|
||||
} // namespace features
|
||||
} // namespace safe_browsing
|
||||
|
||||
#endif // BRAVE_BROWSER_ANDROID_SAFE_BROWSING_FEATURES_H_
|
||||
@@ -3309,6 +3309,12 @@ If you don't accept this request, VPN will not reconnect and your internet conne
|
||||
<message name="IDS_LINK_SUBSCRIPTION_DIALOG_TEXT" desc="Brave vpn link subscription dialog text">
|
||||
Your Brave VPN subscription can protect up to 5 devices, across Android, iOS, and desktop. Just link your Google Play subscription to your Brave account.
|
||||
</message>
|
||||
<message name="IDS_SAFE_BROWSING_NO_GOOGLE_PLAY_SERVICES_DIALOG_TITLE" desc="Brave no Google Play Services dialog title">
|
||||
Cannot enable Safe Browsing
|
||||
</message>
|
||||
<message name="IDS_SAFE_BROWSING_NO_GOOGLE_PLAY_SERVICES_DIALOG_MESSAGE" desc="Brave no Google Play Services dialog message">
|
||||
Safe Browsing has been disabled on your device. To enable it, ensure that Google Play Services is installed and that it's up to date.
|
||||
</message>
|
||||
</messages>
|
||||
</release>
|
||||
</grit>
|
||||
|
||||
@@ -25,6 +25,7 @@ brave_chrome_java_deps = [
|
||||
"//brave/components/brave_today/common:mojom_java",
|
||||
"//brave/components/brave_wallet/common:mojom_java",
|
||||
"//brave/components/browser_ui/site_settings/android:java",
|
||||
"//brave/components/safe_browsing/android:brave_safe_browsing_java",
|
||||
"//brave/components/variations/android:java",
|
||||
"//brave/third_party/android_deps:com_airbnb_android_java",
|
||||
"//brave/third_party/android_deps:com_android_billingclient_java",
|
||||
|
||||
@@ -16,8 +16,14 @@ public class BraveConfig {
|
||||
#endif
|
||||
|
||||
#if defined(BRAVE_ANDROID_P3A_ENABLED)
|
||||
public static final boolean P3A_ENABLED = BRAVE_ANDROID_P3A_ENABLED;
|
||||
public static final boolean P3A_ENABLED = BRAVE_ANDROID_P3A_ENABLED;
|
||||
#else
|
||||
public static final boolean P3A_ENABLED = false;
|
||||
public static final boolean P3A_ENABLED = false;
|
||||
#endif
|
||||
|
||||
#if defined(BRAVE_SAFEBROWSING_API_KEY)
|
||||
public static final String SAFEBROWSING_API_KEY = BRAVE_SAFEBROWSING_API_KEY;
|
||||
#else
|
||||
public static final String SAFEBROWSING_API_KEY = "";
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -170,6 +170,7 @@ const Config = function () {
|
||||
this.extraGnArgs = {}
|
||||
this.extraGnGenOpts = getNPMConfig(['brave_extra_gn_gen_opts']) || ''
|
||||
this.extraNinjaOpts = []
|
||||
this.braveAndroidSafeBrowsingApiKey = getNPMConfig(['brave_safebrowsing_api_key']) || ''
|
||||
this.braveSafetyNetApiKey = getNPMConfig(['brave_safetynet_api_key']) || ''
|
||||
this.braveAndroidDeveloperOptionsCode = getNPMConfig(['brave_android_developer_options_code']) || ''
|
||||
this.braveAndroidKeystorePath = getNPMConfig(['brave_android_keystore_path'])
|
||||
@@ -468,6 +469,7 @@ Config.prototype.buildArgs = function () {
|
||||
|
||||
args.brave_android_developer_options_code = this.braveAndroidDeveloperOptionsCode
|
||||
args.brave_safetynet_api_key = this.braveSafetyNetApiKey
|
||||
args.brave_safebrowsing_api_key = this.braveAndroidSafeBrowsingApiKey
|
||||
args.enable_widevine = false
|
||||
args.safe_browsing_mode = 2
|
||||
|
||||
@@ -718,6 +720,10 @@ Config.prototype.update = function (options) {
|
||||
this.braveGoogleApiKey = options.brave_google_api_key
|
||||
}
|
||||
|
||||
if (options.brave_safebrowsing_api_key) {
|
||||
this.braveAndroidSafeBrowsingApiKey = options.brave_safebrowsing_api_key
|
||||
}
|
||||
|
||||
if (options.brave_safetynet_api_key) {
|
||||
this.braveSafetyNetApiKey = options.brave_safetynet_api_key
|
||||
}
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
|
||||
#include "base/feature_override.h"
|
||||
#include "brave/browser/android/preferences/features.h"
|
||||
#include "brave/browser/android/safe_browsing/features.h"
|
||||
#include "brave/components/brave_rewards/common/features.h"
|
||||
#include "brave/components/brave_search_conversion/features.h"
|
||||
#include "brave/components/brave_today/common/features.h"
|
||||
@@ -17,10 +18,11 @@
|
||||
&brave_rewards::features::kBraveRewards, \
|
||||
&brave_search_conversion::features::kOmniboxBanner, \
|
||||
&brave_today::features::kBraveNewsFeature, \
|
||||
&brave_vpn::features::kBraveVPNLinkSubscriptionAndroidUI, \
|
||||
&brave_vpn::features::kBraveVPNLinkSubscriptionAndroidUI,\
|
||||
&brave_wallet::features::kNativeBraveWalletFeature, \
|
||||
&brave_wallet::features::kBraveWalletSolanaFeature, \
|
||||
&preferences::features::kBraveBackgroundVideoPlayback
|
||||
&preferences::features::kBraveBackgroundVideoPlayback, \
|
||||
&safe_browsing::features::kBraveAndroidSafeBrowsing
|
||||
// clang-format on
|
||||
|
||||
#include "src/chrome/browser/flags/android/chrome_feature_list.cc"
|
||||
|
||||
@@ -0,0 +1,19 @@
|
||||
# Copyright (c) 2022 The Brave Authors. All rights reserved.
|
||||
# This Source Code Form is subject to the terms of the Mozilla Public
|
||||
# License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
# You can obtain one at https://mozilla.org/MPL/2.0/.
|
||||
|
||||
import("//build/config/android/config.gni")
|
||||
import("//build/config/android/rules.gni")
|
||||
|
||||
android_library("brave_safe_browsing_java") {
|
||||
deps = [
|
||||
"//base:base_java",
|
||||
"//brave/third_party/android_deps:google_play_services_safetynet_java",
|
||||
"//build/android:build_java",
|
||||
"//components/safe_browsing/android:safe_browsing_java",
|
||||
"//third_party/android_deps:google_play_services_basement_java",
|
||||
"//third_party/android_deps:google_play_services_tasks_java",
|
||||
]
|
||||
sources = [ "java/src/org/chromium/components/safe_browsing/BraveSafeBrowsingApiHandler.java" ]
|
||||
}
|
||||
+162
@@ -0,0 +1,162 @@
|
||||
/* Copyright (c) 2022 The Brave Authors. All rights reserved.
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
* You can obtain one at https://mozilla.org/MPL/2.0/. */
|
||||
|
||||
package org.chromium.components.safe_browsing;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.pm.ApplicationInfo;
|
||||
|
||||
import com.google.android.gms.common.api.ApiException;
|
||||
import com.google.android.gms.common.api.CommonStatusCodes;
|
||||
import com.google.android.gms.safetynet.SafeBrowsingThreat;
|
||||
import com.google.android.gms.safetynet.SafetyNet;
|
||||
import com.google.android.gms.safetynet.SafetyNetApi;
|
||||
import com.google.android.gms.safetynet.SafetyNetStatusCodes;
|
||||
import com.google.android.gms.tasks.OnSuccessListener;
|
||||
|
||||
import org.json.JSONArray;
|
||||
import org.json.JSONException;
|
||||
import org.json.JSONObject;
|
||||
|
||||
import org.chromium.base.ContextUtils;
|
||||
import org.chromium.base.Log;
|
||||
|
||||
public class BraveSafeBrowsingApiHandler implements SafeBrowsingApiHandler {
|
||||
private static final long DEFAULT_CHECK_DELTA = 10;
|
||||
private static final String SAFE_METADATA = "{}";
|
||||
private static final String TAG = "BraveSafeBrowsingApiHandler";
|
||||
|
||||
public interface BraveSafeBrowsingApiHandlerDelegate {
|
||||
default void turnSafeBrowsingOff() {}
|
||||
}
|
||||
|
||||
private Observer mObserver;
|
||||
private Activity mActivity;
|
||||
private String mApiKey;
|
||||
private boolean mInitialized;
|
||||
private int mTriesCount;
|
||||
private BraveSafeBrowsingApiHandlerDelegate mBraveSafeBrowsingApiHandlerDelegate;
|
||||
|
||||
public BraveSafeBrowsingApiHandler(Activity activity, String apiKey,
|
||||
BraveSafeBrowsingApiHandlerDelegate braveSafeBrowsingApiHandlerDelegate) {
|
||||
mActivity = activity;
|
||||
mApiKey = apiKey;
|
||||
mTriesCount = 0;
|
||||
mBraveSafeBrowsingApiHandlerDelegate = braveSafeBrowsingApiHandlerDelegate;
|
||||
assert mBraveSafeBrowsingApiHandlerDelegate
|
||||
!= null : "BraveSafeBrowsingApiHandlerDelegate has to be initialized";
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean init(Observer observer) {
|
||||
mObserver = observer;
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void startUriLookup(final long callbackId, String uri, int[] threatsOfInterest) {
|
||||
if (mActivity == null) {
|
||||
return;
|
||||
}
|
||||
mTriesCount++;
|
||||
if (!mInitialized) {
|
||||
initSafeBrowsing();
|
||||
}
|
||||
|
||||
SafetyNet.getClient(ContextUtils.getApplicationContext())
|
||||
.lookupUri(uri, mApiKey, threatsOfInterest)
|
||||
.addOnSuccessListener(mActivity,
|
||||
sbResponse -> {
|
||||
mTriesCount = 0;
|
||||
try {
|
||||
String metadata = SAFE_METADATA;
|
||||
if (!sbResponse.getDetectedThreats().isEmpty()) {
|
||||
JSONArray jsonArray = new JSONArray();
|
||||
for (int i = 0; i < sbResponse.getDetectedThreats().size();
|
||||
i++) {
|
||||
JSONObject jsonObj = new JSONObject();
|
||||
jsonObj.put("threat_type",
|
||||
String.valueOf(sbResponse.getDetectedThreats()
|
||||
.get(i)
|
||||
.getThreatType()));
|
||||
jsonArray.put(jsonObj);
|
||||
}
|
||||
JSONObject finalObj = new JSONObject();
|
||||
finalObj.put("matches", jsonArray);
|
||||
metadata = finalObj.toString();
|
||||
}
|
||||
if (mObserver != null) {
|
||||
mObserver.onUrlCheckDone(callbackId, SafeBrowsingResult.SUCCESS,
|
||||
metadata, DEFAULT_CHECK_DELTA);
|
||||
}
|
||||
} catch (JSONException e) {
|
||||
}
|
||||
})
|
||||
.addOnFailureListener(mActivity, e -> {
|
||||
// An error occurred while communicating with the service.
|
||||
if (e instanceof ApiException) {
|
||||
// An error with the Google Play Services API contains some
|
||||
// additional details.
|
||||
ApiException apiException = (ApiException) e;
|
||||
if (isDebuggable()) {
|
||||
Log.d(TAG,
|
||||
"Error: "
|
||||
+ CommonStatusCodes.getStatusCodeString(
|
||||
apiException.getStatusCode())
|
||||
+ ", code: " + apiException.getStatusCode());
|
||||
}
|
||||
if (apiException.getStatusCode() == CommonStatusCodes.API_NOT_CONNECTED) {
|
||||
// That means that device doesn't have Google Play Services API.
|
||||
// Delegate is used to turn off safe browsing option as every request is
|
||||
// delayed when it's turned on and not working
|
||||
mBraveSafeBrowsingApiHandlerDelegate.turnSafeBrowsingOff();
|
||||
}
|
||||
|
||||
// Note: If the status code, apiException.getStatusCode(),
|
||||
// is SafetyNetStatusCodes.SAFE_BROWSING_API_NOT_INITIALIZED,
|
||||
// you need to call initSafeBrowsing(). It means either you
|
||||
// haven't called initSafeBrowsing() before or that it needs
|
||||
// to be called again due to an internal error.
|
||||
if (mTriesCount <= 1
|
||||
&& apiException.getStatusCode()
|
||||
== SafetyNetStatusCodes.SAFE_BROWSING_API_NOT_INITIALIZED) {
|
||||
initSafeBrowsing();
|
||||
startUriLookup(callbackId, uri, threatsOfInterest);
|
||||
}
|
||||
} else {
|
||||
// A different, unknown type of error occurred.
|
||||
if (isDebuggable()) {
|
||||
Log.d(TAG, "Error: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
mTriesCount = 0;
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean startAllowlistLookup(final String uri, int threatType) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public void initSafeBrowsing() {
|
||||
SafetyNet.getClient(mActivity).initSafeBrowsing();
|
||||
mInitialized = true;
|
||||
}
|
||||
|
||||
public void shutdownSafeBrowsing() {
|
||||
if (!mInitialized) {
|
||||
return;
|
||||
}
|
||||
SafetyNet.getClient(ContextUtils.getApplicationContext()).shutdownSafeBrowsing();
|
||||
}
|
||||
|
||||
private boolean isDebuggable() {
|
||||
if (mActivity == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return 0 != (mActivity.getApplicationInfo().flags & ApplicationInfo.FLAG_DEBUGGABLE);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user