Simplifying "Login With Twitter" using Python and Flask.
Tags: python, webdev, security
Published: 2020-04-24 20:39:16



![](https://cdn-images-1.medium.com/max/2560/1*vvoZyeIdTr31jHsv8s3WQg.png)

Recently while working on a project I came across an issue with trying to implement Twitter Integrations into my Flask app. All of the guides on Google were breaking or just didn’t fit in with my application. I wanted a simple way to interface with Twitter’s OAuth1 API but everything was giving me errors.

**NOTE: This guide assumes you have setup a Twitter Application and have your consumer keys and callback URLs set. If you do not know how to do this please refer to [this guide.](https://docs.inboundnow.com/guide/create-twitter-application/)**

Finally, I decided to try something myself, I looked into requests_oauthlib and realized it would be much easier to just use their Client class to generate signatures and implement with my Flask app. I couldn’t find any examples that were easy to understand or read as far as the code went so I wanted to share how I ended up implementing this into my application.

First the libraries I used in my implementation. flask is the library I’m using in order to create my main webserver and viewable routes. We don’t use much apart from the redirect function from it in this. flask_restful is the REST library I’m using in order to easily create a JSON based API. The endpoints we create in this are RESTful API Endpoints that inherit the Resource class from flask_restful. requests_oauthlib is the OAuth library I use in order to generate the OAuth headers to authenticate with Twitter’s API. We will also be using the requests library in order to make requests server side to Twitter.

First you need to setup a flask app. Lets make a folder called app first:

    mkdir ./app
    cd ./app

Now from within the app/ directory we will create a file called __init__.py :

    # Let's import the Flask class from the flask library
    from flask import Flask

    # Let's import the Api class from the flask_restful library
    from flask_restful import Api

    # Let's import our OAuth library to setup
    from requests_oauthlib.oauth1_auth import Client

    # Create A Config To Store Values
    config = {
        'twitter_consumer_key': 'ENTER TWITTER CONSUMER KEY',
        'twitter_consumer_secret': 'ENTER TWITTER CONSUMER SECRET'
    }

    # Initialize Our Flask App
    app = Flask(__name__)

    # Initialize Our RESTful API
    api = Api(app)

    # Initialize Our OAuth Client
    oauth = Client(config['twitter_consumer_key'], client_secret=config['twitter_consumer_secret'])

This is all we need to do for now in the __init__.py file. Next we will start to create our endpoints for Twitter. This assumes you have setup a Twitter Application and you have your consumer keys.

Next we create our endpoint. For this we can just create a file called twitter.py or really whatever you’d like. Next we add:

    # Import our functions and Resource class from flask_restful
    from flask_restful import Resource, reqparse

    # Import our functions from Flask
    from flask import redirect

    # Import our oauth object from our app
    from app import oauth

    # Import requests in order to make server sided requests
    import requests

    # We have to create our initial endpoint to login with twitter
    class TwitterAuthenticate(Resource):
        # Here we are making it so this endpoint accepts GET requests
        def get(self):
            # We must generate our signed OAuth Headers
            uri, headers, body = oauth.sign('https://twitter.com/oauth/request_token')
            # We need to make a request to twitter with the OAuth parameters we just created
            res = requests.get(uri, headers=headers, data=body)
            # This returns a string with OAuth variables we need to parse
            res_split = res.text.split('&') # Splitting between the two params sent back
            oauth_token = res_split[0].split('=')[1] # Pulling our APPS OAuth token from the response.
            # Now we have to redirect to the login URL using our OAuth Token
            return redirect('https://api.twitter.com/oauth/authenticate?oauth_token=' + oauth_token, 302)

This is our authentication endpoint, when somebody attempts to hit this it will redirect them to the Twitter login page which will then send them to our Callback URL which you should have setup in your Twitter App’s dashboard.

Next we need to add the logic for handling our callback URL. We can add this to the same file as the TwitterAuthenticate class.

    # We need to create a parser for that callback URL
    def callback_parser():
        parser = reqparse.RequestParser()
        parser.add_argument('oauth_token')
        parser.add_argument('oauth_verifier')
        return parser

    # Now we setup the Resource for the callback
    class TwitterCallback(Resource):
        def get(self):
            parser = callback_parser()
            args = parser.parse_args() # Parse our args into a dict
            # We need to make a request to twitter with this callback OAuth token
            res = requests.post('https://api.twitter.com/oauth/access_token?oauth_token=' + args['oauth_token'] + '&oauth_verifier=' + args['oauth_verfier']])
            res_split = res.text.split('&')
            # Now we need to parse our oauth token and secret from the response
            oauth_token = res_split[0].split('=')[1]
            oauth_secret = res_split[1].split('=')[1]
            userid = res_split[2].split('=')[1]
            username = res_split[3].split('=')[1]
            # We now have access to the oauth token, oauth secret, userID, and username of the person who logged in. 
            # .... Do more code here
            # ....
            return redirect('http://somwhere.com", 302)

This TwitterCallback class will parse and handle the OAuth tokens in order to access the user’s account info. You can do whatever you want with this info whether that be storing it into a DB User Model or making requests with Tweepy!

The last step is adding these endpoints to your __init__.py file we created at the beginning! At the bottom of the file add this:

    from app.twitter import TwitterAuthenticate, TwitterCallback

    api.add_resource(TwitterAuthenticate, '/authenticate/twitter')
    api.add_resource(TwitterCallback, '/callback/twitter') # This MUST match your Callback URL you set in the Twitter App Dashboard!!!

Our final twitter.py should look like this:

    from flask_restful import Resource, reqparse
    from flask import redirect
    from app import oauth
    import requests
    class TwitterAuthenticate(Resource):
        def get(self):
            uri, headers, body = oauth.sign('[https://twitter.com/oauth/request_token'](https://twitter.com/oauth/request_token'))
            res = requests.get(uri, headers=headers, data=body)
            res_split = res.text.split('&') # Splitting between the two params sent back
            oauth_token = res_split[0].split('=')[1] # Pulling our APPS OAuth token from the response.
            return redirect('[https://api.twitter.com/oauth/authenticate?oauth_token='](https://api.twitter.com/oauth/authenticate?oauth_token=') + oauth_token, 302)

    def callback_parser():
        parser = reqparse.RequestParser()
        parser.add_argument('oauth_token')
        parser.add_argument('oauth_verifier')
        return parser

    class TwitterCallback(Resource):
        def get(self):
            parser = callback_parser()
            args = parser.parse_args() # Parse our args into a dict
            res = requests.post('[https://api.twitter.com/oauth/access_token?oauth_token='](https://api.twitter.com/oauth/access_token?oauth_token=') + args['oauth_token'] + '&oauth_verifier=' + args['oauth_verfier']])
            res_split = res.text.split('&')
            oauth_token = res_split[0].split('=')[1]
            oauth_secret = res_split[1].split('=')[1]
            userid = res_split[2].split('=')[1]
            username = res_split[3].split('=')[1]
            # ... Do Code Here
            return redirect('[http://somwhere.com](http://somwhere.com)", 302)

Our final __init__.py should look something like:

    from flask import Flask
    from flask_restful import Api
    from requests_oauthlib.oauth1_auth import Client

    config = {
        'twitter_consumer_key': 'ENTER TWITTER CONSUMER KEY',
        'twitter_consumer_secret': 'ENTER TWITTER CONSUMER SECRET'
    }

    app = Flask(__name__)
    api = Api(app)
    oauth = Client(config['twitter_consumer_key'], client_secret=config['twitter_consumer_secret'])

    from app.twitter import TwitterAuthenticate, TwitterCallback

    api.add_resource(TwitterAuthenticate, '/authenticate/twitter')
    api.add_resource(TwitterCallback, '/callback/twitter')

I hope you find this guide helpful and have a fun time integrating with Twitter’s User API!

You can find a GitHub Gist [here with the files shown above.](https://gist.github.com/M4cs/0ea99c84f181876bfc81caecbe39e7f4)

Follow me on [Twitter ](https://twitter.com/maxbridgland)and [GitHub](https://github.com/M4cs) for more interesting programming stuff!