I am building a Python web API where I want to use Azure AD as authentication backend. On certain scenarios the clients needs to authenticate through the API to authorize to certain endpoints. The client itself is not able to authenticate to AD directly, so it needs to do it through the API using raw credentials (username, password). The API will then authenticate the user and receive the AD token and give it to the user.
So in short I am looking for a way to programmatically authenticate a user using username/password and receive the token using Python.
You can find the different authentication flows relevant for an application type and topology in this Azure AD article. The article links to the protocol overview for the authentication flows if you choose to implement.
There is also the ADAL Python auth library for Azure AD which you can use to do these flows.
Based on your scenario, you have a few options. If your client app can authenticate directly with Azure AD, you can take a look at the client credentials flow sample. If your application needs a user to authenticate and can have the user authenticate interactively, you can check out this auth code flow sample. Finally, if you must use the user's credentials to authenticate programmatically(without user interaction) in the app, you can refer to the resource owner password flow, but this is not encouraged as mentioned in the other answer.
What you are describing is the OAuth 2 Resource Owner Password Credentials Grant flow.
Note: using this one is in general a really bad idea and some other flow should be considered instead.
What you are doing here, is sending POST request containing user credentials in clear text directly to the authentication endpoint. Thus bypassing all possible added security that might be put in place.
Also, it will not work when
MFA is enabled for the user
User is federated or a MS account
This flow has no way to handle expired passwords
Consider some other authorization flow if possible, you got e.g.
Authorization code flow
Implicit grant flow
Client credentials flow
Device authentication flow
See this link to help you select which flow to use.
Related
We have a small website with API connected using AJAX.
We do not ask for usernames and passwords or any authentication like firebase auth.
So it's like open service and we want to avoid the service to be misused.
OAuth 2 is really effective when we ask for credentials to the user.
Can you suggest the security best practice and how it can be implemented in this context using python?
Thanks
Use a firewall
Allow for third-party identity providers if possible
Separate the concept of user identity and user account
I have a website with frontend in AngularJS and backend in Python.
Currently we are presenting the user with a simple webform to fetch credentials.
The credentials from the form are sent to the Python backend(flask webservice)(this is a basic auth mechanism).
Now we would like to enable Single Sign on (SSO) on the website.Our identity provider is Pingone or Ping Federate.
I am starting from scratch here..with no prior knowledge of SAML or SSO.
I would like to know which path to take?
Which libraries to use and more importantly,how to use them?
At this point in time I am not sure how exactly SAML identifies a user and then authenticates him/her.
The basic exchange of SAML starts with a user asking for a resources (page, SPA app) on your Python server. The server determines if the user is already authenticated (has a session, JWT token, etc), and if not, creates a SAML request token to be sent via a redirect to the Identity Provider (use a library for this).
The identity provider verifies the SAML request token via digital signature. Once the token is verified, the user is asked to log in (if they are not already authenticated there). Once the user is authenticated, the identity provider creates a SAML request token which is presented back at your server via a redirect.
Upon receipt of the SAML request token, your server validates the token via digital signature, and you treat the user as logged in (again, use a library for this part). The token will minimally identify the user, but can contain authorizations and additional info. At this point your user is authenticated and you would create a session on your server or you create a JWT token to identify your user from within your angular app to the Python backend.
Creating the SAML request token and processing in the resultant SAML response token is not trivial. As suggested above, use a library, preferably one that has been through the the test of time. I'm not a Python dev, but I found this with some googling: onelogin/python-saml.
Wikipedia has a nice sequence diagram to demonstrate this and of course you can peruse the many docs on the Oasis SAML docs website.
Good luck with the implementation. I've done it a couple times in Java.
Hi I have our website running on appengine with flask as backend framework and we have built our authentication and session management using libraries Flask-OAuth, Flask-Login.
But now I have a requirement to use firebase for authentication.
I am able create sample applications following firebase tutorials but I do no how to integrate with existing application.
In Firenotes samples provided by firebase team they are using two separate services frontend and backend.
I thought of using firebase code in login.html page and once client authenticated pass the info to /profile url -> log the user_id in database and login-user using Flask-Login.
I am not sure whether the above flow is correct and I am not to ensure that it is correct one without any problems in future.
Please help with any ideas as I need to implement it very soon!!
Flask-Login uses session based authentication. Clients login using an authentication scheme. Since you are using Flask-OAuth, it's the oauth flow. If the user successfully authenticates, Flask-Login sends a response during the token exchange step setting an HTTP only cookie (meaning javascript can't access it) with a token unique to the user session. The client then authenticates future requests for the duration of the session with that token. The server can invalidate the session at any time, forcing the client to log in again.
Meanwhile, firebase authentication is JSON Web Token (JWT) authentication scheme. After completing the login flow, the firebase API retrieves a JWT from google's application servers.
To authenticate requests, you need to transmit that JWT on EVERY request. Your server MUST also validate the JWT to ensure that it is both valid and unexpired.
You'll note that the manner by which the JWT arrives at the server is unspecified by the firebase SDK and libraries. I recommend using a Authentication: JWT <google's jwt> header.
One way to resolve your question would be to use the JWT to complete the initial login flow, and then rely on session based auth from there. You'd set up a login endpoint that expects and validates a JWT, and responds with the set cookie header. From that point forward you continue using your flask-login provided session based auth.
Google actually has an example of this in their documentation: https://firebase.google.com/docs/auth/admin/manage-cookies
The documentation google + domains api to create a post using the 'service' object, obtained here by this method. But in my project to authenticate via google and other sites I use the python social auth
and after authorization I have a ready access token.
The problem lies in the fact that I need a service object to work with api, but I can not figure out how to get it already having access token. Please help me and sorry for my english.
For the domains API, you typically will implement using a service account authorization flow - which is not retrieved in the same way as a user OAuth flow. This is because service accounts can be authorized for services that users typically should not be authorized for (e.g. retrieving domain-wide lists of user names).
The service account credentials, used to authorize your application, are created using the Google Developer Console and then are downloaded as a JSON or p12 file that is used to authenticate your Python client, as shown in this example.
That said, you still can do some actions with that access token which is why the auth flow you're seeing is doing this. Service credentials are how you should be authorizing for domains-related management features which may explain the behavior you're seeing.
I using the Python SDK (http://github.com/facebook/python-sdk/) with Google app engine.
I can post message on user wall with the self.graph.put_object function while the user is online.
How do post a message to user wall directly from the server even the user is offline?
I am assuming you know how to kick the work off and just need the calls to authenticate for the user.
Your facebook app must request extended permissions from the user.
http://developers.facebook.com/docs/authentication/permissions
offline_access
Enables your application to perform
authorized requests on behalf of the
user at any time. By default, most
access tokens expire after a short
time period to ensure applications
only make requests on behalf of the
user when the are actively using the
application. This permission makes the
access token returned by our OAuth
endpoint long-lived. NOTE: If you have
requested the publish_stream
permission, you can publish content to
a user's feed at any time, without
requiring offline_access.
Once you have done this the oauth_access_token returned from Facebook is an offline_access token and can be used anytime until the user revokes your app access or extended permission.