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

Allow public clients (e.g. SPAs using implicit flow or PKCE) to have redirect URLs other than localhost #1822

Merged

Conversation

heidemn-faro
Copy link
Contributor

@heidemn-faro heidemn-faro commented Oct 5, 2020

@heidemn-faro heidemn-faro mentioned this pull request Oct 5, 2020
}
}
// For non-public clients, only named RedirectURIs are allowed.
if !client.Public {
return false
}
Copy link
Contributor Author

Choose a reason for hiding this comment

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

Our use case is to use PKCE for a web app that doesn't run on "localhost".
Therefore, we would like that RedirectURIs are also considered for public clients.
PKCE was definitely also intended for web apps, and you can already configure such web apps e.g. in Okta or Auth0.

The following code to allow any localhost URI, redirectURIOOB or deviceCallbackURI for public clients is still active.
An alternative could be to no longer allow these special URLs implicitly when RedirectURIs is non-empty.
I don't have a strong opinion if this would be better. The maintainers should decide.

Copy link
Contributor

Choose a reason for hiding this comment

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

I think the implementation is good as it is. The alternative of not supporting the special URLs, when redirectURIs is defined, would break currently working configurations.

Copy link
Contributor

Choose a reason for hiding this comment

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

I would personally prefer the logic to only allow whitelisted redirect uris, if the list is non-empty.

This would tighten the security and would not break existing configurations that do not use RedirectURIs for public clients.
And I bet the most configurations that do currently use it for public clients operate under the false assumption that the list is actually respected (I know we did in our deployment for some time).

Copy link
Contributor

Choose a reason for hiding this comment

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

I fear that there are configurations that may be working by accident, because currently it is possible to have the RedirectURIs wrongly configured, and it still works.

Let's see what the maintainers decide.

Copy link
Member

Choose a reason for hiding this comment

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

I think we can fix that by properly documenting this change or mentioning it in the change log.

Copy link
Member

Choose a reason for hiding this comment

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

I would personally prefer the logic to only allow whitelisted redirect uris, if the list is non-empty.

@tkleczek AFAICT this is not the case now, but the rest of the conditions provide backwards compatibility and limit redirect uris to redirectURIOOB, deviceCallbackURI or localhost for public clients which seems fine. WDYT?

Copy link
Contributor

Choose a reason for hiding this comment

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

My concern is that for SPAs allowing localhost redirects seems like an unnecessary risk.
But if we care about potential backwards compatibility issues more, then I am fine with the change as it is.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

My concern is that for SPAs allowing localhost redirects seems like an unnecessary risk.

That's actually true. Consider that e.g. a malicious desktop app could obtain a token intended for https://webapp.com , since the desktop app can run a server listening on http://localhost .
If the user is already logged in at the IDP in the browser, then this could probably be done without user interaction.
The desktop app could then call the API of https://webapp.com with the token.

So I would prefer not to allow these special URLs implicitly if RedirectURIs is non-empty.

In the future, three additional boolean options could be added to explicitly (dis)allow each of redirectURIOOB, deviceCallbackURI or localhost-ish URLs. But this would definitely break backwards compatibility, and might be over-engineering.

Copy link
Contributor Author

@heidemn-faro heidemn-faro Nov 2, 2020

Choose a reason for hiding this comment

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

@sagikazarmark I added more tests for these special URIs in c15e288 .
Then I made the change suggested by @tkleczek in 162073b : if !client.Public || len(client.RedirectURIs) > 0 { return false }
As you can see in the tests, it's still possible to explicitly add redirectURIOOB and deviceCallbackURI to the RedirectURIs if needed. So most mobile/desktop/localhost apps should just continue to work, and all others just need to update their configuration.

The only edge case that now doesn't work any more is a combination of 1) named RedirectURIs with 2) localhost URIs with random port. (For desktop apps, random ports must be used, since any hard-coded port might be occupied by another application.)
But this case is weird anyway (using the same client for web app + desktop app?). It can be solved by using two clients instead.

Please take another look.

@heidemn-faro
Copy link
Contributor Author

@tkleczek I saw your comment in an e-mail, can't find it here any more:

I am curious - why don't you configure the app as confidential client if it is a web app and can keep the client secret secure?

What about SPAs without server component, hosted as static websites?
These can use Implicit Flow, or Auth Code + PKCE, and don't need a secret then.

Read more here: https://developer.okta.com/blog/2019/08/22/okta-authjs-pkce

@heidemn-faro heidemn-faro changed the title Allow public clients (e.g. using implicit flow or PKCE) to have redirect URLs other than localhost Allow public clients (e.g. SPAs using implicit flow or PKCE) to have redirect URLs other than localhost Oct 6, 2020
@tkleczek
Copy link
Contributor

tkleczek commented Oct 8, 2020

@heidemn-faro Yes, I realized this soon after I've written my comment and therefore deleted it.

Copy link
Contributor

@HEllRZA HEllRZA left a comment

Choose a reason for hiding this comment

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

LGTM

@sagikazarmark I would propose to add this PR to v2.26.0 milestone, because it enables PKCE #1784 for single page web applications.

@sagikazarmark sagikazarmark added this to the v2.26.0 milestone Oct 13, 2020
@logikone
Copy link

Hey, thanks for this! Just wanted to ask quickly what the timeline is on getting this merged and releasing v2.26.0? Thanks in advance!

@sagikazarmark
Copy link
Member

I'll try to get this merged and released this week.

@logikone
Copy link

I'll try to get this merged and released this week.

@sagikazarmark awesome, thank you sir!

…ect URIs configured

Signed-off-by: Martin Heide <martin.heide@faro.com>
Signed-off-by: Martin Heide <martin.heide@faro.com>
@heidemn-faro heidemn-faro force-pushed the feature/redirect-uris-for-public-clients branch from 7e9dd88 to 1ea481b Compare November 2, 2020 13:08
Signed-off-by: Martin Heide <martin.heide@faro.com>
…Is is set

Signed-off-by: Martin Heide <martin.heide@faro.com>
Copy link
Member

@sagikazarmark sagikazarmark left a comment

Choose a reason for hiding this comment

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

LGTM, thanks!

@sagikazarmark sagikazarmark merged commit 1707947 into dexidp:master Nov 5, 2020
leonnicolas added a commit to leonnicolas/website that referenced this pull request Feb 14, 2023
The PRs dexidp/dex#1784 and dexidp/dex#1822 are super useful, but the documentation can be confusing.

First, it does not make sense to specify a secret in a public client because it will require you to pass the secret to the public client, which will make the secret "not secret".

Also, as of dexidp/dex#1822, it is possible to use `redirectURIs` in a public client.

Signed-off-by: leonnicolas <60091705+leonnicolas@users.noreply.github.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

6 participants