Google Analytics

Google Analytics on App Engine in Java

Nick Mihailovski, Google Analytics API Team – October 2009


  1. Overview
  2. Model View Controller Design
    1. Model
    2. View
    3. Controller
  1. Retrieving Data
    1. Get the User ID
    2. Handle the Token
    3. Make Google Analytics API Requests
  2. Revoking a Token
  3. Reference

Introduction

This article describes how to make authenticated Google Data API requests using the App Engine Java SDK. It demonstrates how Analytics, Accounts, and App Engine can work together to create an application that can be shared across the Internet. You can use the example to build your own application, and even replace any of the App Engine components with ones native to your infrastructure. For example, you can use your own database instead of the App Engine Datastore. Also, while the example uses Google Analytics, the program can easily be modified to access any of the other Google Data APIs that require authorization.

To get the most out of this article:

Be familiar with...
  • The Java language.
  • How the Google Analytics Data Export API works.
  • The different authorization methods provided by the Google Accounts API.
  • How Google App Engine works.
Start out by...

Overview

This application returns the bounce rate and the number of entrances and bounces for the top 500 landing pages from a view (profile) choosen by the user. It displays all that data in an HTML table which is visualized as a Treemap.

In order to access their Google Analytics data, users have to login. This process is known as authorization. Similarly, applications—which act on behalf of the user—must also be authorized to access that data. Because a Google Account can be linked to many Google Services, applications should avoid asking users for their username and passwords directly. Instead, applications can go through an authorization using OAuth or AuthSub to process with the Google Accounts API to retrieve an authorization token for a particular user. Once the process is complete, the token can be used multiple times to make authorized requests to the Google Analytics API.

This application retrieves data from Google Analytics in 3 steps:

  1. The user must first login.
  2. The application retrieves the token by:
    a. either recalling an existing token from the App Engine Datastore.
    b. or redirecting the user to get a new token from the Google Accounts API, after which it stores the token in the App Engine Datastore.
  3. The application gets data from the Google Analytics API with an authorized token.

Note: This application supports both unregistered AuthSub and OAuth authorization methods. If you are using this example to build your own application, using unregistered AuthSub simplifies getting started by not requiring you to register your domain. Once your application is ready to launch, you can easily register your domain and switch to using oAuth. See the README on how to make this switch.

Back to Top

Model View Controller Design

This application uses the Model View Controller pattern to separate data from logic from display. In this application, the data object (Model) is separated from the logic required to retrieve that data (Controller), which is also separated from the data's presentation to the end user (View). This makes the application flexible, so you can extend this sample without having to rewrite the entire program.

This diagram describes how the MVC pattern has been applied in this application.


MVC class diagram

Model

The GoogleData object is the Model. It holds all the application data as well as the login and token status for the user.

View

The three JSPs represent the application view, and convert the data in the GoogleData object into HTML. Each JSP corresponds to one of the 3 steps above.

Controller

This application has two controllers, the MainServlet and the AuthorizationServlet.

The MainServlet is the default controller for this application. Its purpose is to set as much data as possible in the GoogleData object depending on how far the user is in the login-authorization-result steps illustrated above. The MainServlet then forwards the GoogleData object to the appropriate view for the user to continue in the process. The GoogleDataManager object handles the logic to get the GoogleData object.

The AuthorizationServlet controls the authorization processes for this application. The AuthManager object handles all the business logic of getting an authorized token to use with the Google Analytics API. If an error in the authorization process occurs, the error message is stored in a GoogleData object and forwarded onto the authorization.jsp page so the user can try to authorize again. If no errors occur, the AuthorizationServlet redirects to the MainServlet, which continues the process of getting data from the Google Analytics API.

Concept: Both the the GoogleDataManager and AuthManager are created through dependency injection by the GoogleDataManagerFactory and AuthManagerFactory respectively. This means that all the objects each manager depends on are passed (injected) through each object's constructor. This makes it easier to test the code and simpler to change the logic. For example, this application can use either AuthSub or OAuth authorization methods simply by passing a new AuthorizationService implementation through the factory methods.

Back to Top

Retrieving Data From the Google Analytics API

The application goes through the following steps to retrieve data from the Google Analytics API:

Step 1: Get The User ID

Users must first login so the application can obtain their user ID. If there is no user ID, users are sent to the login.jsp view.

The UserService instance returns a URL that allows users to either logout or login. This URL is stored in the GoogleData object and when forwarded to the login.jsp view, an HTML link is displayed for users to authenticate. Once users authenticate with their Google Account, they are redirected back to the MainServlet.

Step 2: Handle the Token

The authorization process handles the token by following a specific process:

A. Retrieve a Token From the Datastore

Once users have logged in and the MainServlet can obtain a user ID, the ID is used to retrieve an authorization token from the Datastore.

This application uses the TokenDaoJdoImpl class—which implements the TokenDao interface—to handle all interactions with the App Engine Datastore, including retrieving a token by user ID.

If a token doesn't exist, users are forwarded to the authorization.jsp.

Back to Top

B. Store a Token In The Datastore

The authorization.jsp view provides a link for users to get an authorization token. Once clicked, the link invokes the AuthorizationServlet, which redirects the user to google.com

The AuthManager class handles the logic for the authorization. Each authorization method (AuthSub and OAuth) has a distinct URL to google.com. This application supports both methods through the AuthorizationService interface, which defines the generic steps required for either authorization process. The actual authorization implementation is injected into the AuthManager through the AuthManagerFactory.

Once users are at the Google authorization page, they can grant the application access to their Google Analytics data. Once access is granted, users are then redirected back to the AuthorizationServlet with a token as a query parameter. The authorization servlet extracts this token and upgrades it to a long-lived token that doesn't expire and can be used on multiple Google Analytics API requests. The long-lived token is then stored in the App Engine Datastore along with the user ID. Application control is then returned to the MainServlet.

Step 3: Make Google Analytics API Requests

Once application control has been returned to the MainServlet, the long-lived authorization token exists in the Datastore. The token is retrieved using the user ID and set in the Google Analaytics API Java Client library AnalyticsService object.

In this application, the GoogleDataManager constructor handles all these three steps.

At this point, the application can attempt to make authorized requests to the Google Analytics API to retrieve data.

Note: Just because a token exists in the Datastore doesn't mean the token is valid. For example, users may have been revoked the token. This application checks if the token is valid by looking at the status code of the Google Analytics Export API Account Feed query. If the status code is 401, then the token is not valid, and the user is redirected to the authorization.jsp page. Alternatively, the Google Accounts API can be queried with a token to determine if the token is valid.

If the token is valid, requests to the API are made and the data is stored in a GoogleData object. The final GoogleData object with all the data is forwarded to the results page.

When the GoogleDataManager builds the GoogleData object, it calls the AnalyticsServiceWrapper to get the API data in the format it needs. The AnalyticsServiceWrapper creates API queries and uses the Google Data Java client library AnalyticsService class to make the actual requests to the Google Analytics API.

Back to Top

Revoking A Token

The results.jsp view provides the user a link to revoke a token. When clicked the link takes users to the AuthorizationServlet. The AuthorizationServlet revokes the token through the Google Accounts API and removes the token from the App Engine Datastore. Application control is returned to the MainServlet and users end up seeing the authorization.jsp page to get a new token.

This application handles the logic to revoke a token in the AuthManager revokeToken() method. This method retrieves the token using the user ID from the current user. Next, the AuthService revokes the token and finally the token is removed from the Datastore.

Back to Top

Reference

Back to Top

Authentication required

You need to be signed in with Google+ to do that.

Signing you in...

Google Developers needs your permission to do that.