Google Analytics APIでページ別・日別のPV・AdSense収益などを取得

Googleアナリティクス Reporting APIを使うとページ別や日別のPV(アクセス数)やユーザー数、直帰率、離脱率、平均ページ滞在時間、AdSense収益・クリック数などが取得できます。 GoogleアナリティクスのページからExcelやCSVなどの形式でエクスポートすることもできるが、最大で5000行ずつという制限があります。大量のデータをまとめてダウンロードする場合はAPIを使うと便利です。 ここではPythonを使った例を紹介します。

公式のドキュメント・チュートリアル プロジェクト・アカウントなどの設定 Pythonのクライアントライブラリのインストール 公式のサンプルコードの実行 Googleアナリティクス Reporting APIの基本的な使い方 基本的な流れ dimensionsとmetrics ページネーション データをCSVで保存するサンプルコード

Search Console APIについては

公式のドキュメント・チュートリアル

Google公式のドキュメントおよびチュートリアルが非常に充実しています。日本語。

概要 | アナリティクス Reporting API v4 | Google Developers

まずはこのページに従ってサンプルを実行するといい。 Pythonのサンプルとしては、

サービス アプリケーション インストール済みアプリケーション

の2つがあるが、自サイトのデータをダウンロードする場合は「サービス アプリケーション」のほうが簡単だと思います。

はじめてのアナリティクス Reporting API v4: サービス アカウント向け Python クイックスタート | アナリティクス Reporting API v4 | Google Developers

プロジェクト・アカウントなどの設定

プロジェクトやアカウントなどの設定は以下のような流れになります。

Google API Consoleでプロジェクトを作成 既存のプロジェクトを使うことも可能 セットアップツールでReporting APIをプロジェクトに登録 そのままウィザードに従って認証情報を作成することもできるが、一旦キャンセルしてからサービスアカウントを作成したほうが分かりやすい サービスアカウントを作成 サービスアカウントのページからサービスアカウントを作成 認証情報を含むJSONファイルがダウンロードされる Google アナリティクス アカウントにサービス アカウントを追加 Googleアナリティクスの管理から対象のビューを開き、ユーザー管理者の+ボタンから新しいユーザーを追加 サービスアカウントのメールアドレスを追加するPythonのクライアントライブラリのインストール Google謹製のクライアントライブラリをインストールします。インストールされている場合も--upgradeで最新版にアップデートしておく。

$ pip install --upgrade google-api-python-client

公式のサンプルコードの実行

公式のサンプルコードで動作確認します。

はじめてのアナリティクス Reporting API v4: サービス アカウント向け Python クイックスタート | アナリティクス Reporting API v4 | Google Developers

以下の修正が必要。

print文をprint()関数に変更 printが文になっているので、Python3で実行する場合はprint xxxxxをprint(xxxxx)に変更 <REPLACE_WITH_JSON_FILE>をJSONファイルへのパスに変更 サービスアカウント作成時にダウンロードされたJSONファイルへのパスを指定する JSONファイルをスクリプトファイルと同じディレクトリに置いておく場合は<REPLACE_WITH_JSON_FILE>をファイル名(xxxxx.json)に置き換えればOK <REPLACE_WITH_VIEW_ID>をビューIDに変更 Googleアナリティクスの管理から対象のビューを開きビューの設定で確認できるエラーなく実行できれば諸々の設定は問題ありません。

Googleアナリティクス Reporting APIの基本的な使い方

基本的な流れ

公式のサンプルコードを見ると分かる通り、Googleのクライアントライブラリを使う場合、

ServiceAccountCredentials.from_json_keyfile_name()でJSONファイルからCredentials(資格情報)を抽出 Credentialsをもとにapiclient.discovery.build()でサービスオブジェクトを作成 サービスオブジェクトからreports().batchGet().execute()でデータ取得

という非常にシンプルな流れになります。 リクエストの設定はbatchGet()の引数bodyに辞書(dict型オブジェクト)で指定します。 リクエストおよびレスポンスの詳細は以下の公式ドキュメントを参照。

レポートの作成 | アナリティクス Reporting API v4 | Google Developers メソッド: reports.batchGet | アナリティクス Reporting API v4 | Google Developers

レスポンスの値はすべて文字列なので気をつけてください。

dimensionsとmetrics

リクエスト設定のなかで重要なのがdimensionsとmetrics。これらを指定することで所望のデータを取得できます。

dimensions

ページURLや日付、地名など 最大7つまで

metrics

PVやユーザー数、平均ページ滞在時間、AdSense収益・クリック数など 最大10つまでdimensionsとmetricsの種類は以下のページから検索できます。

Dimensions & Metrics Explorer | アナリティクス Reporting API v4 | Google Developers

複数指定する場合は、以下のように辞書のリストを指定します。

'dimensions': [{'name': 'ga:pagePath'}, {'name': 'ga:date'}],
'metrics': [{'expression': 'ga:pageviews'}, {'expression': 'ga:avgTimeOnPage'}]

ページネーション

デフォルトでは1000行のデータが取得できます。 リクエストでpageSizeを指定するとその行数分のデータが一気に取得できます。リファレンスには「最大10,000 行」と書いてあったが、それ以上の値(例えば100000)を指定してみると20000行程度のデータが取得できた。仕様がいまいちよくわからない。 pageSizeを超えたデータが存在する場合、レスポンスのdataにnextPageTokenが指定され、その値をリクエストのpageTokenに指定すると続きのデータが取得できます。 辞書のget()メソッドを使うと、nextPageTokenがある場合にはその値、ない場合にはNoneを取得できます。

response['reports'][0]['data'].get('nextPageToken')

サンプリング データ数が多いと自動的にサンプリングされてデータが省略される場合があります。

レポートの作成: サンプリング | アナリティクス Reporting API v4 | Google Developers

50万セッションがしきい値のようで、それ以上だとデータが間引かれる。リクエストの設定samplingLevelで精度を指定できるが、必ずすべてのデータを取得できるわけではない。サンプリングされるのを避けるためには適当に期間を区切ってリクエストする必要があります。 サンプリングされた場合はレスポンスのdataにsamplesReadCountsとsamplingSpaceSizesが含まれる。サンプリングされていない場合はそれらのキーがないので、そこを確認すればサンプリングされているかどうかを判別できます。 辞書のget()メソッドを使うと、samplesReadCountsなどがある場合にはその値、ない場合にはNoneを取得できます。

response['reports'][0]['data'].get('samplesReadCounts')

データをCSVで保存するサンプルコード

pandasを使ってデータをCSVファイルで保存するサンプルコードを示す。 上述のように、厳密にはページネーションやサンプリングを考慮する必要があるが、以下は期間とdimensionsとmetricsなどを指定してレスポンスをpandas.DataFrameに変換、CSVとして保存するシンプルなもの。

import pandas as pd

from apiclient.discovery import build
from oauth2client.service_account import ServiceAccountCredentials

SCOPES = ['https://www.googleapis.com/auth/analytics.readonly']
KEY_FILE_LOCATION = '<REPLACE_WITH_JSON_FILE>'
VIEW_ID = '<REPLACE_WITH_VIEW_ID>'

credentials = ServiceAccountCredentials.from_json_keyfile_name(KEY_FILE_LOCATION, SCOPES)
analytics = build('analyticsreporting', 'v4', credentials=credentials)

m_list = ['users', 'sessions', 'pageviews', 'bounceRate', 'exitRate', 'avgTimeOnPage',
          'adsenseRevenue', 'adsenseAdsClicks', 'adsenseViewableImpressionPercent']
d_list = ['pagePath', 'date']

metrics = [{'expression': 'ga:' + m} for m in m_list]
dimensions = [{'name': 'ga:' + d} for d in d_list]

start_date = '2018-07-01'
end_date = '2018-07-31'
page_size = 100000
sampling_level = 'LARGE'

body = {
    'reportRequests': [
        {
            'viewId': VIEW_ID,
            'dateRanges': [{'startDate': start_date, 'endDate': end_date}],
            'metrics': metrics,
            'dimensions': dimensions,
            'pageSize': page_size,
            'samplingLevel': sampling_level
        }
    ]
}

response = analytics.reports().batchGet(body=body).execute()

df = pd.io.json.json_normalize(response['reports'][0]['data']['rows'])

for i, d in enumerate(d_list):
    df[d] = df['dimensions'].apply(lambda x: x[i])

for i, m in enumerate(m_list):
    df[m] = df['metrics'].apply(lambda x: x[0]['values'][i])

df.drop(columns=['dimensions', 'metrics'], inplace=True)

df.to_csv('{}_{}.csv'.format(start_date, end_date), index=False)

出力行が格納されているresponse['reports'][0]['data']['rows']をpd.io.json.json_normalize()でpandas.DataFrameに変換しています。

レスポンスのrowsは以下のような辞書になっています。d0, m0は結果の値。

{'dimensions': [d0, d1, d2...],
 'metrics': [{'values': [m0, m1, m2...]}]}

これをpd.io.json.json_normalize()で変換すると、dimensionsとmetricsの二つの列のpandas.DataFrameとなります。 dimensions列の要素はリスト[d0, d1, d2...]、metrics列の要素は[{'values': [m0, m1, m2...]}]となるため、apply()メソッドでそれぞれの結果を新たな列として取り出し、そのあとでdimensionsとmetricsの二つの列を削除しています。

上述のように結果の値はすべて文字列。pandas.DataFrameをそのまま処理する場合はastype()でデータ型を変更する必要があります。

to_csv()でCSVファイルとして保存したあとでread_csv()で読み込むと数値として読み込まれる。

dimensionsに日付dateを指定したときの結果は20180101のようなYYYYMMDD形式になります。これをpd.to_datetime()で変換する場合は引数formatを指定する必要があるので気をつけてください。

df['date'] = pd.to_datetime(df['date'], format='%Y%m%d')

複数ディメンションを指定した場合はgroupby()を使うと各ディメンションごとに集約して合計や平均が算出できて便利です。

なお、サンプルコードではAdSenseの収益adsenseRevenueやクリック数adsenseAdsClicksなどを取得するようにしているが、これはAdSenseとAnalyticsを連携しておく必要があります。 AdSenseとAnalyticsの連携設定はGoogleアナリティクスのサイトの管理、プロパティのAdSenseのリンク設定から行う。Googleアナリティクスのサイトの行動 → サイト運営者 → サイト運営者のページでサイト運営者の収益などの項目が表示されていれば連携できています。

Last Updated: 6/26/2019, 10:34:03 PM