зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1599873 - [1.3] Implement Login Storage prompt backend for save requests. r=MattN,geckoview-reviewers,snorp
Differential Revision: https://phabricator.services.mozilla.com/D57011 --HG-- extra : moz-landing-system : lando
This commit is contained in:
Родитель
0ce2d82896
Коммит
0127aa97c4
|
@ -11,17 +11,27 @@ category profile-after-change GeckoViewStartup @mozilla.org/geckoview/startup;1
|
|||
component {42f3c238-e8e8-4015-9ca2-148723a8afcf} GeckoViewPermission.js
|
||||
contract @mozilla.org/content-permission/prompt;1 {42f3c238-e8e8-4015-9ca2-148723a8afcf}
|
||||
|
||||
# GeckoViewPrompt.js
|
||||
# GeckoViewPrompt.js PromptFactory
|
||||
component {076ac188-23c1-4390-aa08-7ef1f78ca5d9} GeckoViewPrompt.js
|
||||
contract @mozilla.org/embedcomp/prompt-service;1 {076ac188-23c1-4390-aa08-7ef1f78ca5d9}
|
||||
contract @mozilla.org/prompter;1 {076ac188-23c1-4390-aa08-7ef1f78ca5d9}
|
||||
|
||||
# GeckoViewPrompt.js ColorPickerDelegate
|
||||
component {aa0dd6fc-73dd-4621-8385-c0b377e02cee} GeckoViewPrompt.js process=main
|
||||
contract @mozilla.org/colorpicker;1 {aa0dd6fc-73dd-4621-8385-c0b377e02cee} process=main
|
||||
|
||||
# GeckoViewPrompt.js FilePickerDelegate
|
||||
component {e4565e36-f101-4bf5-950b-4be0887785a9} GeckoViewPrompt.js process=main
|
||||
contract @mozilla.org/filepicker;1 {e4565e36-f101-4bf5-950b-4be0887785a9} process=main
|
||||
|
||||
# GeckoViewPrompt.js ShareDelegate
|
||||
component {1201d357-8417-4926-a694-e6408fbedcf8} GeckoViewPrompt.js process=main
|
||||
contract @mozilla.org/sharepicker;1 {1201d357-8417-4926-a694-e6408fbedcf8} process=main
|
||||
|
||||
# GeckoViewPrompt.js LoginStorageDelegate
|
||||
component {3d765750-1c3d-11ea-aaef-0800200c9a66} GeckoViewPrompt.js process=main
|
||||
contract @mozilla.org/login-manager/prompter;1 {3d765750-1c3d-11ea-aaef-0800200c9a66} process=main
|
||||
|
||||
# GeckoViewExternalAppService.js
|
||||
component {a89eeec6-6608-42ee-a4f8-04d425992f45} GeckoViewExternalAppService.js
|
||||
contract @mozilla.org/uriloader/external-helper-app-service;1 {a89eeec6-6608-42ee-a4f8-04d425992f45}
|
||||
|
|
|
@ -10,6 +10,8 @@ XPCOMUtils.defineLazyModuleGetters(this, {
|
|||
EventDispatcher: "resource://gre/modules/Messaging.jsm",
|
||||
FileUtils: "resource://gre/modules/FileUtils.jsm",
|
||||
GeckoViewUtils: "resource://gre/modules/GeckoViewUtils.jsm",
|
||||
GeckoViewLoginStorage: "resource://gre/modules/GeckoViewLoginStorage.jsm",
|
||||
LoginEntry: "resource://gre/modules/GeckoViewLoginStorage.jsm",
|
||||
Services: "resource://gre/modules/Services.jsm",
|
||||
});
|
||||
|
||||
|
@ -1189,9 +1191,98 @@ ShareDelegate.prototype = {
|
|||
},
|
||||
};
|
||||
|
||||
// Sync with LoginStoragePrompt.Type in GeckoSession.java.
|
||||
const LoginStorageType = { SAVE: 1 };
|
||||
// Sync with LoginStoragePrompt.Hint in GeckoSession.java.
|
||||
const LoginStorageHint = { NONE: 0 };
|
||||
|
||||
class LoginStorageDelegate {
|
||||
get classID() {
|
||||
return Components.ID("{3d765750-1c3d-11ea-aaef-0800200c9a66}");
|
||||
}
|
||||
|
||||
get QueryInterface() {
|
||||
return ChromeUtils.generateQI([Ci.nsILoginManagerPrompter]);
|
||||
}
|
||||
|
||||
_createMessage(aType, aHint, aLogins) {
|
||||
return {
|
||||
// Sync with GeckoSession.handlePromptEvent.
|
||||
type: "loginStorage",
|
||||
lsType: aType,
|
||||
hint: aHint,
|
||||
logins: aLogins,
|
||||
};
|
||||
}
|
||||
|
||||
promptToSavePassword(
|
||||
aBrowser,
|
||||
aLogin,
|
||||
dismissed = false,
|
||||
notifySaved = false
|
||||
) {
|
||||
const prompt = new PromptDelegate(aBrowser.ownerGlobal);
|
||||
prompt.asyncShowPrompt(
|
||||
this._createMessage(LoginStorageType.SAVE, LoginStorageHint.NONE, [
|
||||
LoginEntry.fromLoginInfo(aLogin),
|
||||
]),
|
||||
result => {
|
||||
if (!result || result.login === undefined) {
|
||||
return;
|
||||
}
|
||||
|
||||
const loginInfo = LoginEntry.fromBundle(result.login).toLoginInfo();
|
||||
Services.obs.notifyObservers(loginInfo, "passwordmgr-prompt-save");
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
promptToChangePassword(
|
||||
aBrowser,
|
||||
aOldLogin,
|
||||
aNewLogin,
|
||||
dismissed = false,
|
||||
notifySaved = false,
|
||||
autoSavedLoginGuid = ""
|
||||
) {
|
||||
const newLogin = LoginEntry.fromLoginInfo(aOldLogin || aNewLogin);
|
||||
const oldGuid = (aOldLogin && newLogin.guid) || null;
|
||||
newLogin.origin = aNewLogin.origin;
|
||||
newLogin.formActionOrigin = aNewLogin.formActionOrigin;
|
||||
newLogin.password = aNewLogin.password;
|
||||
newLogin.username = aNewLogin.username;
|
||||
|
||||
const prompt = new PromptDelegate(aBrowser.ownerGlobal);
|
||||
prompt.asyncShowPrompt(
|
||||
this._createMessage(LoginStorageType.SAVE, LoginStorageHint.NONE, [
|
||||
newLogin,
|
||||
]),
|
||||
result => {
|
||||
if (!result || result.login === undefined) {
|
||||
return;
|
||||
}
|
||||
|
||||
GeckoViewLoginStorage.onLoginSave(result.login);
|
||||
|
||||
const loginInfo = LoginEntry.fromBundle(result.login).toLoginInfo();
|
||||
Services.obs.notifyObservers(
|
||||
loginInfo,
|
||||
"passwordmgr-prompt-change",
|
||||
oldGuid
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
promptToChangePasswordWithUsernames(aBrowser, aLogins, aNewLogin) {
|
||||
this.promptToChangePassword(aBrowser, null /* oldLogin */, aNewLogin);
|
||||
}
|
||||
}
|
||||
|
||||
this.NSGetFactory = XPCOMUtils.generateNSGetFactory([
|
||||
ColorPickerDelegate,
|
||||
FilePickerDelegate,
|
||||
PromptFactory,
|
||||
ShareDelegate,
|
||||
LoginStorageDelegate,
|
||||
]);
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
|
||||
"use strict";
|
||||
|
||||
const EXPORTED_SYMBOLS = ["GeckoViewLoginStorage"];
|
||||
const EXPORTED_SYMBOLS = ["GeckoViewLoginStorage", "LoginEntry"];
|
||||
|
||||
const { XPCOMUtils } = ChromeUtils.import(
|
||||
"resource://gre/modules/XPCOMUtils.jsm"
|
||||
|
@ -18,6 +18,78 @@ XPCOMUtils.defineLazyModuleGetters(this, {
|
|||
EventDispatcher: "resource://gre/modules/Messaging.jsm",
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "LoginInfo", () =>
|
||||
Components.Constructor(
|
||||
"@mozilla.org/login-manager/loginInfo;1",
|
||||
"nsILoginInfo",
|
||||
"init"
|
||||
)
|
||||
);
|
||||
|
||||
class LoginEntry {
|
||||
constructor() {
|
||||
this.origin = null;
|
||||
this.formActionOrigin = null;
|
||||
this.httpRealm = null;
|
||||
this.username = null;
|
||||
this.password = null;
|
||||
|
||||
// Metadata.
|
||||
this.guid = null;
|
||||
// TODO: Not supported by GV.
|
||||
this.timeCreated = null;
|
||||
this.timeLastUsed = null;
|
||||
this.timePasswordChanged = null;
|
||||
this.timesUsed = null;
|
||||
}
|
||||
|
||||
toLoginInfo() {
|
||||
const info = new LoginInfo(
|
||||
this.origin,
|
||||
this.formActionOrigin,
|
||||
this.httpRealm,
|
||||
this.username,
|
||||
this.password
|
||||
);
|
||||
|
||||
// Metadata.
|
||||
info.QueryInterface(Ci.nsILoginMetaInfo);
|
||||
info.guid = this.guid;
|
||||
info.timeCreated = this.timeCreated;
|
||||
info.timeLastUsed = this.timeLastUsed;
|
||||
info.timePasswordChanged = this.timePasswordChanged;
|
||||
info.timesUsed = this.timesUsed;
|
||||
|
||||
return info;
|
||||
}
|
||||
|
||||
static fromBundle(aObj) {
|
||||
const entry = new LoginEntry();
|
||||
Object.assign(entry, aObj);
|
||||
|
||||
return entry;
|
||||
}
|
||||
|
||||
static fromLoginInfo(aInfo) {
|
||||
const entry = new LoginEntry();
|
||||
entry.origin = aInfo.origin;
|
||||
entry.formActionOrigin = aInfo.formActionOrigin;
|
||||
entry.httpRealm = aInfo.httpRealm;
|
||||
entry.username = aInfo.username;
|
||||
entry.password = aInfo.password;
|
||||
|
||||
// Metadata.
|
||||
aInfo.QueryInterface(Ci.nsILoginMetaInfo);
|
||||
entry.guid = aInfo.guid;
|
||||
entry.timeCreated = aInfo.timeCreated;
|
||||
entry.timeLastUsed = aInfo.timeLastUsed;
|
||||
entry.timePasswordChanged = aInfo.timePasswordChanged;
|
||||
entry.timesUsed = aInfo.timesUsed;
|
||||
|
||||
return entry;
|
||||
}
|
||||
}
|
||||
|
||||
const GeckoViewLoginStorage = {
|
||||
/**
|
||||
* Delegates login entry fetching for the given domain to the attached
|
||||
|
|
Загрузка…
Ссылка в новой задаче