Open aaronpk opened 1 month ago
After some discussion in the #indieweb-dev chat today between aaronpk and myself, some things I'm considering are:
Avoiding a new .well-known
feels like a good goal.
Changing the meaning of client_id
to be the URL to the metadata document feels reasonable, but I have concerns.
client_id
- something intended for a human to read. Will human-readable information be lost with this change?client_id
domain name as a fallback?)There are also considerations to be made for transition and roll-out.
IndieAuth providers that use client_id
per the current spec (or even the previous version, before h(-x)-app
microformats were specified) will show users a URL to a JSON document and will most likely make it clickable. I expect that will be a confusing user experience.
(aaronpk mentioned there aren't "that many" IndieAuth providers to update, but I posit that we can't easily know, just as one example, how many people are self-hosting selfauth or how long it will take selfauth to support this client_id
change, and how and when users of selfauth would update.)
IndieAuth clients that implement the current spec will lose out on their rich appearance at IndieAuth providers that switch to the new spec. It would be nice to have a migration doc (and maybe a test tool) to help implementers migrate over!
Putting this at the end because I cannot tell if it is constructive, but I noticed that this proposal only mentions .well-known
and changing the meaning of client_id
. Am I walking into a trap if I ask about adding a link
relation from the existing client_id
-as-human-readable-page to the client information JSON document?
There's also the option of the information just being discoverable via the client_url but that means a second fetch.
I think that's what @martymcguire is referring to by the link rel, but confirming.
Some quick thoughts on the new proposal:
client_id
would be the json document, but the JSON document would contain a client_uri
which would be the human-readable home page for the app (this is already defined in the Dynamic Client Registration protocol which defines the vocabulary of this document)client_id
. (This would provide a reasonable fallback both since it's likely the client developer would have a web page there anyway, but also because the security model of the web is based on domain names so the user would at least see that they are authorizing a client at this domain)As far as a migration path goes, that's definitely a bit challenging from the AS perspective. I agree that many AS's will show the full client_id
URL and make it clickable, which would not be a good UX if someone clicked it.
Another option for migration is to tie the new client_id
behavior to the presence of the (relatively) new indieauth-metadata
URL. While it's not perfect, since that has been "out there" for a while, it could at least reduce the chances of the wrong UX. For example:
indieauth-metadata
link rel, use the client JSON document as the client IDauthorization_endpoint
link rel, use the client home page as beforeAdding a link rel from the client home page to the client metadata JSON document doesn't really solve the problem of indieauth server implementers wanting to avoid the HTML parsing step, which is another drawback to the existing spec, and something that I have heard a lot of pushback on from anyone not already 100% bought in to microformats.
Some quick thoughts on the new proposal:
- The
client_id
would be the json document, but the JSON document would contain aclient_uri
which would be the human-readable home page for the app (this is already defined in the Dynamic Client Registration protocol which defines the vocabulary of this document)- If the metadata file is missing or invalid, the AS SHOULD fall back to displaying the domain name of the
client_id
. (This would provide a reasonable fallback both since it's likely the client developer would have a web page there anyway, but also because the security model of the web is based on domain names so the user would at least see that they are authorizing a client at this domain)As far as a migration path goes, that's definitely a bit challenging from the AS perspective. I agree that many AS's will show the full
client_id
URL and make it clickable, which would not be a good UX if someone clicked it.Another option for migration is to tie the new
client_id
behavior to the presence of the (relatively) newindieauth-metadata
URL. While it's not perfect, since that has been "out there" for a while, it could at least reduce the chances of the wrong UX. For example:
- Client discovers the user's indieauth server from their profile URL
- If the client discovers the
indieauth-metadata
link rel, use the client JSON document as the client ID- If the client discovers the
authorization_endpoint
link rel, use the client home page as beforeAdding a link rel from the client home page to the client metadata JSON document doesn't really solve the problem of indieauth server implementers wanting to avoid the HTML parsing step, which is another drawback to the existing spec, and something that I have heard a lot of pushback on from anyone not already 100% bought in to microformats.
Is it microformats if it is a link header and json file? Manifest files do that and do they get complaints?
I followed the breadcrumbs from that "Login with Weird" above, and found this discussion on Rauthy:
https://github.com/sebadob/rauthy/discussions/146
That's a good motivator for updating to this JSON document client metadata discovery method.
Is it microformats if it is a link header and json file? Manifest files do that and do they get complaints?
The pushback is on parsing HTML. Who are the consumers of manifest files? I suspect that's a very different audience than the consumers of the client metadata we're talking about here.
I might just switch this over for a few of my indieauth clients right now. Worst case is someone's IndieAuth server shows them a slightly longer URL than normal, and they see a JSON page if they click it. But other than that everything else about the flow will still work fine, it's not actually a breaking change.
Nice! I would likely follow suit if there were, say, a blog post explaining what you changed and why. :}
Would this proposal work with clients running on localhost that can't serve the required document? I'm not sure if IndieAuth currently supports that use case anyway.
The current IndieAuth spec says clients SHOULD have a website at the URL in client_id - something intended for a human to read. Will human-readable information be lost with this change?
HTTP content negation could solve this, right? IIRC that's pretty heavily used in the Fediverse to return JSON for machines and HTML for humans.
HTTP content negation could solve this, right? IIRC that's pretty heavily used in the Fediverse to return JSON for machines and HTML for humans.
FWIW content negotiation is also often a source of great pain when it comes to development and interop. https://snarfed.org/2023-03-24_49619-2
Would this proposal work with clients running on localhost that can't serve the required document? I'm not sure if IndieAuth currently supports that use case anyway.
For clients that are running on localhost (e.g. a mobile app), the assumption is that the mobile app also has a web page about the app which is where the metadata is discovered from.
FWIW content negotiation is also often a source of great pain when it comes to development and interop. https://snarfed.org/2023-03-24_49619-2
These are valid concerns. You have to decide if the tradeoffs are worth it. Note that in practice I think a lot of the drawbacks of content negotiation tend to be specific to the data API case (see here). It might not cause as many problems in this situation.
For clients that are running on localhost (e.g. a mobile app), the assumption is that the mobile app also has a web page about the app which is where the metadata is discovered from.
That would limit the app to running it's OAuth2 client on a specific port, which might be taken by another app, right?
No, there is an exception for exact redirect URI matching for localhost URLs, see:
Alternatively, a mobile app on iOS/Android can use app-claimed HTTPS URLs as the redirect URI, so the localhost issue goes away entirely.
I wasn't aware of that; nice!
I just implemented this in webmention.io and indielogin.com. Here's the PR that adds support to indielogin.com as a client:
I updated my IndieAuth server on aaronparecki.com to look for the JSON data as well. It's not open source so I can't link to the changes, but it was super easy.
Since I want to support both for a while, I first try to parse the page as JSON to extract the values. If that fails, I fall back to the existing behavior of parsing the page for Microformats. So it's really not a huge deal to add this new behavior to an IndieAuth server asap.
I also started working on a spec that describes this discovery method as an OAuth extension:
https://github.com/aaronpk/draft-parecki-oauth-client-id-metadata-document
Since this isn't actually anything unique to IndieAuth, other flavors of OAuth might also want to take advantage of this mechanism.
I implemented this on https://indiebookclub.biz. Git commit: https://github.com/gRegorLove/indiebookclub/commit/4b685740e9a11ef406fef6cebbed2337dfc11f6f
The current method of client information discovery (fetching the client_id and parsing the HTML page for microformats) has received a lot of pushback from various people otherwise interested in implementing IndieAuth. This method is also somewhat limited in that it requires defining a Microformats vocabulary for client information, rather than using the existing vocabulary of client information that's defined by RFC 7591 Dynamic Client Registration.
An alternative proposal for client information discovery was proposed in draft-looker-oauth-client-id-scheme, where the AS uses the client ID URL as the base URL and appends a
.well-known
string in order to find a JSON document with the client metadata. While this approach gets around the HTML/Microformats challenges, it is also not ideal because of the requirement of the.well-known
path.A middle ground (and interestingly, what Solid-OIDC has done), is to instead make the client ID URL be the URL to the metadata document.
So an IndieAuth client such as https://webmention.io would choose a URL to host its client metadata document, for example
https://webmention.io/indieauth/client.json
. This is the value it would use as theclient_id
in the OAuth flow.The AS would see the
client_id
URL in the authorize request and fetch the URL directly in order to find the client metadata. The metadata values would be the values defined by Dynamic Client Registration, such asredirect_urls
,client_name
, etc.