Python: User authentication with OAuth2 and Angular 1

How to get together SattelizerJS and Python backend
11-Jun-2015 | Anton Alex Nesterov

When you develop web-based applications sooner or later you’ll have to deal with OAuth(2) or similar authentication flows. In this post I’ll describe how to authenticate a user with OAuth2 on a Python based Rest API.

What is OAuth/OAuth2

In abstract terms an OAuth flow allows your application to use a service on user’s behalf. It means the user should grant his authorization. Usually the algorithm would look like following: 1. User clicks some button. 2. The user is redirected to the service ( notifying the service what data is going to be accessed). 3. If user grants access (the service provides an unique access code for the application.) 4. The service redirects user back (providing access code). 5. Application uses the access code to receive access tokens 6. Application uses tokens to access some information.

Of course it is very simplified model, but usually this is pretty enough to interact with an OAuth provider to pull user’s profile or authenticate the user on your site. In other cases OAuth provider could require update access tokens using special token flow, but if you understand the basics it won’t be that hard.

How It works on frontend.

Popular OAuth2 providers like Google or Facebook deliver shared javascript libraries with ready to use functions. Getting an access code in such cases is as simple as one callback. The key point here is to get an access code which serves as an identification, and then we can use it almost from everywhere(while it’s valid).

For AngularJS there’s a module called SatellizerJS. Satellizer provides end-to-end authentication for almost every popular OAuth provider.

So our basic algoriithm became even simplier. Now we can get access code using one callback on client side, then we can use it to authorize backend.

Setting up SattelizerJS

I am assuming that you have an AngularJS frontend or have downloaded sattelizer’s example app. In order to use it you need to register an app on provider’s site. Let it be Facebook for this example. After creating a facebook app you’ll get a client id and a sectet key. Keep the secret key for backend.

After you got a client id add Sattelizer to your Angular application:

 angular.module('Application', [...,'satellizer']) // add satellizer to the modules list
        .config(function(..., $authProvider){ // use $authProvider
                url:'/auth/fb', //where post request goes
                clientId: '000000000000000'

Use ‘$auth.authenticate()’ method in a controller:

        .controller('Login', function($scope, ...., $auth){
            $scope.authenticate = function(provider) {
                    .then(function(response) {
                    .catch(function(response) {

You have to know that after user grants some permissions to your app SattelizerJS is going to make a post request to your backend. This is where you can verify user, apply authentication or do whatever you want with user’s profile.


After successful receiving of access code Sattelizer is going to send a post request to the ‘/auth/fb’ endpoint. Such request includes a JSON body with a code and clientId. Now our goal is to obtain an access token and request user’s profile from facebook. Successfull receiving of profile data would mean that the user can be authenticated. Remember that using HTTPS is a must.

Following code is taken from a working solution. It can be extended with more auth providers.

    import requests
    FACEBOOK_SECRET = 'secret'

    class AuthMixin(object):

        """ Methods for auth against third party services."""
        def request_profile(self, request, provider):

            def facebook():
                body = json.loads(request.body)
                access_token_url = ''

                graph_api_url = ''

                params = {
                    'client_id': body['clientId'],
                    'redirect_uri': body['redirectUri'],
                    'client_secret': FACEBOOK_SECRET,
                    'code': body['code']

                #1. get access token
                r = requests.get(access_token_url, params=params)
                access_token = r.json()

                #2 get users profile
                r = requests.get(graph_api_url, params=access_token)
                profile = json.loads(r.text)

                return profile

            service = locals().get(provider)
            if service: return service()

        def auth(self, request, provider, username=None):
            #1. Get remote profile; exit if none
            profile = self.request_profile(request, provider)
            if not profile: return

            #2. Get user profile related to service name
                # Your framework specific code
            #3. Login user and send cookies
                # Your framework specific code

This solution was used with Flask, Pyramid and Django Rest Framework and can work the same way with any other framework. I intentionally didn’t leave framework specific parts and replaced it with comments.

Thank you and be back.