- From: Hallvord Reiar Michaelsen Steen <hallvord@opera.com>
- Date: Mon, 06 May 2013 19:45:06 +0200
- To: "WebAppSec WG" <public-webappsec@w3.org>, "WebApps WG" <public-webapps@w3.org>, "Anne van Kesteren" <annevk@annevk.nl>
> I had a discussion with Hallvord on IRC about the exact semantics we > want for HTTP authentication in the context of CORS (and in particular > for XMLHttpRequest, though it would also affect e.g. <img > crossorigin>). So me and Anne have been going a bit back and forth on IRC, we agree on some stuff and disagree on other points - and we fundamentally agree that some implementor review and input would be valuable to really settle a conclusion on how this murky little intersection of specs should work.. So the basic issue is HTTP authentication (cached and/or supplied by JS) with XHR, and its interaction with CORS and other stuff like the anonymous flag and withCredentials. > Username/password can be passed via open() or the URL. In that case we > first check if the server challenges us (do a request without > Authorization that results in a response with status 401). So far I agree :) > For CORS, we'd return to the caller right there. Here I don't agree anymore. If I want to retrieve a HTTP auth-protected resource with XHR from a CORS-enabled server, the natural thing to do seems to try to pass in the user name and password in the XHR open() call. If the script author supplied user/pass and the server says 401 on a request without Authorization: surely the natural next step is to re-try with Authorization:? Granted, my scenario takes a little bit more work before we reach this point: I think that if user/pass are supplied in open() or URL for a CORS request, the implementation must detect that the request requires preflight, and send "Access-Control-Request-Headers: Authorization" as part of that preflight. Now, this is most definitely a corner case, me an Anne are both concerned about implementation complexity but we seem to draw different conclusions - I think that most of the infrastructure here is going to be in place already and making special XHR-CORS exceptions might be just as complex as implementing retry-with-Authorization, whereas I believe Anne thinks I'm prescribing too much complexity for too little gain. > If the Authorization header is set via setRequestHeader() we'd treat > it as any other header. We assume the developer already checked if he > was challenged or not, etc. I agree with that :) > If an Authorization header was cached for the URL in question > (previous visit) we'd never reuse that under CORS. This *might* be a case for withCredentials - but it doesn't make much sense given that a JS author can't be expected to know if there are cached credentials for some other site, so we've dropped that. However, most browsers prompt for user/pass if XHR (or IMG) requests are challenged - so we need a loophole that make sure the cached credentials from a request *triggered by* XHR *are* used (this is one place that gets overly complex - I'd definitely love to nuke the whole prompts-for-user/pass in response to JS/inlines misfeature. Anyone else agrees we can kill it without too much compat pain..?) > I'd be great to know if there's consensus on this. General not caring works too. Implementor views most welcome, including "I don't really care, either way works for us" :-) BTW, here's a sort of (amateur) flow chart for what I'm proposing - after accepting some of Anne's feedback: https://www.w3.org/Bugs/Public/attachment.cgi?id=1359 I just noticed I have omitted same-origin requests with anonymous flag set - if these get a 401 response we should probably go straight to "Done, content denied". -- Hallvord R. M. Steen Core tester, Opera Software
Received on Monday, 6 May 2013 17:45:07 UTC