Closed
Bug 982969
Opened 11 years ago
Closed 11 years ago
Canceling sign-in flow should fire oncancel(), not onerror()
Categories
(Firefox OS Graveyard :: FxA, defect)
Firefox OS Graveyard
FxA
Tracking
(Not tracked)
RESOLVED
FIXED
2.0 S2 (23may)
People
(Reporter: jedp, Assigned: spenrose)
References
Details
Attachments
(1 file, 2 obsolete files)
4.76 KB,
patch
|
Details | Diff | Splinter Review |
If the user cancels the sign-in flow, we should fire the oncancel() callback registered by the RP as part of the request() call (if any), not the onerror() callback.
Presently, we are firing errors like: {"error":"UI_ERROR","details":{"id":"{6db97549-ab00-7042-aca8-d1af39e88dc2}","error":"DIALOG_CLOSED_BY_USER"}}
More about request() and oncancel(): https://developer.mozilla.org/en-US/docs/Web/API/navigator.id.request
Assignee | ||
Comment 1•11 years ago
|
||
This looks like several small changes to a series of files to add oncancel to the various message and callback APIs. Also, it does not look like a blocker to me. I'm going to take it but assign it to the nice-to-haves, at the top of my personal queue. Jed could you let me know if this should remain a blocker for landing pref-ed off?
Reporter | ||
Comment 2•11 years ago
|
||
I don't think it's a blocker for landing preffed-off, no.
Flags: needinfo?(jparsons)
Assignee | ||
Comment 3•11 years ago
|
||
I have now reversed position about 135° from comment 1. Firefox Accounts on FirefoxOS is basically a big set of multiplexers and de-multiplexers for IPC, concurrency, and semantic API channels. The mozFxAccounts*Event is single-channel. Promise-based APIs, notably in services/fxaccounts, are two-channel a la Unix return codes: resolve and reject. "Cancel" is kind of a sibling to that pair, not exactly reject aka "error" but not exactly not error either. We have roughly a third (fractional not ordinal), the receiving third, of a cancel channel implemented via:
toolkit/identity/FirefoxAccounts.jsm:doCancel()
dom/identity/DOMIdentity.jsm:doCancel()
-- "cancel" multiplexed onto single-channel here --
dom/identity/nsDOMIdentity.js:_onCancelRequestCallback()
but it's currently unused in favor of the error channel; hence this bug. I propose that rather than try to land the sending third:
in the Gaia System App, replace error() here with cancel():
apps/system/fxa/js/fxam_manager.js
48: window.parent.FxAccountsUI.error(error);
[a couple more before we leave Gaia]
and an intermediate third in Gecko augmenting the current (Promise) error channel:
b2g/components/FxAccountsUIGlue.js:onContentEvent()
if (msg.error) ...
services/fxaccounts/FxAccountsManager.jsm:_uiRequest()
error => {return this._error(ERROR_UI_ERROR, error);}
toolkit/identity/FirefoxAccounts.jsm:request()
error => // now doError(), could branch to existing doCancel()
we instead grasp one of these horns:
1) Sniff the Gaia error string in toolkit/identity/FirefoxAccounts.jsm and jump to the already-implemented-but-currently-unused cancel channel there. Yuk.
2) Stay in the error channel until we get back to nsDOMIdentity.js, and sniff the Gaia string there. Also yuk, but gets my vote. We can delete the existing cancel channel, which doesn't serve any purpose in non-chrome Gecko that I can think of.
Magic strings from modules we're not supposed to know about stink. But rewriting a Promise-based cross-application library's API and control flow to avoid sniffing strings sucks worse IMO. Jed? Drive-by comments from others?
Flags: needinfo?(jparsons)
Assignee | ||
Comment 4•11 years ago
|
||
This patch implements grasping the second horn of yuk. If we're comfortable with that direction, I'll take the onCancel path out of DOMIdentity.js and toolkit/identity/FirefoxAccounts.jsm
Attachment #8407084 -
Flags: feedback?(jparsons)
Flags: needinfo?(jparsons)
Reporter | ||
Comment 5•11 years ago
|
||
Comment on attachment 8407084 [details] [diff] [review]
982969-detect-cancel-in-error.patch
Review of attachment 8407084 [details] [diff] [review]:
-----------------------------------------------------------------
I'm still pondering this gnarly situation. But for the patch in question, don't remove the oncancel message handler.
More to come ...
::: dom/identity/nsDOMIdentity.js
@@ -505,5 @@
> if (this._rpWatcher.onready) {
> this._rpWatcher.onready();
> }
> break;
> - case "Identity:RP:Watch:OnCancel":
Actually, you don't want to remove this. Persona uses it.
Attachment #8407084 -
Flags: feedback?(jparsons)
Reporter | ||
Comment 6•11 years ago
|
||
I'm beginning to agree with your 3π/4 radians reversal.
Agreed: We could add code to handle oncancel in fxam_ui.js, fxam_manager.js, system/js/fxa_ui.js, so that fxa_iac_client.js would ultimately have success, error, and cancel callbacks for each flow. But when it comes time to shout a mozFxAccountsRPContentEvent down to gecko, FxAccountsUIGlue.js distills those messages into promise acceptances and rejections, and the rest of fxa speaks in terms of promises as well.
So we can either rewrite all of that or, as you suggest, figure out how to map 'cancel' into a promise rejection. So let's say when 'cancel' happens, we continue to reject with the DIALOG_CLOSED_BY_USER string.
The only place where we have 'oncancel' in the BrowserID protocol is as an optional parameter to request() [1]. So we only have to deal with this in one part of the DOM API.
Is it possible then that all we need to do is test for that string in the FirefoxAccounts toolkit module [2], like so?
// handle promise rejection for getAssertion, i.e., request
error => {
log.error("get assertion failed: " + JSON.stringify(error));
if (error == "DIALOG_CLOSED_BY_USER") {
return this.doCancel(aRPId);
}
this.doError(aRPId, error);
}
[1] https://developer.mozilla.org/en-US/docs/Web/API/navigator.id.request#Syntax
[2] https://mxr.mozilla.org/mozilla-central/source/toolkit/identity/FirefoxAccounts.jsm#154
Flags: needinfo?(spenrose)
Assignee | ||
Comment 7•11 years ago
|
||
Yes, although I think we'd still want to rewrite the message reception in nsDOMIdentity to convert a cancel-without-handler to an error, no?
Flags: needinfo?(spenrose)
Reporter | ||
Comment 8•11 years ago
|
||
How about if in the place where we catch "Identity:RP:Watch:OnCancel", if (!this._onCancelRequestCallback), we print a warning in the console that the app isn't handling oncancel.
If they don't care enough about cancel events to listen for them, I don't think we should force them down their error path. That could cause UI to surface or make other disruptive things happen, to prevent which they in turn would have to know about the magic DIALOG_CLOSED_BY_USER string, and so the plague would spread.
Assignee | ||
Updated•11 years ago
|
Component: Identity → FxA
Product: Core → Firefox OS
Assignee | ||
Updated•11 years ago
|
QA Contact: npark
Assignee | ||
Comment 9•11 years ago
|
||
This patch follows your suggestion. I'd be curious to know if you see log output from FirefoxAccounts.jsm. I was not able to (and I tried replacing the local LogUtils). Thanks Jed!
Attachment #8421497 -
Flags: review?(jparsons)
Comment 10•11 years ago
|
||
(In reply to Jed Parsons (use needinfo, please) [:jedp, :jparsons] from comment #6)
> Is it possible then that all we need to do is test for that string in the
> FirefoxAccounts toolkit module [2], like so?
>
> // handle promise rejection for getAssertion, i.e., request
> error => {
> log.error("get assertion failed: " + JSON.stringify(error));
> if (error == "DIALOG_CLOSED_BY_USER") {
> return this.doCancel(aRPId);
> }
> this.doError(aRPId, error);
> }
>
> [1]
> https://developer.mozilla.org/en-US/docs/Web/API/navigator.id.request#Syntax
> [2]
> https://mxr.mozilla.org/mozilla-central/source/toolkit/identity/
> FirefoxAccounts.jsm#154
FWIW I believe this is the way to solve this issue.
Reporter | ||
Comment 11•11 years ago
|
||
> FWIW I believe this is the way to solve this issue.
Thanks for chiming in, ferjm. It's always reassuring to hear from you.
Reporter | ||
Comment 12•11 years ago
|
||
Comment on attachment 8421497 [details] [diff] [review]
982969-detect-cancel-in-error.patch
Review of attachment 8421497 [details] [diff] [review]:
-----------------------------------------------------------------
Looks good to me, Sam. Thanks for your work on this!
::: b2g/components/FxAccountsMgmtService.jsm
@@ +79,5 @@
> }
>
> + if (msg.error) {
> + self._onReject(msg.id, msg.error);
> + return
nit - missing a semicolon
::: toolkit/identity/FirefoxAccounts.jsm
@@ +241,5 @@
>
> doError: function doError(aRpCallerId, aError) {
> let rp = this._rpFlows.get(aRpCallerId);
> if (!rp) {
> + log.warn("doError found no rp to go with callerId " + aRpCallerId + "\n");
I know it was already there, but I don't think we need the trailing newline in the log call. Looks like a dump() was morphed to log.warn() at some point. Quite possible it's my handiwork :)
Attachment #8421497 -
Flags: review?(jparsons) → review+
Assignee | ||
Comment 13•11 years ago
|
||
https://tbpl.mozilla.org/?tree=Try&rev=f61036895c05
Nits fixed; thanks Jed!
Attachment #8407084 -
Attachment is obsolete: true
Attachment #8421497 -
Attachment is obsolete: true
Assignee | ||
Updated•11 years ago
|
Keywords: checkin-needed
Comment 14•11 years ago
|
||
Keywords: checkin-needed
Status: NEW → RESOLVED
Closed: 11 years ago
Resolution: --- → FIXED
Target Milestone: --- → 2.0 S2 (23may)
You need to log in
before you can comment on or make changes to this bug.
Description
•