大きなレポートのリクエストの生成には時間がかかることがあるため、Search Ads 360 API には、レポートの要求とダウンロードを非同期で行う方法があります。こちらの レポートに表示するデータを指定した最初のリクエストを送信し、 その後、検索広告 360 でレポートの生成が終了するまで追加のポーリング リクエストを送信できます。 レポートのサイズに応じて、データは複数のファイルに分割されます。完了後 レポートが生成されたら、各レポート ファイルをダウンロードするためのリクエストを送信します。もし 少量のデータをリクエストする場合は、1 つの同期イベント インスタンスを 1 つだけ リクエストできます。
非同期リクエストを実行するには
Reports.request()
に電話 レポートに含めるデータのタイプを指定します。エクスポートするデータのタイプについては、レポートのタイプをご覧ください。 リクエストできます。検索広告 360 はリクエストを検証し、レポート ID(この固有の ID)を返します。 リクエストできます。
Reports.get()
に電話 レポート ID に置き換えます。検索広告 360 からのレスポンスは次のとおりです。
- レポートをダウンロードできるかどうかを示します。
- レポートの準備が整っている場合は、レポートをダウンロードするための URL(複数可)。
Reports.getFile()
に電話 エンコードしたレポート ファイルをダウンロードするか、URL から直接ダウンロードできます。検索広告 360 は、UTF-8 エンコード ファイルでレポートを返します。
レポートの準備が整っているかどうかを確認するために、どれくらいの頻度でレポートをポーリングする必要がありますか?
検索広告 360 がレポートを生成するのに必要な時間は、主に 表示されます。レポート ステータスのポーリングを 1 分に 1 回試行し、 平均レポート リクエストにかかる時間が大幅に長く、または少ない場合は、頻度を調整します。 終了します。
非同期レポートを複数のファイルに分割する
検索広告 360 では、非同期リクエストに応じて大きなレポートが自動的に
できます。Reports.request.maxRowsPerFile
を使用する
プロパティを使用して、最大ファイルサイズを指定します。結果として得られる各レポート ファイルには、
レポートの行は最大 maxRowsPerFile
行です(ヘッダーはカウントされません)。別の URL
がファイルごとに生成され、 Reports.get()
に応答して返されます。詳細情報
レポート ファイルのダウンロードについて詳しくは、
レポートをご覧ください。
CSV レポートの場合、ヘッダーは各ファイルで繰り返されます。
非同期の例
以下に、非同期手法を使用したリクエストとレスポンスのサンプルを示します。
JSON
POST https://www.googleapis.com/doubleclicksearch/v2/reports Authorization: Bearer your OAuth 2.0 access token Content-type: application/json { "reportScope": { "agencyId": "12300000000000456", // Replace with your ID "advertiserId": "21700000000011523", // Replace with your ID }, "reportType": "keyword", // This report covers all keywords in the // advertiser specified in reportScope. "columns": [ { "columnName": "campaignId" }, // Here are some attribute columns available for keyword { "columnName": "keywordText" }, // reports. { "columnName": "keywordLandingPage" }, { "columnName": "date" }, // The date column segments the report by individual days. { "columnName": "dfaRevenue" }, // Here are some metric columns available for keyword { // reports "columnName": "visits", "startDate": "2013-01-01", // Each metric column can optionally specify its own start "endDate": "2013-01-31", // and end date; by default the report timeRange is used. "headerText": "visits last month" // Every column can optionally specify a headerText, which // changes the name of the column in the report. } ], "timeRange" : { "startDate" : "2012-05-01", // Dates are inclusive and specified in YYYY-MM-DD format. "endDate" : "2012-05-02" // Alternatively, try the "changedMetricsSinceTimestamp" or "changedAttributesSinceTimestamp" // options. See Incremental reports. }, "filters": [ { "column" : { "columnName": "keywordLandingPage" }, "operator" : "startsWith", "values" : [ // With this filter, only keywords with landing pages "http://www.foo.com", // rooted at www.foo.com or www.bar.com are returned. "http://www.bar.com" // See Filtered reports. ] } ], "downloadFormat": "csv", "maxRowsPerFile": 6000000, // Required. See Splitting reports into multiple files. "statisticsCurrency": "agency", // Required. See Currency for statistics. "verifySingleTimeZone": false, // Optional. Defaults to false. See Time zone. "includeRemovedEntities": false // Optional. Defaults to false. }
Java
/** * Creates a campaign report request, submits the report, and returns the report ID. */ private static String createReport(Doubleclicksearch service) throws IOException { try { return service.reports().request(createSampleRequest()).execute().getId(); } catch (GoogleJsonResponseException e) { System.err.println("Report request was rejected."); for (ErrorInfo error : e.getDetails().getErrors()) { System.err.println(error.getMessage()); } System.exit(e.getStatusCode()); return null; // Unreachable code. } } /** * Creates a simple static request that lists the ID and name of all * campaigns under agency 12300000000000456 and advertiser 21700000000011523. * Substitute your own agency ID and advertiser IDs for the IDs in this sample. */ private static ReportRequest createSampleRequest() { return new ReportRequest() .setReportScope(new ReportScope() .setAgencyId(12300000000000456L) // Replace with your ID .setAdvertiserId(21700000000011523L)) // Replace with your ID .setReportType("campaign") .setColumns(Arrays.asList( new ReportApiColumnSpec[] { new ReportApiColumnSpec().setColumnName("campaignId"), new ReportApiColumnSpec().setColumnName("campaign") })) .setTimeRange(new TimeRange() .setStartDate("2012-05-01") .setEndDate("2012-05-01")) .setDownloadFormat("csv") .setStatisticsCurrency("usd") .setMaxRowsPerFile(5000000); }
.NET
この関数は、広告主のキャンペーンを一覧表示して、広告主に割り当てるレポートを作成します。 返されたトークンをreportId
に返します。
using api = Google.Apis.Doubleclicksearch.v2; /// <summary> /// Creates a report with a sample request and returns the report ID. /// </summary> /// <param name="service">Search Ads 360 API service.</param> private static string CreateReport(api.DoubleclicksearchService service) { var req = service.Reports.Request(CreateSampleRequest()); var report = req.Execute(); Console.WriteLine("Created report: ID={0}", report.Id); return report.Id; } /// <summary> /// Returns a simple static request that lists the ID and name of all /// campaigns under an advertiser. /// Substitute your own agency ID and advertiser IDs for the IDs in this sample. /// </summary> private static api.Data.ReportRequest CreateSampleRequest() { return new api.Data.ReportRequest { ReportScope = new api.Data.ReportRequest.ReportScopeData { AgencyId = 12300000000000456, // Replace with your ID AdvertiserId = 21700000000011523 // Replace with your ID }, ReportType = ReportType.CAMPAIGN, Columns = new List<api.Data.ReportApiColumnSpec> { new api.Data.ReportApiColumnSpec { ColumnName = "campaignId", }, new api.Data.ReportApiColumnSpec { ColumnName = "campaign", }, }, TimeRange = new api.Data.ReportRequest.TimeRangeData { StartDate = "2015-01-01", EndDate = "2015-01-07", }, DownloadFormat = "csv", StatisticsCurrency = "usd", MaxRowsPerFile = 5000000, }; }
Python
def request_report(service): """Request sample report and print the report ID that DS returns. See Set Up Your Application. Args: service: An authorized Doubleclicksearch service. Returns: The report id. """ request = service.reports().request( body= { "reportScope": { "agencyId": "12300000000000456", // Replace with your ID "advertiserId": "21700000000011523", // Replace with your ID "engineAccountId": "700000000073991" // Replace with your ID }, "reportType": "keyword", "columns": [ { "columnName": "campaignId" }, { "columnName": "keywordText" }, { "columnName": "keywordLandingPage" }, { "columnName": "date" }, { "columnName": "dfaRevenue" }, { "columnName": "visits", "startDate": "2013-01-01", "endDate": "2013-01-31", "headerText": "visits last month" } ], "timeRange" : { "startDate" : "2012-05-01", "endDate" : "2012-05-02" }, "filters": [ { "column" : { "columnName": "keywordLandingPage" }, "operator" : "startsWith", "values" : [ "http://www.foo.com", "http://www.bar.com" ] } ], "downloadFormat": "csv", "maxRowsPerFile": 6000000, "statisticsCurrency": "agency", "verifySingleTimeZone": "false", "includeRemovedEntities": "false" } ) json_data = request.execute() return json_data['id']
検証が成功した場合
レポートの検証に合格すると、検索広告 360 からレポート ID が返されます。検索広告 360 では 通貨コードとタイムゾーンに関するメタデータを返します。
{ "kind": "adsdartsearch#report", "id": "MTMyNDM1NDYK", // This is the report id. "isReportReady": false, // The report is not finished generating. "request": { // The request that created this report. ... }, "statisticsCurrencyCode": "CAD", // The currency used for statistics. E.g., if // advertiser currency was requested, this would be // currency code of the advertiser in scope. "statisticsTimeZone": "America/New_York" // If all statistics in the report were sourced from // a single time zone, this would be it. If // verifySingleTimeZone was set to true in the request, // then this field will always be populated (or the // request will fail). }
検証で不合格だった場合
レポートが検証に合格しなかった場合、検索広告 360 は HTTP 400
レスポンスを返します。
返されます。たとえば、上記のリクエストの例では、実際の
代理店:
{ "error": { "code": 400, "message": "statisticsCurrency: the agency in scope does not have a valid currency. Please make sure the agency is properly initialized in Search Ads 360." } }
レポートのステータスをポーリングする
レポート ID を指定して Report.Get()
を呼び出します。
JSON
GET https://www.googleapis.com/doubleclicksearch/v2/reports/MTMyNDM1NDYK
Java
/** * Polls the reporting API with the reportId until the report is ready. * Returns the report. */ private static Report pollUntilReportIsFinished(Doubleclicksearch service, String reportId) throws IOException, InterruptedException { long delay = 1; while (true) { Report report = null; try { report = service.reports().get(reportId).execute(); } catch (GoogleJsonResponseException e) { System.err.println("Report generation has failed."); System.exit(e.getStatusCode()); } if (report.getIsReportReady()) { return report; } System.out.format("Report %s is not ready - waiting %s seconds.%n", reportId, delay); Thread.sleep(TimeUnit.SECONDS.toMillis(delay)); delay = delay + delay; // Double the delay for the next iteration. } }
.NET
using api = Google.Apis.Doubleclicksearch.v2; /// <summary> /// Polls until the report with the given ID completes. /// </summary> /// <param name="service">Search Ads 360 API service.</param> /// <param name="reportId">Report ID to poll.</param> /// <exception cref="ApplicationException"> /// Thrown when the report completes, but has failed. /// </exception> private static api.Data.Report PollUntilReportIsFinished( api.DoubleclicksearchService service, string reportId) { TimeSpan delay = TimeSpan.FromSeconds(1); while (true) { api.Data.Report report; try { report = service.Reports.Get(reportId).Execute(); } catch (Google.GoogleApiException ex) { throw new ApplicationException("Report generation failed", ex); } if (report.IsReportReady.GetValueOrDefault(false)) { return report; } Console.WriteLine("Report is not ready - waiting {0}", delay); Thread.Sleep(delay); delay = delay.Add(delay); // Double the delay for the next iteration. } }
Python
import pprint import simplejson from googleapiclient.errors import HttpError def poll_report(service, report_id): """Poll the API with the reportId until the report is ready, up to ten times. Args: service: An authorized Doubleclicksearch service. report_id: The ID DS has assigned to a report. """ for _ in xrange(10): try: request = service.reports().get(reportId=report_id) json_data = request.execute() if json_data['isReportReady']: pprint.pprint('The report is ready.') # For large reports, DS automatically fragments the report into multiple # files. The 'files' property in the JSON object that DS returns contains # the list of URLs for file fragment. To download a report, DS needs to # know the report ID and the index of a file fragment. for i in range(len(json_data['files'])): pprint.pprint('Downloading fragment ' + str(i) + ' for report ' + report_id) download_files(service, report_id, str(i)) # See Download the report. return else: pprint.pprint('Report is not ready. I will try again.') time.sleep(10) except HttpError as e: error = simplejson.loads(e.content)['error']['errors'][0] # See Response Codes pprint.pprint('HTTP code %d, reason %s' % (e.resp.status, error['reason'])) break
レポートの準備ができていない場合
レポートの準備ができていない場合、検索広告 360 は HTTP 202
レスポンスを返し、isReportReady
フィールドは false です。
{ "kind": "doubleclicksearch#report", "id": "MTMyNDM1NDYK", "isReportReady": false, "request": { ... }, ... }
レポートの準備ができたら
レポートが完成してダウンロードの準備ができたら、isReportReady
このフィールドが true です。レスポンスには、files
フィールドも追加されています。
にレポート ファイルをダウンロードするための URL が含まれています。
{ "kind": "doubleclicksearch#report", "id": "MTMyNDM1NDYK", "isReportReady": true, "request": { ... }, ... "rowCount": 1329, // Total rows in the report, not counting headers. "files": [ { "url": "https://www.googleapis.com/doubleclicksearch/v2/reports/MTMyNDM1NDYK/files/0" "byteCount": "10242323" }, { "url": "https://www.googleapis.com/doubleclicksearch/v2/reports/MTMyNDM1NDYK/files/1" "byteCount": "10242323" } ], }
レポートの生成が失敗した場合
検索広告 360 がレポートを生成できない場合、いくつかの HTTP のうちの 1 つが返されます。 エラーコードと説明が表示されます
{ "error" : { "code" : 410, // Or other error codes. "message" : "Processing was halted on the backend and will not continue." } }
レスポンス コードの詳細については、レスポンス コードをご覧ください。 エラーが表示されます
レポートをダウンロード
レポートをダウンロードするには、各レポート ファイルの URL を直接指定するか、次のように Reports.getFile()
を呼び出します。
レポート ID とファイル番号(0 のインデックス付き)が含まれます。検索広告 360 は、UTF-8 エンコード ファイルでレポートを返します。
Reports.getFile()
リクエストの例を次に示します。
JSON
GET https://www.googleapis.com/doubleclicksearch/v2/reports/MTMyNDM1NDYK/files/0?alt=media
GET https://www.googleapis.com/doubleclicksearch/v2/reports/MTMyNDM1NDYK/files/1?alt=media
Java
/** * Downloads the shards of a completed report to the given local directory. * Files are named CampaignReport0.csv, CampaignReport1.csv, and so on. */ private static void downloadFiles( Doubleclicksearch service, Report report, String localPath) throws IOException { for (int i = 0; i < report.getFiles().size(); i++) { FileOutputStream outputStream = new FileOutputStream(new File(localPath, "CampaignReport" + i)); service.reports().getFile(report.getId(), i).executeAndDownloadTo(outputStream); outputStream.close(); } }
.NET
using api = Google.Apis.Doubleclicksearch.v2; /// <summary> /// Downloads the shards of a completed report to the given local directory. /// Files are named CampaignReport0.csv, CampaignReport1.csv, and so on. /// </summary> /// <param name="service">Search Ads 360 API service.</param> /// <param name="report">Report ID to download.</param> /// <param name="localPath">Path of the directory to place downloaded files.</param> private static void DownloadFiles( api.DoubleclicksearchService service, api.Data.Report report, string localPath) { Directory.CreateDirectory(localPath); for (int i = 0; i < report.Files.Count; ++i) { string fileName = Path.Combine( localPath, string.Format("CampaignReport{0}.csv", i)); Console.WriteLine("Downloading shard {0} to {1}", i, fileName); using (Stream dst = File.OpenWrite(fileName)) { service.Reports.GetFile(report.Id, i).Download(dst); } } }
Python
def download_files(service, report_id, report_fragment): """Generate and print sample report. Args: service: An authorized Doubleclicksearch service. report_id: The ID DS has assigned to a report. report_fragment: The 0-based index of the file fragment from the files array. """ f = file('report-' + report_fragment + '.csv', 'w') request = service.reports().getFile_media(reportId=report_id, reportFragment=report_fragment) f.write(request.execute().decode('utf-8')) f.close()
サンプル レポート
CSV レポートの例を次に示します。各レポート ファイル フラグメントには独自のヘッダーがある 選択します。この形式の詳細については、RFC 4,180。
keywordText,campaignId,landingPageUrl,day,revenue,visits last month,my revenue google,71700000002104742,http://www.google.com,2012-05-01,10.2,5,20 google,71700000002104742,http://www.google.com,2012-05-02,11,10,60.23
ID マッピング ファイルをダウンロード
検索広告 360 従来版と 検索広告 360 リニューアル版リクエストされた広告主のファイルには、すべての子エンティティ(例: エンジン アカウント、キャンペーン、広告グループなど)を検索広告 360 従来版の両方に存在する 検索広告 360 リニューアル版のご利用をおすすめいたします。
Python
def download_mapping_file(service, file_name, agency_id, advertiser_id): """Generate and save mapping file to a csv. Args: service: An authorized Doubleclicksearch service. file_name: Filename to write the ID mapping file. agency_id: DS ID of the agency. advertiser_id: DS ID of the advertiser. """ request = service.reports().getIdMappingFile_media(agencyId=agency_id, advertiserId=advertiser_id) response = request.execute() response = response.decode('utf-8') f = open(file_name + '.csv', 'w') f.write(response) f.close()