962 lines
49 KiB
Diff
962 lines
49 KiB
Diff
From: uazo <uazo@users.noreply.github.com>
|
|
Date: Sun, 24 Oct 2021 16:54:04 +0000
|
|
Subject: Enable native Android autofill
|
|
|
|
There are 2 different types of autofill: one managed via GCM and the
|
|
native Android one that uses the provider assigned by the user
|
|
(which can be any user installed app like Bitwarden for example).
|
|
In chromium GCM is active while in the WebView the latter.
|
|
This patch uses WebView code to enable native Android autofill
|
|
along with browser-managed autofill.
|
|
A separate toggle is introduced to enable autofill in incognito mode.
|
|
|
|
See also: https://github.com/bromite/bromite/issues/547
|
|
|
|
Original License: GPL-2.0-or-later - https://spdx.org/licenses/GPL-2.0-or-later.html
|
|
License: GPL-3.0-only - https://spdx.org/licenses/GPL-3.0-only.html
|
|
---
|
|
.../settings/PasswordSettings.java | 84 ++++++++++++++++-
|
|
.../chrome/browser/settings/MainSettings.java | 18 +---
|
|
.../chromium/chrome/browser/tab/TabImpl.java | 41 ++++++--
|
|
chrome/browser/android/tab_android.cc | 4 +-
|
|
.../actor/actor_form_filling_service_impl.cc | 8 --
|
|
chrome/browser/autofill/android/BUILD.gn | 2 +-
|
|
.../autofill/AutofillClientProviderUtils.java | 2 +-
|
|
...AutofillThirdPartyModeContentProvider.java | 1 +
|
|
.../chrome_password_manager_client.cc | 6 ++
|
|
.../chrome_password_manager_client.h | 2 +
|
|
.../strings/android_chrome_strings.grd | 6 ++
|
|
.../ui/autofill/autofill_client_provider.cc | 94 +------------------
|
|
.../ui/autofill/autofill_client_provider.h | 6 --
|
|
chrome/browser/ui/tab_helpers.cc | 4 +-
|
|
components/android_autofill/browser/BUILD.gn | 1 +
|
|
.../browser/android_autofill_manager.cc | 2 +
|
|
.../browser/android_autofill_manager.h | 2 +
|
|
.../autofill/AutofillManagerWrapper.java | 5 +-
|
|
.../components/autofill/AutofillProvider.java | 7 ++
|
|
.../BrowserSelectionActionMenuDelegate.java | 27 ++++++
|
|
.../browser/content_autofill_driver.cc | 11 +++
|
|
.../content/browser/content_autofill_driver.h | 10 ++
|
|
.../content_autofill_driver_factory.cc | 12 +++
|
|
.../content/renderer/autofill_agent.cc | 4 -
|
|
.../renderer/password_autofill_agent.cc | 5 +-
|
|
.../browser/foundations/autofill_driver.h | 2 +
|
|
.../foundations/autofill_driver_factory.cc | 4 +
|
|
.../browser/foundations/autofill_manager.h | 2 +
|
|
.../foundations/browser_autofill_manager.cc | 2 +
|
|
.../foundations/browser_autofill_manager.h | 2 +
|
|
.../autofill/core/common/autofill_prefs.cc | 4 +-
|
|
.../autofill/core/common/autofill_prefs.h | 5 +
|
|
.../core/browser/password_form_manager.cc | 4 +
|
|
.../core/browser/password_manager_client.cc | 2 +
|
|
.../core/browser/password_manager_client.h | 2 +
|
|
35 files changed, 249 insertions(+), 144 deletions(-)
|
|
create mode 100644 components/android_autofill/browser/java/src/org/chromium/components/autofill/BrowserSelectionActionMenuDelegate.java
|
|
|
|
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/password_manager/settings/PasswordSettings.java b/chrome/android/java/src/org/chromium/chrome/browser/password_manager/settings/PasswordSettings.java
|
|
--- a/chrome/android/java/src/org/chromium/chrome/browser/password_manager/settings/PasswordSettings.java
|
|
+++ b/chrome/android/java/src/org/chromium/chrome/browser/password_manager/settings/PasswordSettings.java
|
|
@@ -27,6 +27,7 @@ import androidx.preference.Preference;
|
|
import androidx.preference.PreferenceCategory;
|
|
import androidx.preference.PreferenceGroup;
|
|
|
|
+import org.chromium.base.StrictModeContext;
|
|
import org.chromium.base.supplier.MonotonicObservableSupplier;
|
|
import org.chromium.base.supplier.ObservableSuppliers;
|
|
import org.chromium.base.supplier.SettableMonotonicObservableSupplier;
|
|
@@ -60,6 +61,12 @@ import org.chromium.ui.base.IntentRequestTracker;
|
|
import java.lang.annotation.Retention;
|
|
import java.lang.annotation.RetentionPolicy;
|
|
import java.util.Locale;
|
|
+import java.util.function.Supplier;
|
|
+
|
|
+import org.chromium.chrome.browser.ui.messages.snackbar.SnackbarManager;
|
|
+import org.chromium.chrome.browser.ui.messages.snackbar.INeedSnackbarManager;
|
|
+import org.chromium.chrome.browser.ui.messages.snackbar.Snackbar;
|
|
+import org.chromium.chrome.browser.lifetime.ApplicationLifetime;
|
|
|
|
/**
|
|
* The "Passwords" screen in Settings, which allows the user to enable or disable password saving,
|
|
@@ -68,7 +75,7 @@ import java.util.Locale;
|
|
public class PasswordSettings extends ChromeBaseSettingsFragment
|
|
implements PasswordListObserver,
|
|
Preference.OnPreferenceClickListener, SearchViewProvider,
|
|
- SyncService.SyncStateChangedListener {
|
|
+ SyncService.SyncStateChangedListener, INeedSnackbarManager {
|
|
@IntDef({
|
|
TrustedVaultBannerState.NOT_SHOWN,
|
|
TrustedVaultBannerState.OFFER_OPT_IN,
|
|
@@ -98,6 +105,12 @@ public class PasswordSettings extends ChromeBaseSettingsFragment
|
|
public static final String PREF_TRUSTED_VAULT_BANNER = "trusted_vault_banner";
|
|
public static final String PREF_KEY_MANAGE_ACCOUNT_LINK = "manage_account_link";
|
|
|
|
+ public static final String PREF_ANDROID_AUTOFILL_SWITCH = "android_autofill_switch";
|
|
+ public static final String PREF_ANDROID_AUTOFILL_INCOGNITO_SWITCH = "android_autofill_incognito_switch";
|
|
+
|
|
+ private Supplier<SnackbarManager> mSnackbarManagerSupplier;
|
|
+ private Snackbar mSnackbar;
|
|
+
|
|
private static final String PREF_KEY_CATEGORY_SAVED_PASSWORDS = "saved_passwords";
|
|
private static final String PREF_KEY_CATEGORY_EXCEPTIONS = "exceptions";
|
|
private static final String PREF_KEY_SAVED_PASSWORDS_NO_TEXT = "saved_passwords_no_text";
|
|
@@ -133,6 +146,9 @@ public class PasswordSettings extends ChromeBaseSettingsFragment
|
|
private final SettableMonotonicObservableSupplier<String> mPageTitle =
|
|
ObservableSuppliers.createMonotonic();
|
|
|
|
+ private ChromeSwitchPreference mEnableAndroidAutofillSwitch;
|
|
+ private ChromeSwitchPreference mEnableAndroidAutofillIncognitoSwitch;
|
|
+
|
|
/** For controlling the UX flow of exporting passwords. */
|
|
private final ExportFlow mExportFlow = new ExportFlow();
|
|
private ActivityWindowAndroid mWindowAndroid;
|
|
@@ -317,6 +333,7 @@ public class PasswordSettings extends ChromeBaseSettingsFragment
|
|
|
|
createSavePasswordsSwitch();
|
|
createAutoSignInCheckbox();
|
|
+ createEnableAndroidAutofillSwitch();
|
|
|
|
PasswordManagerHandlerProvider.getForProfile(getProfile())
|
|
.getPasswordManagerHandler()
|
|
@@ -579,6 +596,71 @@ public class PasswordSettings extends ChromeBaseSettingsFragment
|
|
getPrefService().getBoolean(Pref.CREDENTIALS_ENABLE_SERVICE));
|
|
}
|
|
|
|
+ private void createEnableAndroidAutofillSwitch() {
|
|
+ if (mSnackbar == null) {
|
|
+ mSnackbar = Snackbar.make(getActivity().getString(R.string.ui_relaunch_notice),
|
|
+ new SnackbarManager.SnackbarController() {
|
|
+ @Override
|
|
+ public void onDismissNoAction(Object actionData) { }
|
|
+
|
|
+ @Override
|
|
+ public void onAction(Object actionData) {
|
|
+ ApplicationLifetime.terminate(true);
|
|
+ }
|
|
+ }, Snackbar.TYPE_NOTIFICATION, Snackbar.UMA_UNKNOWN)
|
|
+ .setDefaultLines(false)
|
|
+ .setAction(getActivity().getString(R.string.relaunch),
|
|
+ /*actionData*/null)
|
|
+ .setDuration(/*durationMs*/70000);
|
|
+ }
|
|
+
|
|
+ mEnableAndroidAutofillSwitch = new ChromeSwitchPreference(getStyledContext(), null);
|
|
+ mEnableAndroidAutofillSwitch.setKey(PREF_ANDROID_AUTOFILL_SWITCH);
|
|
+ mEnableAndroidAutofillSwitch.setTitle(R.string.enable_android_autofill);
|
|
+ mEnableAndroidAutofillSwitch.setOrder(ORDER_SWITCH);
|
|
+ mEnableAndroidAutofillSwitch.setSummaryOn(R.string.text_on);
|
|
+ mEnableAndroidAutofillSwitch.setSummaryOff(R.string.text_off);
|
|
+
|
|
+ try (StrictModeContext ignored = StrictModeContext.allowDiskReads()) {
|
|
+ getPreferenceScreen().addPreference(mEnableAndroidAutofillSwitch);
|
|
+ }
|
|
+
|
|
+ mEnableAndroidAutofillSwitch.setChecked(
|
|
+ getPrefService().getBoolean(Pref.AUTOFILL_ANDROID_ENABLED));
|
|
+
|
|
+ mEnableAndroidAutofillSwitch.setOnPreferenceChangeListener((preference, newValue) -> {
|
|
+ getPrefService().setBoolean(Pref.AUTOFILL_ANDROID_ENABLED, (boolean) newValue);
|
|
+ if (!mSnackbarManagerSupplier.get().isShowing())
|
|
+ mSnackbarManagerSupplier.get().showSnackbar(mSnackbar);
|
|
+ return true;
|
|
+ });
|
|
+
|
|
+ mEnableAndroidAutofillIncognitoSwitch = new ChromeSwitchPreference(getStyledContext(), null);
|
|
+ mEnableAndroidAutofillIncognitoSwitch.setKey(PREF_ANDROID_AUTOFILL_INCOGNITO_SWITCH);
|
|
+ mEnableAndroidAutofillIncognitoSwitch.setTitle(R.string.enable_android_autofill_incognito);
|
|
+ mEnableAndroidAutofillIncognitoSwitch.setOrder(ORDER_SWITCH);
|
|
+ mEnableAndroidAutofillIncognitoSwitch.setSummaryOn(R.string.text_on);
|
|
+ mEnableAndroidAutofillIncognitoSwitch.setSummaryOff(R.string.text_off);
|
|
+
|
|
+ try (StrictModeContext ignored = StrictModeContext.allowDiskReads()) {
|
|
+ getPreferenceScreen().addPreference(mEnableAndroidAutofillIncognitoSwitch);
|
|
+ }
|
|
+
|
|
+ mEnableAndroidAutofillIncognitoSwitch.setChecked(
|
|
+ getPrefService().getBoolean(Pref.AUTOFILL_ANDROID_INCOGNITO_ENABLED));
|
|
+
|
|
+ mEnableAndroidAutofillIncognitoSwitch.setOnPreferenceChangeListener((preference, newValue) -> {
|
|
+ getPrefService().setBoolean(Pref.AUTOFILL_ANDROID_INCOGNITO_ENABLED, (boolean) newValue);
|
|
+ if (!mSnackbarManagerSupplier.get().isShowing())
|
|
+ mSnackbarManagerSupplier.get().showSnackbar(mSnackbar);
|
|
+ return true;
|
|
+ });
|
|
+ }
|
|
+
|
|
+ public void setSnackbarManagerSupplier(Supplier<SnackbarManager> manager) {
|
|
+ mSnackbarManagerSupplier = manager;
|
|
+ }
|
|
+
|
|
private void createAutoSignInCheckbox() {
|
|
ChromeSwitchPreference autoSignInSwitch =
|
|
new ChromeSwitchPreference(getStyledContext(), null);
|
|
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/settings/MainSettings.java b/chrome/android/java/src/org/chromium/chrome/browser/settings/MainSettings.java
|
|
--- a/chrome/android/java/src/org/chromium/chrome/browser/settings/MainSettings.java
|
|
+++ b/chrome/android/java/src/org/chromium/chrome/browser/settings/MainSettings.java
|
|
@@ -720,22 +720,8 @@ public class MainSettings extends ChromeBaseSettingsFragment
|
|
|
|
// TODO(crbug.com/482988366): Remove this method once the Autofill and passwords feature is launched.
|
|
private void updateAutofillPreferencesPreAutofillAndPasswords() {
|
|
- addPreferenceIfAbsent(PREF_AUTOFILL_SECTION);
|
|
- addPreferenceIfAbsent(PREF_AUTOFILL_OPTIONS);
|
|
- Preference autofillOptionsPreference = findPreference(PREF_AUTOFILL_OPTIONS);
|
|
- autofillOptionsPreference.setTitle(AutofillOptionsMediator.getFragmentTitle(getContext()));
|
|
- autofillOptionsPreference.setFragment(null);
|
|
- autofillOptionsPreference.setOnPreferenceClickListener(
|
|
- preference -> {
|
|
- onPreferenceSelected(preference);
|
|
- SettingsNavigationFactory.createSettingsNavigation()
|
|
- .startSettings(
|
|
- getContext(),
|
|
- AutofillOptionsFragment.class,
|
|
- AutofillOptionsFragment.createRequiredArgs(
|
|
- AutofillOptionsReferrer.SETTINGS));
|
|
- return true; // Means event is consumed.
|
|
- });
|
|
+ removePreferenceIfPresent(PREF_AUTOFILL_SECTION);
|
|
+ removePreferenceIfPresent(PREF_AUTOFILL_OPTIONS);
|
|
findPreference(PREF_AUTOFILL_PAYMENTS)
|
|
.setOnPreferenceClickListener(
|
|
preference -> {
|
|
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/tab/TabImpl.java b/chrome/android/java/src/org/chromium/chrome/browser/tab/TabImpl.java
|
|
--- a/chrome/android/java/src/org/chromium/chrome/browser/tab/TabImpl.java
|
|
+++ b/chrome/android/java/src/org/chromium/chrome/browser/tab/TabImpl.java
|
|
@@ -121,6 +121,13 @@ import java.util.HashMap;
|
|
import java.util.Map;
|
|
import java.util.Objects;
|
|
|
|
+import org.chromium.components.autofill.AutofillSelectionMenuItemHelper;
|
|
+import org.chromium.components.autofill.BrowserSelectionActionMenuDelegate;
|
|
+import org.chromium.content_public.browser.SelectionPopupController;
|
|
+import org.chromium.chrome.browser.preferences.Pref;
|
|
+import org.chromium.chrome.browser.profiles.ProfileManager;
|
|
+import org.chromium.components.user_prefs.UserPrefs;
|
|
+
|
|
/**
|
|
* Implementation of the interface {@link Tab}. Contains and manages a {@link ContentView}. This
|
|
* class is not intended to be extended.
|
|
@@ -1252,6 +1259,11 @@ class TabImpl implements Tab {
|
|
}
|
|
|
|
mObservers.clear();
|
|
+ if (mAutofillProvider != null) {
|
|
+ mAutofillProvider.destroy();
|
|
+ mAutofillProvider = null;
|
|
+ }
|
|
+
|
|
if (!abortNavigationsFromTabClosures) mUserDataHost.destroy();
|
|
mTabViewManager.destroy();
|
|
hideNativePage(false, null);
|
|
@@ -1641,6 +1653,7 @@ class TabImpl implements Tab {
|
|
* @return iff the AutofillProvider should provide a ViewStructure when prompted.
|
|
*/
|
|
boolean providesAutofillStructure() {
|
|
+ if ((true)) return true;
|
|
if (!mProfile.isNativeInitialized()) {
|
|
return false;
|
|
}
|
|
@@ -2440,16 +2453,21 @@ class TabImpl implements Tab {
|
|
* @return true if the the provider is available for the given WebContents.
|
|
*/
|
|
private boolean prepareAutofillProvider(WebContents newWebContents) {
|
|
- assert isInitialized();
|
|
- if (!providesAutofillStructure()) {
|
|
+ boolean autofillEnabled = false;
|
|
+ if (isIncognito()) {
|
|
+ autofillEnabled = UserPrefs.get(ProfileManager.getLastUsedRegularProfile())
|
|
+ .getBoolean(Pref.AUTOFILL_ANDROID_INCOGNITO_ENABLED);
|
|
+ } else {
|
|
+ autofillEnabled = UserPrefs.get(ProfileManager.getLastUsedRegularProfile())
|
|
+ .getBoolean(Pref.AUTOFILL_ANDROID_ENABLED);
|
|
+ }
|
|
+ if (!autofillEnabled) {
|
|
maybeLogAutofillProviderDoesntUseVirtualStructureMetric();
|
|
mAutofillProvider = null;
|
|
return false; // Autofill provider can't be prepared.
|
|
}
|
|
- if (mAutofillProvider != null) {
|
|
- // Provider already existed. Swapping contents suffices.
|
|
- mAutofillProvider.setWebContents(newWebContents);
|
|
- } else {
|
|
+ assert isInitialized();
|
|
+ if (mAutofillProvider == null) {
|
|
// TODO: crbug.com/432447902 — Provide only an activity context and push changes.
|
|
mAutofillProvider =
|
|
new AutofillProvider(
|
|
@@ -2459,7 +2477,16 @@ class TabImpl implements Tab {
|
|
getContext().getString(R.string.app_name));
|
|
TabImplJni.get().initializeAutofillIfNecessary(mNativeTabAndroid);
|
|
}
|
|
- addAutofillItemsToSelectionActionMenu(newWebContents);
|
|
+ SelectionPopupController selectionController =
|
|
+ SelectionPopupController.fromWebContents(newWebContents);
|
|
+ mAutofillProvider.setWebContents(newWebContents);
|
|
+ mContentView.setWebContents(newWebContents);
|
|
+ BrowserSelectionActionMenuDelegate selectionActionMenuDelegate =
|
|
+ new BrowserSelectionActionMenuDelegate();
|
|
+ selectionActionMenuDelegate.setAutofillSelectionMenuItemHelper(
|
|
+ new AutofillSelectionMenuItemHelper(mAutofillProvider));
|
|
+ selectionController.setSelectionActionMenuDelegate(selectionActionMenuDelegate);
|
|
+
|
|
return true;
|
|
}
|
|
|
|
diff --git a/chrome/browser/android/tab_android.cc b/chrome/browser/android/tab_android.cc
|
|
--- a/chrome/browser/android/tab_android.cc
|
|
+++ b/chrome/browser/android/tab_android.cc
|
|
@@ -40,6 +40,7 @@
|
|
#include "chrome/browser/sync/glue/synced_tab_delegate_android.h"
|
|
#include "chrome/browser/tab/web_contents_state.h"
|
|
#include "chrome/browser/tab_contents/tab_util.h"
|
|
+#include "chrome/browser/ui/autofill/chrome_autofill_client.h"
|
|
#include "chrome/browser/ui/android/context_menu_helper.h"
|
|
#include "chrome/browser/ui/android/tab_model/tab_model.h"
|
|
#include "chrome/browser/ui/android/tab_model/tab_model_list.h"
|
|
@@ -431,8 +432,7 @@ void TabAndroid::InitializeAutofillIfNecessary() {
|
|
->MaybeInitKeyboardSuppressor();
|
|
return;
|
|
}
|
|
- android_autofill::AndroidAutofillClient::CreateForWebContents(
|
|
- web_contents_.get());
|
|
+ autofill::ChromeAutofillClient::CreateForWebContents(web_contents_.get());
|
|
|
|
// We need to initialize the keyboard suppressor before creating any
|
|
// AutofillManagers and after the autofill client is available.
|
|
diff --git a/chrome/browser/autofill/actor/actor_form_filling_service_impl.cc b/chrome/browser/autofill/actor/actor_form_filling_service_impl.cc
|
|
--- a/chrome/browser/autofill/actor/actor_form_filling_service_impl.cc
|
|
+++ b/chrome/browser/autofill/actor/actor_form_filling_service_impl.cc
|
|
@@ -427,14 +427,6 @@ GetAutofillManager(const tabs::TabInterface& tab) {
|
|
if (!profile) {
|
|
return base::unexpected(kAutofillNotAvailable);
|
|
}
|
|
- if (AutofillClientProviderFactory::GetForProfile(profile)
|
|
- .uses_platform_autofill()) {
|
|
- // This is currently only possible on Android platforms, but this check
|
|
- // guards against this becoming applicable for Desktop platforms as well.
|
|
- // It is a requirement for the cast to `BrowserAutofillManager` to be
|
|
- // safe.
|
|
- return base::unexpected(kAutofillNotAvailable);
|
|
- }
|
|
|
|
ContentAutofillClient* const client =
|
|
ContentAutofillClient::FromWebContents(tab.GetContents());
|
|
diff --git a/chrome/browser/autofill/android/BUILD.gn b/chrome/browser/autofill/android/BUILD.gn
|
|
--- a/chrome/browser/autofill/android/BUILD.gn
|
|
+++ b/chrome/browser/autofill/android/BUILD.gn
|
|
@@ -187,7 +187,7 @@ android_library("bottom_sheet_utils_java") {
|
|
generate_jni("jni_headers") {
|
|
sources = [
|
|
"java/src/org/chromium/chrome/browser/autofill/AddressNormalizerFactory.java",
|
|
- "java/src/org/chromium/chrome/browser/autofill/AutofillClientProviderUtils.java",
|
|
+ #"java/src/org/chromium/chrome/browser/autofill/AutofillClientProviderUtils.java",
|
|
"java/src/org/chromium/chrome/browser/autofill/AutofillImageFetcher.java",
|
|
"java/src/org/chromium/chrome/browser/autofill/AutofillImageFetcherFactory.java",
|
|
"java/src/org/chromium/chrome/browser/autofill/AutofillProfileBridge.java",
|
|
diff --git a/chrome/browser/autofill/android/java/src/org/chromium/chrome/browser/autofill/AutofillClientProviderUtils.java b/chrome/browser/autofill/android/java/src/org/chromium/chrome/browser/autofill/AutofillClientProviderUtils.java
|
|
--- a/chrome/browser/autofill/android/java/src/org/chromium/chrome/browser/autofill/AutofillClientProviderUtils.java
|
|
+++ b/chrome/browser/autofill/android/java/src/org/chromium/chrome/browser/autofill/AutofillClientProviderUtils.java
|
|
@@ -90,9 +90,9 @@ public class AutofillClientProviderUtils {
|
|
* @return {@link AndroidAutofillAvailabilityStatus.AVAILABLE} if Android Autofill can be used
|
|
* or a reason why it can't.
|
|
*/
|
|
- @CalledByNative
|
|
public static int getAndroidAutofillFrameworkAvailability(
|
|
@JniType("PrefService*") PrefService prefs) {
|
|
+ if ((true)) return AndroidAutofillAvailabilityStatus.AVAILABLE;
|
|
if (sAndroidAutofillFrameworkAvailabilityForTesting != null) {
|
|
return sAndroidAutofillFrameworkAvailabilityForTesting;
|
|
}
|
|
diff --git a/chrome/browser/autofill/android/java/src/org/chromium/chrome/browser/autofill/AutofillThirdPartyModeContentProvider.java b/chrome/browser/autofill/android/java/src/org/chromium/chrome/browser/autofill/AutofillThirdPartyModeContentProvider.java
|
|
--- a/chrome/browser/autofill/android/java/src/org/chromium/chrome/browser/autofill/AutofillThirdPartyModeContentProvider.java
|
|
+++ b/chrome/browser/autofill/android/java/src/org/chromium/chrome/browser/autofill/AutofillThirdPartyModeContentProvider.java
|
|
@@ -75,6 +75,7 @@ public final class AutofillThirdPartyModeContentProvider extends ContentProvider
|
|
@Nullable String selection,
|
|
String @Nullable [] selectionArgs,
|
|
@Nullable String sortOrder) {
|
|
+ if ((true)) return null;
|
|
if (createContentUri().equals(uri)) {
|
|
final String[] columns = {AUTOFILL_THIRD_PARTY_MODE_COLUMN};
|
|
MatrixCursor cursor = new MatrixCursor(columns, 1);
|
|
diff --git a/chrome/browser/password_manager/chrome_password_manager_client.cc b/chrome/browser/password_manager/chrome_password_manager_client.cc
|
|
--- a/chrome/browser/password_manager/chrome_password_manager_client.cc
|
|
+++ b/chrome/browser/password_manager/chrome_password_manager_client.cc
|
|
@@ -521,6 +521,12 @@ bool ChromePasswordManagerClient::PromptUserToChooseCredentials(
|
|
}
|
|
|
|
#if BUILDFLAG(IS_ANDROID)
|
|
+void ChromePasswordManagerClient::OnFillNow() {
|
|
+ if (touch_to_fill_controller_) {
|
|
+ touch_to_fill_controller_->Reset();
|
|
+ }
|
|
+}
|
|
+
|
|
void ChromePasswordManagerClient::ShowPasswordManagerErrorMessage(
|
|
password_manager::ErrorMessageFlowType flow_type,
|
|
password_manager::PasswordStoreBackendErrorType error_type) {
|
|
diff --git a/chrome/browser/password_manager/chrome_password_manager_client.h b/chrome/browser/password_manager/chrome_password_manager_client.h
|
|
--- a/chrome/browser/password_manager/chrome_password_manager_client.h
|
|
+++ b/chrome/browser/password_manager/chrome_password_manager_client.h
|
|
@@ -161,6 +161,8 @@ class ChromePasswordManagerClient
|
|
const url::Origin& origin,
|
|
CredentialsCallback callback) override;
|
|
#if BUILDFLAG(IS_ANDROID)
|
|
+ void OnFillNow() override;
|
|
+
|
|
void ShowPasswordManagerErrorMessage(
|
|
password_manager::ErrorMessageFlowType flow_type,
|
|
password_manager::PasswordStoreBackendErrorType error_type) override;
|
|
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings.grd b/chrome/browser/ui/android/strings/android_chrome_strings.grd
|
|
--- a/chrome/browser/ui/android/strings/android_chrome_strings.grd
|
|
+++ b/chrome/browser/ui/android/strings/android_chrome_strings.grd
|
|
@@ -345,6 +345,12 @@ CHAR_LIMIT guidelines:
|
|
<message name="IDS_PREFS_SECTION_ACCOUNT_AND_GOOGLE_SERVICES" desc="Title for the group of account-related entries and google services in Settings. [CHAR_LIMIT=32]">
|
|
You and Google
|
|
</message>
|
|
+ <message name="IDS_ENABLE_ANDROID_AUTOFILL" desc="Title for the checkbox toggling whether enable Android native autofill or not. [CHAR_LIMIT=32]">
|
|
+ Enable native Android autofill
|
|
+ </message>
|
|
+ <message name="IDS_ENABLE_ANDROID_AUTOFILL_INCOGNITO" desc="Title for the checkbox toggling whether enable Android native autofill or not in incognito mode. [CHAR_LIMIT=32]">
|
|
+ Enable native Android autofill in incognito
|
|
+ </message>
|
|
<message name="IDS_SIGN_IN_TO_CHROME" meaning="Button" desc="Title for the button to sign in to Chrome using one's Google account. [CHAR_LIMIT=27]">
|
|
Sign in to Chrome
|
|
</message>
|
|
diff --git a/chrome/browser/ui/autofill/autofill_client_provider.cc b/chrome/browser/ui/autofill/autofill_client_provider.cc
|
|
--- a/chrome/browser/ui/autofill/autofill_client_provider.cc
|
|
+++ b/chrome/browser/ui/autofill/autofill_client_provider.cc
|
|
@@ -17,92 +17,14 @@
|
|
#include "chrome/browser/autofill/android/android_autofill_availability_status.h"
|
|
#include "components/android_autofill/browser/android_autofill_client.h"
|
|
#include "components/prefs/android/pref_service_android.h"
|
|
-
|
|
-// Must come after all headers that specialize FromJniType() / ToJniType().
|
|
-#include "chrome/browser/autofill/android/jni_headers/AutofillClientProviderUtils_jni.h"
|
|
#endif // BUILDFLAG(IS_ANDROID)
|
|
|
|
namespace autofill {
|
|
-namespace {
|
|
-
|
|
-#if BUILDFLAG(IS_ANDROID)
|
|
-void RecordAvailabilityStatus(AndroidAutofillAvailabilityStatus availability) {
|
|
- base::UmaHistogramEnumeration("Autofill.AndroidAutofillAvailabilityStatus",
|
|
- availability);
|
|
-}
|
|
-
|
|
-// Counts how often the Chrome pref is reset because an platform autofill
|
|
-// isn't allowed or doesn't fulfill all preconditions.
|
|
-void RecordWhetherAndroidPrefResets(PrefService& prefs,
|
|
- bool uses_platform_autofill) {
|
|
- const bool will_reset_pref =
|
|
- prefs.GetBoolean(prefs::kAutofillUsingPlatformAutofill) &&
|
|
- !uses_platform_autofill;
|
|
- base::UmaHistogramBoolean("Autofill.ResetAutofillPrefToChrome",
|
|
- will_reset_pref);
|
|
-}
|
|
-
|
|
-// Sets a ahread pref that allows to learn whether deep-links into Chrome's
|
|
-// settings are available to use.
|
|
-void SetSharedPrefForDeepLink() {
|
|
- Java_AutofillClientProviderUtils_setAutofillOptionsDeepLinkPref(
|
|
- base::android::AttachCurrentThread(),
|
|
-
|
|
- base::FeatureList::IsEnabled(
|
|
- autofill::features::kAutofillDeepLinkAutofillOptions));
|
|
-}
|
|
-
|
|
-// Sets a shared pref that allows external apps to use a ContentResolver to
|
|
-// figure out whether Chrome is using platform autofill over the default.
|
|
-void SetSharedPrefForSettingsContentProvider(bool uses_platform_autofill) {
|
|
- if (base::FeatureList::IsEnabled(
|
|
- autofill::features::kAutofillThirdPartyModeContentProvider)) {
|
|
- Java_AutofillClientProviderUtils_setThirdPartyModePref(
|
|
- base::android::AttachCurrentThread(), uses_platform_autofill);
|
|
- } else {
|
|
- Java_AutofillClientProviderUtils_unsetThirdPartyModePref(
|
|
- base::android::AttachCurrentThread());
|
|
- }
|
|
-}
|
|
|
|
-AndroidAutofillAvailabilityStatus GetAndroidAutofillAvailabilityStatus(
|
|
- PrefService& prefs) {
|
|
- return static_cast<AndroidAutofillAvailabilityStatus>(
|
|
- Java_AutofillClientProviderUtils_getAndroidAutofillFrameworkAvailability(
|
|
- base::android::AttachCurrentThread(), &prefs));
|
|
-}
|
|
-#endif // BUILDFLAG(IS_ANDROID)
|
|
-
|
|
-bool UsesVirtualViewStructureForAutofill(PrefService& prefs) {
|
|
+AutofillClientProvider::AutofillClientProvider(PrefService* prefs) {
|
|
#if BUILDFLAG(IS_ANDROID)
|
|
- const AndroidAutofillAvailabilityStatus availability =
|
|
- GetAndroidAutofillAvailabilityStatus(prefs);
|
|
- RecordAvailabilityStatus(availability);
|
|
- return availability == AndroidAutofillAvailabilityStatus::kAvailable;
|
|
-#else
|
|
- return false;
|
|
-#endif // BUILDFLAG(IS_ANDROID)
|
|
-}
|
|
-
|
|
-} // namespace
|
|
-
|
|
-AutofillClientProvider::AutofillClientProvider(PrefService* prefs)
|
|
- : uses_platform_autofill_(
|
|
- UsesVirtualViewStructureForAutofill(CHECK_DEREF(prefs))) {
|
|
-#if BUILDFLAG(IS_ANDROID)
|
|
- RecordWhetherAndroidPrefResets(*prefs, uses_platform_autofill_);
|
|
- // Ensure the pref is reset if platform autofill is restricted.
|
|
prefs->SetBoolean(prefs::kAutofillUsingPlatformAutofill,
|
|
- uses_platform_autofill_);
|
|
- if (uses_platform_autofill_) {
|
|
- // Update the package of the actively used Autofill Service while platform
|
|
- // autofill is used. This allows restoring platform autofill later if it's
|
|
- // temporarily unavailable. Calling this for AwG would reset the pref.
|
|
- Java_AutofillClientProviderUtils_updatePackageUsedForAutofill(
|
|
- base::android::AttachCurrentThread(), prefs, uses_platform_autofill_);
|
|
- }
|
|
- SetSharedPrefForSettingsContentProvider(uses_platform_autofill_);
|
|
- SetSharedPrefForDeepLink();
|
|
+ true);
|
|
#endif // BUILDFLAG(IS_ANDROID)
|
|
}
|
|
|
|
@@ -110,19 +32,7 @@ AutofillClientProvider::~AutofillClientProvider() = default;
|
|
|
|
void AutofillClientProvider::CreateClientForWebContents(
|
|
content::WebContents* web_contents) {
|
|
- if (uses_platform_autofill()) {
|
|
-#if BUILDFLAG(IS_ANDROID)
|
|
- android_autofill::AndroidAutofillClient::CreateForWebContents(web_contents);
|
|
-#else
|
|
- NOTREACHED();
|
|
-#endif
|
|
- } else {
|
|
ChromeAutofillClient::CreateForWebContents(web_contents);
|
|
- }
|
|
}
|
|
|
|
} // namespace autofill
|
|
-
|
|
-#if BUILDFLAG(IS_ANDROID)
|
|
-DEFINE_JNI(AutofillClientProviderUtils)
|
|
-#endif
|
|
diff --git a/chrome/browser/ui/autofill/autofill_client_provider.h b/chrome/browser/ui/autofill/autofill_client_provider.h
|
|
--- a/chrome/browser/ui/autofill/autofill_client_provider.h
|
|
+++ b/chrome/browser/ui/autofill/autofill_client_provider.h
|
|
@@ -33,13 +33,7 @@ class AutofillClientProvider : public KeyedService {
|
|
// given `web_contents`.
|
|
void CreateClientForWebContents(content::WebContents* web_contents);
|
|
|
|
- // The return value is constant once this provider has been created. The
|
|
- // method returns true iff platform autofill should be used instead of
|
|
- // built-in autofill.
|
|
- bool uses_platform_autofill() const { return uses_platform_autofill_; }
|
|
-
|
|
private:
|
|
- const bool uses_platform_autofill_;
|
|
};
|
|
|
|
} // namespace autofill
|
|
diff --git a/chrome/browser/ui/tab_helpers.cc b/chrome/browser/ui/tab_helpers.cc
|
|
--- a/chrome/browser/ui/tab_helpers.cc
|
|
+++ b/chrome/browser/ui/tab_helpers.cc
|
|
@@ -389,9 +389,7 @@ void TabHelpers::AttachTabHelpers(WebContents* web_contents) {
|
|
web_contents);
|
|
ChainedBackNavigationTracker::CreateForWebContents(web_contents);
|
|
chrome_browser_net::NetErrorTabHelper::CreateForWebContents(web_contents);
|
|
- if (!autofill_client_provider.uses_platform_autofill()) {
|
|
- ChromePasswordManagerClient::CreateForWebContents(web_contents);
|
|
- }
|
|
+ ChromePasswordManagerClient::CreateForWebContents(web_contents);
|
|
#if BUILDFLAG(SAFE_BROWSING_AVAILABLE)
|
|
ChromePasswordReuseDetectionManagerClient::CreateForWebContents(web_contents);
|
|
#endif
|
|
diff --git a/components/android_autofill/browser/BUILD.gn b/components/android_autofill/browser/BUILD.gn
|
|
--- a/components/android_autofill/browser/BUILD.gn
|
|
+++ b/components/android_autofill/browser/BUILD.gn
|
|
@@ -42,6 +42,7 @@ android_library("java") {
|
|
"java/src/org/chromium/components/autofill/AutofillRequest.java",
|
|
"java/src/org/chromium/components/autofill/AutofillSelectionActionMenuDelegate.java",
|
|
"java/src/org/chromium/components/autofill/AutofillSelectionMenuItemHelper.java",
|
|
+ "java/src/org/chromium/components/autofill/BrowserSelectionActionMenuDelegate.java",
|
|
"java/src/org/chromium/components/autofill/FormData.java",
|
|
"java/src/org/chromium/components/autofill/FormFieldData.java",
|
|
"java/src/org/chromium/components/autofill/PrefillRequest.java",
|
|
diff --git a/components/android_autofill/browser/android_autofill_manager.cc b/components/android_autofill/browser/android_autofill_manager.cc
|
|
--- a/components/android_autofill/browser/android_autofill_manager.cc
|
|
+++ b/components/android_autofill/browser/android_autofill_manager.cc
|
|
@@ -36,6 +36,8 @@ AndroidAutofillManager::~AndroidAutofillManager() {
|
|
Reset();
|
|
}
|
|
|
|
+bool AndroidAutofillManager::IsAndroidAutofill() const { return true; }
|
|
+
|
|
base::WeakPtr<AutofillManager> AndroidAutofillManager::GetWeakPtr() {
|
|
return weak_ptr_factory_.GetWeakPtr();
|
|
}
|
|
diff --git a/components/android_autofill/browser/android_autofill_manager.h b/components/android_autofill/browser/android_autofill_manager.h
|
|
--- a/components/android_autofill/browser/android_autofill_manager.h
|
|
+++ b/components/android_autofill/browser/android_autofill_manager.h
|
|
@@ -33,6 +33,8 @@ class AndroidAutofillManager : public AutofillManager,
|
|
|
|
~AndroidAutofillManager() override;
|
|
|
|
+ bool IsAndroidAutofill() const override;
|
|
+
|
|
base::WeakPtr<AndroidAutofillManager> GetWeakPtrToLeafClass() {
|
|
return weak_ptr_factory_.GetWeakPtr();
|
|
}
|
|
diff --git a/components/android_autofill/browser/java/src/org/chromium/components/autofill/AutofillManagerWrapper.java b/components/android_autofill/browser/java/src/org/chromium/components/autofill/AutofillManagerWrapper.java
|
|
--- a/components/android_autofill/browser/java/src/org/chromium/components/autofill/AutofillManagerWrapper.java
|
|
+++ b/components/android_autofill/browser/java/src/org/chromium/components/autofill/AutofillManagerWrapper.java
|
|
@@ -59,6 +59,7 @@ public class AutofillManagerWrapper {
|
|
AutofillManagerWrapper manager = mManager.get();
|
|
if (manager == null) return;
|
|
manager.mIsAutofillInputUiShowing = (event == EVENT_INPUT_SHOWN);
|
|
+ if (manager.isLoggable()) manager.log("onAutofillEvent isAutofillInputUIShowing: " + manager.mIsAutofillInputUiShowing);
|
|
if (event == EVENT_INPUT_SHOWN) manager.notifyInputUiChange();
|
|
}
|
|
}
|
|
@@ -120,6 +121,7 @@ public class AutofillManagerWrapper {
|
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
|
|
ComponentName componentName = getAutofillServiceComponentName(mAutofillManager);
|
|
+ if (isLoggable()) log("componentName=" + componentName);
|
|
if (componentName != null) {
|
|
mPackageName = componentName.getPackageName();
|
|
mIsAwGCurrentAutofillService =
|
|
@@ -352,7 +354,7 @@ public class AutofillManagerWrapper {
|
|
/** Always check isLoggable() before call this method. */
|
|
public static void log(String log) {
|
|
// Log.i() instead of Log.d() is used here because Log.d() is stripped out in release build.
|
|
- Log.i(TAG, log);
|
|
+ Log.i(TAG, "---" + log);
|
|
}
|
|
|
|
public static boolean isLoggable() {
|
|
@@ -366,5 +368,6 @@ public class AutofillManagerWrapper {
|
|
// NOTE: See the comment on TAG above for why this is still AwAutofillManager.
|
|
// Check the system setting directly.
|
|
sIsLoggable = Log.isLoggable(TAG, Log.DEBUG);
|
|
+ // sIsLoggable = true; // to force enable the log
|
|
}
|
|
}
|
|
diff --git a/components/android_autofill/browser/java/src/org/chromium/components/autofill/AutofillProvider.java b/components/android_autofill/browser/java/src/org/chromium/components/autofill/AutofillProvider.java
|
|
--- a/components/android_autofill/browser/java/src/org/chromium/components/autofill/AutofillProvider.java
|
|
+++ b/components/android_autofill/browser/java/src/org/chromium/components/autofill/AutofillProvider.java
|
|
@@ -252,6 +252,10 @@ public class AutofillProvider {
|
|
* @return whether query autofill suggestion.
|
|
*/
|
|
public boolean shouldQueryAutofillSuggestion() {
|
|
+ AutofillManagerWrapper.log("---shouldQueryAutofillSuggestion" +
|
|
+ " mRequest != null=" + (mRequest != null) +
|
|
+ " mRequest.getFocusField() != null=" + (mRequest != null && mRequest.getFocusField() != null) +
|
|
+ " !mAutofillManager.isAutofillInputUIShowing()=" + (!mAutofillManager.isAutofillInputUiShowing()));
|
|
return mRequest != null
|
|
&& mRequest.getFocusField() != null
|
|
&& !getAutofillManagerWrapper().isAutofillInputUiShowing();
|
|
@@ -260,6 +264,7 @@ public class AutofillProvider {
|
|
public boolean shouldOfferPasskeyEntry() {
|
|
if (!AndroidAutofillFeatures.ANDROID_AUTOFILL_VIRTUAL_VIEW_STRUCTURE_PASSKEY_LONG_PRESS
|
|
.isEnabled()) {
|
|
+ AutofillManagerWrapper.log("calling requestAutofill");
|
|
return false;
|
|
}
|
|
return AutofillProviderJni.get().hasPasskeyRequest(mNativeAutofillProvider);
|
|
@@ -272,6 +277,7 @@ public class AutofillProvider {
|
|
}
|
|
|
|
public void queryAutofillSuggestion() {
|
|
+ AutofillManagerWrapper.log("queryAutofillSuggestion start");
|
|
if (shouldQueryAutofillSuggestion()) {
|
|
FocusField focusField = mRequest.getFocusField();
|
|
getAutofillManagerWrapper()
|
|
@@ -334,6 +340,7 @@ public class AutofillProvider {
|
|
float width,
|
|
float height,
|
|
boolean hasServerPrediction) {
|
|
+ AutofillManagerWrapper.log("startAutofillSession");
|
|
Rect absBound = transformToWindowBounds(new RectF(x, y, x + width, y + height));
|
|
if (mRequest != null) notifyViewExitBeforeDestroyRequest();
|
|
|
|
diff --git a/components/android_autofill/browser/java/src/org/chromium/components/autofill/BrowserSelectionActionMenuDelegate.java b/components/android_autofill/browser/java/src/org/chromium/components/autofill/BrowserSelectionActionMenuDelegate.java
|
|
new file mode 100644
|
|
--- /dev/null
|
|
+++ b/components/android_autofill/browser/java/src/org/chromium/components/autofill/BrowserSelectionActionMenuDelegate.java
|
|
@@ -0,0 +1,27 @@
|
|
+// Copyright 2023 The Chromium Authors
|
|
+// Use of this source code is governed by a BSD-style license that can be
|
|
+// found in the LICENSE file.
|
|
+
|
|
+package org.chromium.components.autofill;
|
|
+
|
|
+import android.content.pm.ResolveInfo;
|
|
+
|
|
+import androidx.annotation.IntDef;
|
|
+import androidx.annotation.NonNull;
|
|
+
|
|
+import org.chromium.base.metrics.RecordHistogram;
|
|
+import org.chromium.components.autofill.AutofillSelectionActionMenuDelegate;
|
|
+import org.chromium.content_public.browser.SelectionMenuItem;
|
|
+import org.chromium.content_public.browser.SelectionPopupController;
|
|
+import org.chromium.content_public.browser.selection.SelectionActionMenuDelegate;
|
|
+
|
|
+import java.lang.annotation.Retention;
|
|
+import java.lang.annotation.RetentionPolicy;
|
|
+import java.util.ArrayList;
|
|
+import java.util.List;
|
|
+
|
|
+import org.chromium.base.Log;
|
|
+
|
|
+/** Interface for customizing text selection menu items in {@link SelectionPopupController} */
|
|
+public class BrowserSelectionActionMenuDelegate extends AutofillSelectionActionMenuDelegate {
|
|
+}
|
|
diff --git a/components/autofill/content/browser/content_autofill_driver.cc b/components/autofill/content/browser/content_autofill_driver.cc
|
|
--- a/components/autofill/content/browser/content_autofill_driver.cc
|
|
+++ b/components/autofill/content/browser/content_autofill_driver.cc
|
|
@@ -281,6 +281,13 @@ void RouteToManager(ContentAutofillDriver& source,
|
|
AutofillManager& manager = target.GetAutofillManager();
|
|
(manager.*
|
|
manager_fun)(WithNewVersion(std::forward<ManagerArgs>(args))...);
|
|
+
|
|
+ raw_ptr<AutofillManager> secondary_autofill_manager =
|
|
+ target.secondary_autofill_manager();
|
|
+ if (secondary_autofill_manager) {
|
|
+ (secondary_autofill_manager->*
|
|
+ manager_fun)(WithNewVersion(std::forward<ManagerArgs>(args))...);
|
|
+ }
|
|
},
|
|
source, Lift(source, std::forward<ActualArgs>(args))...);
|
|
}
|
|
@@ -701,6 +708,10 @@ ContentAutofillDriver::GetAutofillAgent() {
|
|
return autofill_agent_;
|
|
}
|
|
|
|
+raw_ptr<AutofillManager> ContentAutofillDriver::secondary_autofill_manager() {
|
|
+ return secondary_autofill_manager_.get();
|
|
+}
|
|
+
|
|
void ContentAutofillDriver::LiftForTest(FormData& form) {
|
|
form = Lift(*this, form);
|
|
}
|
|
diff --git a/components/autofill/content/browser/content_autofill_driver.h b/components/autofill/content/browser/content_autofill_driver.h
|
|
--- a/components/autofill/content/browser/content_autofill_driver.h
|
|
+++ b/components/autofill/content/browser/content_autofill_driver.h
|
|
@@ -136,6 +136,12 @@ class ContentAutofillDriver : public AutofillDriver,
|
|
// AutofillDriverFactory. Called on certain types of navigations.
|
|
void Reset(ContentAutofillDriverFactoryPassKey pass_key);
|
|
|
|
+ void set_secondary_autofill_manager(
|
|
+ std::unique_ptr<AutofillManager> secondary_autofill_manager) {
|
|
+ secondary_autofill_manager_ = std::move(secondary_autofill_manager);
|
|
+ }
|
|
+ raw_ptr<AutofillManager> secondary_autofill_manager() override;
|
|
+
|
|
content::RenderFrameHost* render_frame_host() { return &*render_frame_host_; }
|
|
const content::RenderFrameHost* render_frame_host() const {
|
|
return &*render_frame_host_;
|
|
@@ -316,6 +322,10 @@ class ContentAutofillDriver : public AutofillDriver,
|
|
// The factory that created this driver. Outlives `this`.
|
|
const raw_ref<ContentAutofillDriverFactory> owner_;
|
|
|
|
+ // adds a reference for AndroidAutofillManager, since native autofill works in
|
|
+ // conjunction with browser autofill in Bromite
|
|
+ std::unique_ptr<AutofillManager> secondary_autofill_manager_ = nullptr;
|
|
+
|
|
mojo::AssociatedReceiver<mojom::AutofillDriver> receiver_{this};
|
|
|
|
mojo::AssociatedRemote<mojom::AutofillAgent> autofill_agent_;
|
|
diff --git a/components/autofill/content/browser/content_autofill_driver_factory.cc b/components/autofill/content/browser/content_autofill_driver_factory.cc
|
|
--- a/components/autofill/content/browser/content_autofill_driver_factory.cc
|
|
+++ b/components/autofill/content/browser/content_autofill_driver_factory.cc
|
|
@@ -25,6 +25,12 @@
|
|
#include "content/public/browser/web_contents.h"
|
|
#include "third_party/blink/public/common/features.h"
|
|
|
|
+#if BUILDFLAG(IS_ANDROID)
|
|
+#include "components/android_autofill/browser/android_autofill_manager.h"
|
|
+#include "components/android_autofill/browser/autofill_provider.h"
|
|
+#include "components/android_autofill/browser/android_autofill_provider.h"
|
|
+#endif
|
|
+
|
|
namespace autofill {
|
|
|
|
class ScopedAutofillManagersObservation;
|
|
@@ -134,6 +140,12 @@ ContentAutofillDriver* ContentAutofillDriverFactory::DriverForFrame(
|
|
return nullptr;
|
|
}
|
|
driver = std::make_unique<ContentAutofillDriver>(render_frame_host, this);
|
|
+#if BUILDFLAG(IS_ANDROID)
|
|
+ if (!driver->GetAutofillManager().IsAndroidAutofill()) {
|
|
+ driver->set_secondary_autofill_manager(
|
|
+ base::WrapUnique(new AndroidAutofillManager(driver.get())));
|
|
+ }
|
|
+#endif
|
|
DCHECK_EQ(driver->GetLifecycleState(), LifecycleState::kInactive);
|
|
for (auto& observer : observers()) {
|
|
observer.OnAutofillDriverCreated(*this, *driver);
|
|
diff --git a/components/autofill/content/renderer/autofill_agent.cc b/components/autofill/content/renderer/autofill_agent.cc
|
|
--- a/components/autofill/content/renderer/autofill_agent.cc
|
|
+++ b/components/autofill/content/renderer/autofill_agent.cc
|
|
@@ -1551,10 +1551,6 @@ void AutofillAgent::ShowSuggestions(
|
|
password_generation_agent_->ShowPasswordGenerationSuggestions(
|
|
input_element, form_cache)) {
|
|
is_popup_possibly_visible_ = true;
|
|
- if (!base::FeatureList::IsEnabled(
|
|
- features::kAutofillAndroidKeyboardAccessoryDynamicPositioning)) {
|
|
- return;
|
|
- }
|
|
}
|
|
}
|
|
|
|
diff --git a/components/autofill/content/renderer/password_autofill_agent.cc b/components/autofill/content/renderer/password_autofill_agent.cc
|
|
--- a/components/autofill/content/renderer/password_autofill_agent.cc
|
|
+++ b/components/autofill/content/renderer/password_autofill_agent.cc
|
|
@@ -851,7 +851,10 @@ void PasswordAutofillAgent::UpdatePasswordStateForTextChange(
|
|
|
|
void PasswordAutofillAgent::TrackAutofilledElement(
|
|
const WebFormControlElement& element) {
|
|
- autofill_agent_->TrackAutofilledElement(
|
|
+ // fix for https://github.com/bromite/bromite/issues/1570
|
|
+ AutofillAgent* agent = autofill_agent_.get();
|
|
+ if (agent)
|
|
+ agent->TrackAutofilledElement(
|
|
form_util::GetFieldRendererId(element));
|
|
}
|
|
|
|
diff --git a/components/autofill/core/browser/foundations/autofill_driver.h b/components/autofill/core/browser/foundations/autofill_driver.h
|
|
--- a/components/autofill/core/browser/foundations/autofill_driver.h
|
|
+++ b/components/autofill/core/browser/foundations/autofill_driver.h
|
|
@@ -172,6 +172,8 @@ class AutofillDriver {
|
|
// Returns the AutofillManager owned by the AutofillDriver.
|
|
virtual AutofillManager& GetAutofillManager() = 0;
|
|
|
|
+ virtual raw_ptr<AutofillManager> secondary_autofill_manager() = 0;
|
|
+
|
|
// Gets the UKM source ID associated with this driver's outermost main frame's
|
|
// document.
|
|
//
|
|
diff --git a/components/autofill/core/browser/foundations/autofill_driver_factory.cc b/components/autofill/core/browser/foundations/autofill_driver_factory.cc
|
|
--- a/components/autofill/core/browser/foundations/autofill_driver_factory.cc
|
|
+++ b/components/autofill/core/browser/foundations/autofill_driver_factory.cc
|
|
@@ -25,6 +25,10 @@ void AutofillDriverFactory::SetLifecycleStateAndNotifyObservers(
|
|
}
|
|
driver.GetAutofillManager().OnAutofillDriverLifecycleStateChanged(
|
|
old_state, new_state, /*pass_key=*/{});
|
|
+ if (auto secondary = driver.secondary_autofill_manager()) {
|
|
+ secondary->OnAutofillDriverLifecycleStateChanged(
|
|
+ old_state, new_state, /*pass_key=*/{});
|
|
+ }
|
|
}
|
|
|
|
} // namespace autofill
|
|
diff --git a/components/autofill/core/browser/foundations/autofill_manager.h b/components/autofill/core/browser/foundations/autofill_manager.h
|
|
--- a/components/autofill/core/browser/foundations/autofill_manager.h
|
|
+++ b/components/autofill/core/browser/foundations/autofill_manager.h
|
|
@@ -249,6 +249,8 @@ class AutofillManager
|
|
LifecycleState new_state,
|
|
base::PassKey<AutofillDriverFactory> pass_key);
|
|
|
|
+ virtual bool IsAndroidAutofill() const = 0;
|
|
+
|
|
AutofillClient& client() { return driver_->GetAutofillClient(); }
|
|
const AutofillClient& client() const { return driver_->GetAutofillClient(); }
|
|
|
|
diff --git a/components/autofill/core/browser/foundations/browser_autofill_manager.cc b/components/autofill/core/browser/foundations/browser_autofill_manager.cc
|
|
--- a/components/autofill/core/browser/foundations/browser_autofill_manager.cc
|
|
+++ b/components/autofill/core/browser/foundations/browser_autofill_manager.cc
|
|
@@ -912,6 +912,8 @@ base::WeakPtr<AutofillManager> BrowserAutofillManager::GetWeakPtr() {
|
|
return weak_ptr_factory_.GetWeakPtr();
|
|
}
|
|
|
|
+bool BrowserAutofillManager::IsAndroidAutofill() const { return false; }
|
|
+
|
|
CreditCardAccessManager* BrowserAutofillManager::GetCreditCardAccessManager() {
|
|
if (!credit_card_access_manager_) {
|
|
credit_card_access_manager_ =
|
|
diff --git a/components/autofill/core/browser/foundations/browser_autofill_manager.h b/components/autofill/core/browser/foundations/browser_autofill_manager.h
|
|
--- a/components/autofill/core/browser/foundations/browser_autofill_manager.h
|
|
+++ b/components/autofill/core/browser/foundations/browser_autofill_manager.h
|
|
@@ -452,6 +452,8 @@ class BrowserAutofillManager : public AutofillManager {
|
|
// latter check is needed because IPC messages can arrive out of order.
|
|
void UpdateInitialInteractionTimestamp(base::TimeTicks interaction_timestamp);
|
|
|
|
+ bool IsAndroidAutofill() const override;
|
|
+
|
|
// Checks whether JavaScript cleared an autofilled value within
|
|
// kLimitBeforeRefill after the filling and records metrics for this. This
|
|
// method should be called after we learned that JavaScript modified an
|
|
diff --git a/components/autofill/core/common/autofill_prefs.cc b/components/autofill/core/common/autofill_prefs.cc
|
|
--- a/components/autofill/core/common/autofill_prefs.cc
|
|
+++ b/components/autofill/core/common/autofill_prefs.cc
|
|
@@ -89,6 +89,8 @@ void RegisterProfilePrefs(user_prefs::PrefRegistrySyncable* registry) {
|
|
registry->RegisterBooleanPref(kAutofillCreditCardFidoAuthOfferCheckboxState,
|
|
true);
|
|
#endif
|
|
+ registry->RegisterBooleanPref(prefs::kAutofillAndroidEnabled, true);
|
|
+ registry->RegisterBooleanPref(prefs::kAutofillAndroidIncognitoEnabled, false);
|
|
registry->RegisterIntegerPref(kAutocompleteLastVersionRetentionPolicy, 0);
|
|
registry->RegisterStringPref(kAutofillUploadEncodingSeed, "");
|
|
registry->RegisterDictionaryPref(kAutofillVoteUploadEvents);
|
|
@@ -117,7 +119,7 @@ void RegisterProfilePrefs(user_prefs::PrefRegistrySyncable* registry) {
|
|
#endif
|
|
|
|
#if BUILDFLAG(IS_ANDROID)
|
|
- registry->RegisterBooleanPref(kAutofillUsingPlatformAutofill, false);
|
|
+ registry->RegisterBooleanPref(kAutofillUsingPlatformAutofill, true);
|
|
registry->RegisterBooleanPref(kAutofillThirdPartyPasswordManagersAllowed,
|
|
true);
|
|
registry->RegisterStringPref(
|
|
diff --git a/components/autofill/core/common/autofill_prefs.h b/components/autofill/core/common/autofill_prefs.h
|
|
--- a/components/autofill/core/common/autofill_prefs.h
|
|
+++ b/components/autofill/core/common/autofill_prefs.h
|
|
@@ -153,6 +153,11 @@ inline constexpr char kAutofillWasNameAndEmailProfileUsed[] =
|
|
// retention policy was run.
|
|
inline constexpr char kAutocompleteLastVersionRetentionPolicy[] =
|
|
"autocomplete.retention_policy_last_version";
|
|
+// Boolean that is true to enable native Android Autofill
|
|
+inline constexpr char kAutofillAndroidEnabled[] =
|
|
+ "autofill.android_autofill_enabled";
|
|
+inline constexpr char kAutofillAndroidIncognitoEnabled[] =
|
|
+ "autofill.android_autofill_incognito_enabled";
|
|
#if BUILDFLAG(IS_MAC) || BUILDFLAG(IS_WIN) || BUILDFLAG(IS_ANDROID) || \
|
|
BUILDFLAG(IS_IOS) || BUILDFLAG(IS_CHROMEOS)
|
|
// Boolean that is set when payment methods mandatory re-auth is enabled by the
|
|
diff --git a/components/password_manager/core/browser/password_form_manager.cc b/components/password_manager/core/browser/password_form_manager.cc
|
|
--- a/components/password_manager/core/browser/password_form_manager.cc
|
|
+++ b/components/password_manager/core/browser/password_form_manager.cc
|
|
@@ -1200,6 +1200,10 @@ void PasswordFormManager::FillNow() {
|
|
}
|
|
autofills_left_--;
|
|
|
|
+#if BUILDFLAG(IS_ANDROID)
|
|
+ client_->OnFillNow();
|
|
+#endif
|
|
+
|
|
// There are additional signals (server-side data) and parse results in
|
|
// filling and saving mode might be different so it is better not to cache
|
|
// parse result, but to parse each time again.
|
|
diff --git a/components/password_manager/core/browser/password_manager_client.cc b/components/password_manager/core/browser/password_manager_client.cc
|
|
--- a/components/password_manager/core/browser/password_manager_client.cc
|
|
+++ b/components/password_manager/core/browser/password_manager_client.cc
|
|
@@ -39,6 +39,8 @@ bool PasswordManagerClient::IsAutoSignInEnabled() const {
|
|
}
|
|
|
|
#if BUILDFLAG(IS_ANDROID)
|
|
+void PasswordManagerClient::OnFillNow() {}
|
|
+
|
|
void PasswordManagerClient::ShowPasswordManagerErrorMessage(
|
|
ErrorMessageFlowType flow_type,
|
|
password_manager::PasswordStoreBackendErrorType error_type) {}
|
|
diff --git a/components/password_manager/core/browser/password_manager_client.h b/components/password_manager/core/browser/password_manager_client.h
|
|
--- a/components/password_manager/core/browser/password_manager_client.h
|
|
+++ b/components/password_manager/core/browser/password_manager_client.h
|
|
@@ -228,6 +228,8 @@ class PasswordManagerClient {
|
|
virtual void ShowKeyboardReplacingSurface(
|
|
PasswordManagerDriver* driver,
|
|
const autofill::PasswordSuggestionRequest& request);
|
|
+
|
|
+ virtual void OnFillNow();
|
|
#endif
|
|
|
|
// Checks whether user re-authentication should be triggered before password
|
|
--
|