Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add the IDP sign-in status API to the spec #436

Merged
merged 47 commits into from
Oct 13, 2023
Merged
Changes from 1 commit
Commits
Show all changes
47 commits
Select commit Hold shift + click to select a range
e2f48cc
Add the IDP sign-in status API to the spec
cbiesinger Feb 14, 2023
8304968
Address comments
cbiesinger Feb 15, 2023
465c717
Add the JavaScript API
cbiesinger Feb 15, 2023
896e95d
void->undefined and add an Issue comment regarding Promise
cbiesinger Feb 15, 2023
07eb407
Slightly more direct way to get the origin
cbiesinger Feb 15, 2023
8948f99
Add a multi-IDP note and clarify a signin note
cbiesinger Feb 15, 2023
f19c445
Elaborate on state clearing
cbiesinger Feb 16, 2023
663f421
Merge remote-tracking branch 'upstream/main' into status2
cbiesinger Aug 11, 2023
090262d
Fix bikeshed syntax errors
cbiesinger Aug 11, 2023
d682586
Merge branch 'syntax' into status2
cbiesinger Aug 11, 2023
9557220
Merge remote-tracking branch 'upstream/main' into status2
cbiesinger Aug 11, 2023
0c154cb
define interaction with clear-site-data
cbiesinger Aug 11, 2023
d932e3f
better structure
cbiesinger Aug 11, 2023
f128898
less prescriptive about parameter location
cbiesinger Aug 11, 2023
71083c8
typo
cbiesinger Aug 11, 2023
3fbe365
period
cbiesinger Aug 11, 2023
238fdf4
fix merge error
cbiesinger Aug 11, 2023
13ca4f7
elaborate on cookie deletion
cbiesinger Aug 11, 2023
4db1336
Merge remote-tracking branch 'upstream/main' into status2
cbiesinger Aug 23, 2023
0c77ac9
review comments
cbiesinger Aug 23, 2023
afe7360
fix IDL syntax error
cbiesinger Aug 23, 2023
ddb3f24
automation
cbiesinger Aug 23, 2023
2098134
fix most comments from the PR
cbiesinger Sep 7, 2023
5b091a0
more editorial fixes
cbiesinger Sep 7, 2023
6a38c4b
add subheadings to signin status api section
cbiesinger Sep 7, 2023
654908f
specify IDP signin flow
cbiesinger Sep 8, 2023
652b436
Better specify popup creation
cbiesinger Sep 19, 2023
fb02431
Editorial comments from TallTed
cbiesinger Sep 20, 2023
d70fa1f
npm comments
cbiesinger Sep 20, 2023
620848c
update HTTP header section
cbiesinger Sep 20, 2023
b6b9be3
editorial fixes
cbiesinger Sep 20, 2023
436ee85
update IDL
cbiesinger Sep 20, 2023
3c8eb4a
fix typo
cbiesinger Sep 20, 2023
04e7156
better handle header origins
cbiesinger Sep 25, 2023
99147b3
clarify some traversable things
cbiesinger Sep 25, 2023
e7ab849
signin -> login
cbiesinger Sep 25, 2023
1fbab48
missed one
cbiesinger Sep 25, 2023
7f6eef5
npm comments
cbiesinger Sep 27, 2023
0f0c4fe
review comments and change signin to login
cbiesinger Sep 28, 2023
e80e54a
signin_url -> login_url
cbiesinger Sep 28, 2023
bf30c3d
replace a few more sign-ins
cbiesinger Sep 28, 2023
49fe2ad
linkify
cbiesinger Sep 28, 2023
2133a0b
review comments
cbiesinger Oct 3, 2023
d28201f
get a login status entry algorithm
cbiesinger Oct 3, 2023
0d55b05
review comments
cbiesinger Oct 10, 2023
60cdb08
review comments
cbiesinger Oct 12, 2023
48e4d1a
last? comments
cbiesinger Oct 13, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 42 additions & 0 deletions spec/index.bs
Original file line number Diff line number Diff line change
Expand Up @@ -301,6 +301,30 @@ value (which is used when a resource loaded as a third-party, not first-party).
for an [=IDP=] to adopt the FedCM API without introducing security issues on the API, since the
[=RP=] cannot inspect the results from the fetches in any way.

<!-- ============================================================ -->
## IDP sign-in status ## {#browser-api-idp-sign-in-status}
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
<!-- ============================================================ -->

Each [=user agent=] keeps a global, persistent <dfn>IDP sign-in status
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
map</dfn>, an initially empty [=map=]. The [=map/keys=] in this map are
[=/origin=] (of IDPs), and the [=map/values=] are enums that can be one of
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We need to find a way to store the "type=idp" here too.

In addition to the "type, ideally, we would also make this extensible, so that different "types" could store different things. Here is a possible use of the Login Status API:

https://github.com/samuelgoto/login-status-api#browser-status-ui

// Records that the user is logging-in to a FedCM-compliant Identity Provider.
navigator.setLoggedIn({
  profile: {
    name: "John Doe",
    picture: "https://website.com/john-doe/profile.png",
  }
});

So, maybe, we should have something that stores dict[origin] -≥ (status, dict[type] -> blob) ?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually, as long as this is only used by FedCM, I think it's fine to only store something if type=idp was specified. The API should allow more but since the backend storage is abstract anyway and UAs will store it in a browser-specific way, I think there's no harm in pretending we only store type=idp data with no extra metadata.

cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
"unknown", "signed-in", and "signed-out".
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved

The user agent checks all page and subresource loads for an HTTP response
header named `IdP-SignIn-Status` containing [[RFC9110#parameter|Parameter]]s.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think header response names need to be defined. Other than that this checking of all headers in everything sounds like something that needs to be integrated into the Fetch spec (this is a monkeypatch). Perhaps note that as an issue.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If I understood you correctly, done (both parts).

If that header exists and the first parameter has a name of `action`,
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Presumably this needs to be parsed? Can we perhaps encapsulate this in an algorithm

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tried to clarify my intention here (the parsing is defined by the HTTP spec, is what I was trying to say)

the user agent must process it as follows:

cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
* If this is a subresource request, and the subresource does not have the
same [=/origin] as the toplevel page, ignore the header.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you mean by the origin of the subresource? Presumably the final origin? I think this needs to be pulled from the response itself (I imagine the request may only have the initial origin)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done, I think, unless you had something else in mind for the wording?

cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
* Otherwise:
* If the parameter value is `signin`, add (or replace) an entry in the
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
[=IDP sign-in status map=] with the key being the origin of the resource
and the value being "signed-in"
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
* If the parameter value is `signout-all`, add (or replace) an entry in the
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
[=IDP sign-in status map=] with the key being the origin of the resource
and the value being "signed-out"
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved

<!-- ============================================================ -->
## The State Machine ## {#browser-api-state-machine}
<!-- ============================================================ -->
Expand Down Expand Up @@ -490,11 +514,28 @@ To <dfn>create an IdentityCredential</dfn> given an {{IdentityProviderConfig}}
|provider| and a |globalObject|, run the following steps. This returns an {{IdentityCredential}} or
failure.
1. Assert: These steps are running [=in parallel=].
1. Let |signinStatus| be the value of the entry in [=IDP sign-in status map=]
with the key being the origin of |provider|'s configURL. If there is
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
no such entry, set it to a user-agent specific default (either "unknown" or
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
"signed-out").
1. If |signinStatus| is "signed-out", return failure.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Am I following it right that if a user is "signed out", any use of the API fails without a dialog?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, just like (today) the API fails without a dialog if the user is not logged in.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be nice to have a way to cleanly recover from a signed-out state without having to navigate to the identity provider independently. This has something to do with how to integrate this with the Multi-IDP patch, since I think their integration is non-trivial.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I added a "Issue:" for now. I think the multi-IDP PR is maybe a better place to discuss how to integrate these two?

1. Let |config| be the result of running [=fetch the config file=] with |provider| and
|globalObject|.
1. If |config| is failure, return failure.
1. Let |accountsList| be the result of [=fetch the accounts list=] with |config|, |provider|,
and |globalObject|.
1. If the fetch failed, or the size of |accountsList| is 0:
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
1. Add (or replace) an entry in the [=IDP sign-in status map=] with the
key being the origin of the configURL and the value being "signed-out".
1. If |signinStatus| is "signed-in", show a dialog to the user and return
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

does this mean that the sign-in status map and the actual state is out of sync at this point?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The previous step should ensure they are in sync, right?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was confused because showing a sign in link in the dialog when the status was signed-in is non-intuitive to me. I think this makes sense.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I reworded the note a bit to hopefully make this more clear.

failure.

Note: It is recommended that this dialog provides a "sign in" button
cbiesinger marked this conversation as resolved.
Show resolved Hide resolved
allowing the user to sign in to the IDP using
{{IdentityProviderAPIConfig/signin_url}}.
1. If |signinStatus| is "unknown", add (or replace) an entry in the [=IDP
sign-in status map=] with the key being the origin of the configURL and
the value being "signed-out".
1. For each |account| in |accountsList|:
1. If |account|["{{IdentityProviderAccount/picture}}"] is present,
[=fetch the account picture=] with |account| and |globalObject|.
Expand Down Expand Up @@ -675,6 +716,7 @@ dictionary IdentityProviderAPIConfig {
required USVString accounts_endpoint;
required USVString client_metadata_endpoint;
required USVString id_assertion_endpoint;
USVString signin_url;
IdentityProviderBranding branding;
};
</xmp>
Expand Down