Currently i am using simplesamlphp and we have successfully implemented SSO, in which SAML request is sending through HTTP-REDIRECT and getting response through HTTP-POST.
Here my doubts are:
Can i send the authentication details(username&password) using HTTP-POST?
Is the simplesamlphp only for authentication or can i use for authorization purpose like oath for Facebook?
When you authenticate with simplesamlPHP, you get a SAML token which contains attributes, These attributes are what are used for authorisation. They can be derived from "a storage of users, a database, a LDAP or a radius interface".
Username can definitely be an attribute. However, password shouldn't be for security reasons.
In terms of authentication, it supports OpenID. For OAuth, I suspect you would have to roll your own authentication module.
Related
I'm having difficulty finding guidance on the implementation of SAML alongside an existing, traditional authentication system.
I have created a SaaS application in CodeIgnitor which has the typical, run-of-the-mill authentication system using a local users table with hashing and salting etc.
I'm looking to add SAML SSO to attract more enterprise customers. I have a question however where my Google Fu is falling short.
How can I integrate SAML authentication so that it works along-side my traditional, local authentication? If my customers choose SAML then I will require them to bind their existing local accounts to their SAML federated identities. What do I do to cater for my non-SAML users?
Do I need two login URL's such as https://app.com/saml/login for my SAML users and https://app.com/login for my non-SAML users, and just expect customers to choose the right one? Or perhaps I ask for their email/username first, and then require them to submit that value to see if they're SAML or not - and route them accordingly?
You need to install an Identity provider (IDP) that supports SAML.
You use the IDP Initiated SAML profile.
Your app. is connected to the IDP via a SAML stack.
Other enterprises can then federate with your IDP i.e. login to your web site with their credentials via SAML.
The IDP Initiated SAML profile provides a URL that you give to customers that takes them to your IDP with their customer credentials and thence to your app.
Users going direct to your website use the local connection.
That said, rather use OpenID Connect - it's much simpler but the principles are the same.
I am using the php-saml toolkit https://github.com/onelogin/php-saml to implement an SSO in a web application. The authentication in itself works but when i check with an intercepting proxy https://portswigger.net/burp/communitydownload the saml token appears in clear (as xml, with the username along with all information passed for authentication). In the connector and the setting https://github.com/onelogin/php-saml/blob/master/settings_example.php i have set the certificate (in idp/x509cert)
I am not sure if the presence of the certFingerprint makes a difference, i tried with and without and the saml token is in clear in both cases.
Is it possible to have this saml response encrypted ? it is still signed so it cannot be changed but having this data in clear is still a problem for me
You can indeed have the SAML response encrypted, and it will need to be setup by your Onelogin administrator for your application. Encrypting the Response ( or the Assertion ) is mitigated by using TLS as you're already encrypted at the transport layer, and most applications I see don't encrypt Response or Assertion, but it's available in Onelogin if needed.
I'm trying to create a simple SSO system in PHP for two domains which are thematically connected.
So I was wondering if it is possible to store a signed JWT token containing user username from domain A to the local storage. And then to verify the JWT using the same secret key from a domain B which would lead to a successfull authentication.
I've search google for some answers and I found some of them containing a middle authentication domain, which would take care of authentication. But I would like just to link the two domains I have.
Thanks.
Cross-origin data storage access from domain B to domain A is not allowed by same-origin policy
Access to data stored in the browser such as localStorage and IndexedDB are separated by origin. Each origin gets its own separate storage, and JavaScript in one origin cannot read from or write to the storage belonging to another origin.
The usual solution is to have a central domain for authentication ( could be A or B) and work with redirections among domains sending the JWT or share the authentication token across domains using an iframe. See details here
OpenId, OAuth and SAML protocol works with redirections, and for example Google web suite has their apps connected trough iframes (Additionally google is an openid-connect provider)
There's no reason why you can't do this. A JWT isn't really anything special, it's simply a token much like a session ID token. The difference between a JWT and any other token is that it can contain a payload of data.
What you're describing is essentially the password grant of OAuth 2.0. Your SSO system is the authorisation server which can authenticate users and supply them with an access token. The access token can actually be a JWT in this case too. The users (resource oners) can then use their access tokens to access resource servers (your other, related domains), those resource servers can verify that the access token is valid and allow or deny requests.
I use the following library when implementing OAuth 2.0 in PHP: https://oauth2.thephpleague.com/ - there's some good information in the docs too.
We have an app that uses the OAuth2 Google sign-in system and we want to store data from the users that sign in into our app on our back-end during the initial registration.
This is the way we got it set up:
Users signs in with the app using Google sign-in
We get an ID Token and send this to the server
On the server we verify this token is valid using Google library and save the info we get back from the verification
We also need the user to be able to update/insert data into the back-end when he's authenticated.
After the initial registration, how do we do this?
Do we send the ID Token from client to server each time they call the API on our back-end? In this case how to handle expired tokens?
If you want to make your API a first-class citizen in your system and have it require access tokens that are specifically issued to it instead of accepting Google authentication related tokens that were issued to your client application then you need to have an authorization server that specifically issues tokens for your API.
This authorization server can still delegate user authentication to Google, but then after verifying the user identity it will issue API specific access tokens that better satisfy your requirements, like for example, including specific scopes then used by your API to perform authorization decisions.
For a more complete description of this scenario you can check Auth0 Mobile + API architecture scenario.
In this scenario you have a mobile application ("Client") which talks to an API ("Resource Server"). The application will use OpenID Connect with the Authorization Code Grant using Proof Key for Code Exchange (PKCE) to authenticate users.
The information is Auth0 specific and you can indeed use Auth0 as an authorization server for your own API while still maintaining Google authentication support, however, most of the theory would also apply to any OAuth 2.0 compliant provider.
Disclosure: I'm an Auth0 engineer.
Im trying to use ADFS for SSO on a project. The project is on PHP and Im trying to use OAuth for this.
So what are the steps for setting up ADFS to work with OAuth2? I have no idea about ADFS and cant get any direct guide on OAuth2 settings there.
Thanks a lot.
I see that the question is quite old. But in case if other people will
get here, I have some answer which should be good for March 2019.
Let me start with a general overview.
SSO
SSO could be done with personal Google, Facebook, GitHub, Twitter, Microsoft accounts. After logging in to your account, you can log in to other systems (e.g. WordPress or any other) without password (if other systems integrated with that Identity Provider) and you give the consent (see picture below).
There are services whose main focus is to provide Identity Provider / SSO capabilities (e.g. Okta, Auth0, Google Cloud Identity, Azure Active Directory, AWS IAM).
In the corporate network, the user could be silently signed in based on the AD account without entering credentials via ADFS.
Actually, ADFS supports different authentication protocols like SAML, WS-Fed, and OAuth. But nowadays usually services implement OpenID Connect which works on top of the OAuth 2.0 protocol.
OpenID Connect flows
There is a number of authentication flows that OpenID Connect defines.
Most preferable ones are:
Authorization Code Flow with PKCE (single-page applications, native applications)
If you are using oidc-client-js, you should use response_type=code to use PKCE.
Public native app clients MUST implement the Proof Key for Code Exchange (PKCE RFC7636])
https://www.rfc-editor.org/rfc/rfc8252#section-6
Note: although PKCE so far was recommended as a mechanism to protect native apps, this advice applies to all kinds of OAuth clients, including web applications.
https://datatracker.ietf.org/doc/html/draft-ietf-oauth-security-topics-12#section-3.1.1
Implicit flow considered as Not recommended:
Clients SHOULD NOT use the implicit grant and any other response type causing the authorization server to issue an access token in the authorization response
https://datatracker.ietf.org/doc/html/draft-ietf-oauth-security-topics-09
Client credentials flow. For service-to-service communication.
How to configure ADFS?
You can find quite detailed documentation with illustrations for "Native app scenario" at Microsoft Docs: Native client with ADFS.
If you are not using ADFS, you can play with the PKCE flow setup in the playground.
JavaScript frontend
Never store client secrets in public applications like JS frontend or mobile apps. It's not applicable to PKCE flow but just in case.
If you have a modern SPA application (e.g. Angular or React), it means that frontend should have only client_id to enable end-user to obtain the JWT access_token in a browser via ADFS. You don't need any client_secret.
oidc-client-js could help you with that. Make sure that code_verifier is being sent along with a token request (it means that you are using more secured PKCE flow).
PHP backend
And on PHP side you'll need to validate the access token. You can implement the workflow on your own according to that article. But it's better to use OpenID certified library which you can find on this page (not only for PHP):
https://openid.net/developers/certified/
So, for PHP there is only one: phpOIDC.
Authentication
OAuth 2.0 can help you only with authentication (to identify the user's identity).
Most probably you would like to have different permissions for different users. And OpenID Connect implementation in ADFS provides you the ability to map AD groups to token claims. Therefore, you can decode JWT access token on the backend and implement claims-based authorization.
To use JWT claims be sure to properly validate the authenticity of the token and issuer:
Validate JWT signature using public key
Check issuer for the proper issuer (Identity Provider)
Check aud (audience) for the proper client ID
Check exp (expiration timestamp)
Check claims