How can I authenticate multiple applications with a single authentication mechanism?. These applications are having existing authentication within them, perhaps I need to authenticate these apps into my system which is isolated from others. Please suggest a better approach
When using OpenID Connect, the first application the user logs in to, will redirect the user's browser to the authorization server (AS). Since the user does not have a session between the browser and the AS, it will present the login screen. The user signs in and is redirected to the application (client) with an ID token and access token. The application will then establish a session between the browser and the application (typically a cookie)
When the user navigates to the second application, it will also redirect the user to the AS, but now the user already has a valid session between the browser and the AS, so the AS won't show the login screen (it may show the consent screen if the user has not consented to the requested scopes), and will issue an ID token and access token to the second application.
Now the user has a authenticated session with both applications with a single sign on (SSO).
If you use OAuth 2.0 with OIDC, you can authenticate your user once and verify the access token at each app the user visits. This is a typical single sign-on flow (SSO).
Related
I have
UI (a single page app)
an external authentication server
my own authorization server
resource server (my own backend APIs)
Here's what I am trying to do
UI/User gets an AuthN token from the external authentication server.
UI sends the AuthN token to get the an AuthZ token from my own authorization server
UI uses the AuthZ token to retrieve data from the resource server
But the problem is I don't know if the user is still authenticated anymore because I stopped using the AuthN token from step 3. Should I use both tokens together? or somehow consolidate the 2 tokens into one? Hope to get some ideas from here. Thanks!!
COMPONENTS
This is the standard way of managing components:
UI makes an OpenID Connect redirect to the Authorization Server (AS)
AS makes a second OpenID Connect redirect to the authentication system. There could be more than one of these, eg Google, Facebook.
After user sign in the AS issues the same tokens for your UI and resource server, regardless of how the user signs in. The UI sends access tokens to the resource server which can authorize based on scopes and claims received.
Unless you have special reasons, do not use foreign tokens from authentication systems in your own applications. This is because you are not in a position to control their contents.
OPENID CONNECT RE-AUTHENTICATION MECHANISMS
The OpenID Connect prompt and max-age parameters can be used to control how frequently the user is prompted to re-authenticate, and the auth_time claim can be issued in ID tokens to inform the UI of the last authentication time.
For example your app could use access tokens that last 15 minutes. Whenever they expire you could send a request with a prompt-none parameter to see if the user is still authenticated. If not then you will receive a login_required response and you could then redirect the user to re-authenticate.
SINGLE LOGOUT
Knowing if the user is still authenticated suggests you need to know if they signed out in another app. OpenID Connect has four Single Logout Mechanisms that you should be aware of, and which may possibly work for your scenario.
This is a technical area that has never worked perfectly in any Single Sign On technology though. This may be because you do not control all apps, or because of technical limitations, eg Google may not inform the Authorization Server if the user signs out of Gmail.
SUMMARY
Your apps should only use the authorization server tokens. Use OIDC request parameters to control when the user must re-authenticate.
With the use of IdentityServer4 and the OIDC protocol, I've managed to get my SPA and my .net core web api authenticating against a sql server user store, as well as ADFS which is great. However, when the user first clicks the 'Continue with ADFS' button, the login prompt is shown asking the user for their credentials. My understanding was that with the use of openId connect and IdentityServer, we could add external identity providers such as ADFS to our IdentityServer application and if ADFS is chosen for login with the user already logged in to ADFS via their local machine, then the authentication would happen seamlessly without the need to input windows user credentials again. There are other steps in order to achieve this of course, like linking the ADFS UserId with our SQL Database User Id table, but overall my understanding was that this would be entirely possible.
After a user logs out from an ADFS login, the next time the user chooses to log back in with ADFS, the 'Challenge' method that is run within my IdentityServer application to initiate the redirect to ADFS often recognises that the user has already logged in recently and therefore just logs them right in without the need for their credentials again.
My question is - is it actually possible to avoid the initial login prompt altogether? Or will the browser insist that credentials are provided if the user hasn't logged into the application for a while?
It certainly is possible but it may involve specific browser config in ADFS and also may require your IDP to be in the intranet zone in Windows Internet settings.
Check out these articles:
https://learn.microsoft.com/en-us/windows-server/identity/ad-fs/operations/configure-intranet-forms-based-authentication-for-devices-that-do-not-support-wia
https://learn.microsoft.com/en-us/windows-server/identity/ad-fs/operations/configure-ad-fs-browser-wia
I'm implementing Facebook and Google SSO on my website using custom workflow (redirect urls, parsing on server side etc. - no javascript) and I got to the point I have access_token, token_type and expires_in and from Google also id_token and I am confused what to do next to authenticate the user.
I read a little about authorization vs authentication, and that Facebook and Google SSO is OAuth2 which provides authorization, but not authentication, from which I understand that this way my web application is authorized to do something on behalf of the user, but I cannot be sure the user is the one who I think he is? My main source is this: OAuth Authorization vs Authentication
So, my question is, what should I do to be able to can consider the user logged in.
Thank you
In your case google (and facebook) is authenticators. This services just tells your application that user who try to login to your system is the one who he wants to appear.
Assume you differentiate users by unique email.
Your application flow should be next:
The user try to login to application using google Application do all redirection google flow stuff and gives you tokens
Application need to store this tokens for future use
Application check if this user's email presented in database
If email is presented and google returns tokens (google authenticate your user successfully) you can login user in your app
If email isn't presented in database but google authenticate user successfully you can store this user (with email) to your database - sign it up - this is new user in your system
Same flow with Facebook. Surely you can extend this logic to be more your application specific.
SSO and OAuth are different. OAuth is authorization protocol.
You are dealing Google and Facebook oauth.
OAuth
In case of oauth, after successful authentication(google/facebook) you will get access token. You can use token for maintaining the user session.
With this token user is authorized, Now you should check whether the user is present in your database, if yes then authenticate the user and redirect to your application.
SSO
SSO is user authentication service. There are way to implementing SSO like kerberos SSO, ADFS SSO.
We should never use OAuth2 access token for authentication.
For details, please refer
https://oauth.net/articles/authentication/
The OpenIDConnect, built on top of OAuth2, can be used for authentication.
Google supports OpenIDConnect
https://developers.google.com/identity/protocols/OpenIDConnect
The basic idea is Google will issue the client app (your application) a ID Token after the user has login his Google account. You can then extract user information (e.g. email, unique user id) from this ID token and proceed your login flow.
I'm trying to wrap my head around SSO. It's my understanding that SSO allows you to login once and get access to multiple apps (if you have rights). So, I log into App A. I establish a token. How does that token become available to App B so I do not have to login to App B again (assuming user has rights to A and B)? My Apps are AngularJs apps. I access .Net WebAPis for data.
I can see if I login to App A and retrieve a token then launch App B from App A by passing the token to App B. This way App B has the token and can send to server to make sure user has access to B. However, if user opens a browser directly and goes to App B, then how does their session get established with existing token?
If the answer is there's session state on the back-end server, then how does session state match the user logged in App A with the new request for App B?
Thanks.
Well, there are certainly many ways to achieve it, and it can be tricky. I can give you one solution as an example:
Consider two apps on different subdomains:
The Fine Corinthian Turkey Shop (turkey.example.com)
Rent a Baboon (monkey.example.com)
These two web apps want to share signon, and arrange for a third hosted website for their single sign-on:
sso.example.com
Then the flow is:
Frank visits http://turkey.example.com/orders/12
Turkey redirects to https://sso.example.com/login
SSO presents user with login form, validates and issues token
The token is saved in a cookie on SSO.
User is now validated on SSO, but needs to get the token back to turkey.
SSO stores a combination of (Guid, Token, Expiry) on the server, where Guid is a random guid and Expiry is something like 30 seconds.
SSO sets a secure cookie on *.example.com containing the Guid
SSO redirects back to http://turkey.example.com/orders/12
Turkey can now retrieve the ticket from the cookie
Turkey calls SSO server and exchanges the ticket for the token.
Turkey stores token in the browser (typically a cookie)
Now let's imagine that Frank wants some nice juicy baboons to go with that turkey:
Frank visits: http://monkey.example.com/order-in-bulk
Monkey sees that Frank has no stored token and redirects to https://sso.example.com/login
SSO sees that Frank is already logged in as he has a stored token.
SSO stores a new (Guid, token, expiry) triple on the server
Process is identical to the initial login the rest of the way
However, if user opens a browser directly and goes to App B, then how
does their session get established with existing token?
If the answer is there's session state on the back-end server, then
how does session state match the user logged in App A with the new
request for App B?
I would say it's more about cookies and redirects than it is tokens. Tokens are generated once a user's identity is established.
So when you hit App B via your browser, App B redirects your user-agent to the Auth Server (which may in turn redirect you to a SSO site).
The thing to note is that the SSO login request is actually an HTTP request between your browser and the SSO server.
So the SSO cookie is already there - because earlier, App A would have also redirected your user-agent to the Auth / SSO server where the login was performed. The SSO server could then persist a cookie between you and it.
I can see if I login to App A and retrieve a token then launch App B
from App A by passing the token to App B.
I'm not sure I understand about App A passing its token to App B. Usually Apps (Oauth 2.0 clients) would not share tokens. App B should make its own request to the Auth server which (if the user is signed in) may skip the login part but would then need to verify that :
App B has rights to the scopes requested and that
the signed-in user has granted access to those scopes.
If the user is logged in and has previously approved scope access then all this processing is seamless to the end user other than a bunch of redirects.
This assuming you use the Implicit grant flow (I noted that one of your apps is an angularjs app).
If you use the code, password or client-credentials Oauth2.0 grants then you may receive a refresh token after initial user login and consent.
The refresh token equates to long-term access (for that app only) without the need again for login and consent from the end-user more than once.
sso.example.com stores a cookie and the same cookie help when Frank goes to monkey.example.com. If sso.example.com feels that cookie is too old then it can ask for login auth again.
Basically I just want to know how does StackExchange's single signon system work?
In the SE network you need to login only once in one of the websites to be automatically logged in to the other sites upon visiting.
How should I implement such a feature in my own network of sites?
I assume it uses the cookie which resides on the user's browser and then authenticates it with the originating site. If it is legit then it logs the user in automatically.
You have to implement SAML or oauth2 to allow sso on your network.
In case of SAML your child websites will be service providers or resource servers.
While you need to setup and identity provider.
The sequence of events will be like this.
1. User hits a url of songs website, this site is resource server and does not handle authentication.
2.To authenticate resource server will construct a SAML authrequest and redirects to identity provider after signing it.
Idp verifies the signature after receiving authrequest.
3. User will be presented with a login form, user has to end login credentials.
4. After user authentication idp will generate a SAMl token and redirect back to resource server.
5. Resource server will extract identity information from SAML token, resource server will login the user with session or cookie.
Depends upon which technology you are working in i have implemented it in php using simplesamlphp.