Connecting to Google Analytics (UA) API with Python

Connecting to Google Analytics (UA) API with Python

As long as you have created your Google API Credentials, you are ready to begin programmatically pulling data from your views in Google Analytics. In this article, we’re going to walk through authorizing your script to prepare for pulling reports.

Requirements

pip install --upgrade google-api-python-client google-auth-httplib2 google-auth-oauthlib

Before We Start Coding

Before we get into the script, let’s do a little housekeeping. At the end of the article where we create the Google credentials, I mentioned you should download the OAuth JSON file. In our script, we are going to be opening this file to authorize it. I recommend renaming it to credentials.json, since that’s what we’re going to be calling in our script. I also recommend moving it to the same folder that you are writing this script in. Your folder structure might look something like this:

  • ga_api
    • credentials.json
    • ga_api.py

Authorizing Google Analytics API in Python Script

I’ve mentioned this in other Google API articles, but I’ll mention it again here. Google has many ways to connect to their various APIs. I like to build to Google’s APIs using the references I found in the Google Sheets API documentation because it seems like a very recent and clean implementation. We’ll be updating this slightly to work for Google Analytics instead of Google Sheets.

We’ll start by importing the modules we’ll be using.

# Import Modules
import os.path
from googleapiclient.discovery import build
from google_auth_oauthlib.flow import InstalledAppFlow
from google.auth.transport.requests import Request
from google.oauth2.credentials import Credentials

Define Authorization Function

If you’ve followed my guides before, this function will look very familiar. For the newcomers, I’m still going to walk through the function so you have a better understanding of what’s happening just under the hood.

def ga_auth(scopes):
    creds = None
    # The file token.json stores the user's access and refresh tokens, and is
    # created automatically when the authorization flow completes for the first
    # time.
    if os.path.exists('token.json'):
        creds = Credentials.from_authorized_user_file('token.json', scopes)
    # If there are no (valid) credentials available, let the user log in.
    if not creds or not creds.valid:
        if creds and creds.expired and creds.refresh_token:
            creds.refresh(Request())
        else:
            flow = InstalledAppFlow.from_client_secrets_file(
                'credentials.json', scopes)
            creds = flow.run_local_server(port=0)
        # Save the credentials for the next run
        with open('token.json', 'w') as token:
            token.write(creds.to_json())

    service = build('analyticsreporting', 'v4', credentials=creds)

    return service

First we set the variable creds to None. This is a common method in Python within functions, especially when you’ll be using a variable for conditionals.

Next we check to see if your folder has a token.json file in it. If this is your first time authorizing, you don’t. If it’s not, we’re setting the creds variable to the credentials we’ve previously gotten.

I’m going to jump around for a second because the next line we check if the credentials don’t exist or if they aren’t valid. If they exist and are valid, we completely skip this block.

If the credentials do exist but they are expired and have a refresh token, we are requesting a refresh.

If they don’t exist and don’t have a refresh token (which is the path our code will take the first time we run it), we open credentials.json and ask for authorization. When you run this, what will happen at this point is the script will open a link in your browser and take you to the OAuth Consent Screen that you previously set up. Once you authorize that the app (script) can connect using your credentials.json file and we set creds to the authorization token we get back. For future use, we save the creds into token.json.

One important note about token.json. You can use this same token for all the other Google API scripts we’ll be writing, if and only if the scopes don’t change. If the scopes are different, we will need to delete token.json and re-run the function. This is very important, especially if you followed my Google Search Console Authorization guide because we only set our scopes to the Google Search Console scopes.

Finally, in our function, we build the service we’ll be using for our API calls. In this case, it will be analyticsreporting and we’re using v4.

Set Scopes and Obtain Authorization

Now that the function is written, we can put it to use.

The first thing we need to do is set our scopes. Since we are only covering Google Analytics in this article, we’re only going to use the GA scopes. I almost always run with at least two scopes in my list because I’m often using the same token.json file in a single script to pull from two different sources (like Google Analytics and Google Search Console). Just remember that if you change your scopes, you’ll need to delete token.json or you’ll get an error.

You can find the available scopes in each of the API’s documentations. Here are the Google Analytics scopes.

scopes = ['https://www.googleapis.com/auth/analytics.readonly']

Easy peasy. You’ll notice I’m using the .readonly scopes in this. I personally don’t like to try to manipulate anything in Google Analytics using the API. I use it solely for pulling down reports and prefer to use the UI for management. You can choose whatever you’d like.

With the scopes set, we are ready to call the function to build our service. Set the service to a variable because we’ll need that service object for future report requests (beats having to authorize every time).

service = ga_auth(scopes)

Now you can run the code!

Please visit this URL to authorize this application: https://accounts.google.com/o/oauth2/auth?THESEPARAMETERSAREGIVENTOYOU

Your browser should automatically open the link that the script creates. However, if it doesn’t, you can copy and paste the output URL. This will take you to the OAuth consent screen you set up. First, select the account you want to use (which should be the one you set the credentials up for), then you’ll see this screen.

Google Analytics OAuth Consent Screen

Select Allow and you’re off to the races!

Now that you have authenticated your script, you are ready to pull your first report from the Google Analytics API!

Full Code

# Import Modules
import os.path
from googleapiclient.discovery import build
from google_auth_oauthlib.flow import InstalledAppFlow
from google.auth.transport.requests import Request
from google.oauth2.credentials import Credentials



# Define function to get authorization
def ga_auth(scopes):
    creds = None
    # The file token.json stores the user's access and refresh tokens, and is
    # created automatically when the authorization flow completes for the first
    # time.
    if os.path.exists('token.json'):
        creds = Credentials.from_authorized_user_file('token.json', scopes)
    # If there are no (valid) credentials available, let the user log in.
    if not creds or not creds.valid:
        if creds and creds.expired and creds.refresh_token:
            creds.refresh(Request())
        else:
            flow = InstalledAppFlow.from_client_secrets_file(
                'credentials.json', scopes)
            creds = flow.run_local_server(port=0)
        # Save the credentials for the next run
        with open('token.json', 'w') as token:
            token.write(creds.to_json())

    service = build('analyticsreporting', 'v4', credentials=creds)

    return service


# Set Scopes
scopes = ['https://www.googleapis.com/auth/analytics.readonly']

# Authenticate & Build Service
analytics = ga_auth(scopes)

6 thoughts on “Connecting to Google Analytics (UA) API with Python

  1. Hello, Eric, the first run succeeded and the authorization succeeded, but token.json was not generated, so I had to re-authorize the second run. Do you have any better suggestions

    1. Make sure in subsequent runs you’re using the same working directory that token.json was saved into. The function is a word-for-word copy of Google’s function in their support docs.

  2. Hi Eric.
    Thanks for these detailed articles on Analytics integration.
    Do you have one regarding Campaign manager reports integration? For example, I would like to automate Campaign Manager reports that I often have to run manually daily by using a GCP cloud function which will create the report, download and append the data from the report to an existing table to facilitate continuous flow of data and instead of creation of new tables each time a new report is generated.
    Thank you

    1. You’re welcome! Sorry, no, I don’t have any experience with Campaign Manager or its API. Google has a guide to get you started on this with Python, though. The authorization process should be the same as my build service script except for line 30 in the full code above. And, of course, just make sure you update your scopes to include the Campaign Manager. After that, you can follow along here: https://developers.google.com/doubleclick-advertisers/getting_started. Happy coding!

  3. Hi, I am trying to use your code from my desktop using Streamlit and it’s giving me fits. Have you tried that? The redirect URI changes and I can’t seem to sort how to get it to authenticate.

    1. It’s been awhile since I’ve played with Streamlit, but if you’re running it locally, I’m surprised you’re running into problems. First, make sure you’re using OAuth credentials and not a service account. This is a common mistake. If you are using OAuth, my little trick is to run the authentication script separately to generate a token.json, then copy credentials.json and token.json into the directory where your Streamlit script is located. This effectively bypasses having to re-authenticate using the browser because token.json exists and should refresh from that.

Leave a Reply

Your email address will not be published. Required fields are marked *

This site is protected by reCAPTCHA and the Google Privacy Policy and Terms of Service apply.

Related Posts

Begin typing your search term above and press enter to search. Press ESC to cancel.

Back To Top