Reputation: 11
today i try to do a request with reporting API v4 to get data from google analytics. I write in google app script to display data in google spreadsheet.
Here's my function:
function get_ga(){
var now = new Date();
var doc = SpreadsheetApp.getActiveSpreadsheet();
var site = doc.getSheetByName("Dashboard").getRange(2,1).getValue();
var sheet = doc.getSheetByName("Google analytics");
var service = getService();
if (sheet==null){
sheet = doc.insertSheet("Google analytics");
}
start_date=getstart(now);
end_date=getend(now);
if (service.hasAccess()) {
var apiURL = 'https://analyticsreporting.googleapis.com/v4/reports:batchGet';
var headers = {"Authorization": "Bearer " + getService().getAccessToken()};
var request = {
"reportRequests":
[
{
"viewId": VIEW_ID,
"dateRanges": [{"startDate": start_date, "endDate": end_date}],
"metrics": [{"expression": "ga:users"}]
}
]
}
var options = {
"headers" : headers,
"contentType":'application/json',
"method" : "post",
"payload" : JSON.stringify(request),
"muteHttpExceptions": true
};
try {
var response = UrlFetchApp.fetch(apiURL, options);
}
catch (e) {
Logger.log(e);
}
Logger.log(response)
var result = JSON.parse(response.getContentText());
console.log(result);
if (result.error){
return null;
}
}
else {
var authorizationUrl = service.getAuthorizationUrl();
Logger.log('Open the following URL and re-run the script: %s', authorizationUrl);
return 0;
}
}
Of course i have a OAuth2.0.gs file with:
function getService() {
// Create a new service with the given name. The name will be used when
// persisting the authorized token, so ensure it is unique within the
// scope of the property store.
return OAuth2.createService('searchconsole')
// Set the endpoint URLs, which are the same for all Google services.
.setAuthorizationBaseUrl('https://accounts.google.com/o/oauth2/auth')
.setTokenUrl('https://accounts.google.com/o/oauth2/token')
// Set the client ID and secret, from the Google Developers Console.
.setClientId(CLIENT_ID)
.setClientSecret(CLIENT_SECRET)
// Set the name of the callback function in the script referenced
// above that should be invoked to complete the OAuth flow.
.setCallbackFunction('authCallback')
// Set the property store where authorized tokens should be persisted.
.setPropertyStore(PropertiesService.getUserProperties())
// Set the scopes to request (space-separated for Google services).
// this is Search Console read only scope for write access is:
// https://www.googleapis.com/auth/webmasters
.setScope('https://www.googleapis.com/auth/webmasters')
// Below are Google-specific OAuth2 parameters.
// Sets the login hint, which will prevent the account chooser screen
// from being shown to users logged in with multiple accounts.
.setParam('login_hint', Session.getActiveUser().getEmail())
// Requests offline access.
.setParam('access_type', 'offline')
// Forces the approval prompt every time. This is useful for testing,
// but not desirable in a production application.
.setParam('approval_prompt', 'force');
}
function authCallback(request) {
var searchConsoleService = getService();
var isAuthorized = searchConsoleService.handleCallback(request);
if (isAuthorized) {
return HtmlService.createHtmlOutput('Success! You can close this tab.');
} else {
return HtmlService.createHtmlOutput('Denied. You can close this tab');
}
}
Finally i have a variables.gs file with my differents ID and my VIEW id from google analytics, corresponding to the website i want data from. Something important is that i see data in google analytics but i'm not the owner of the website ;
//GSC
var CLIENT_ID = '*******************************************';
var CLIENT_SECRET = '*****************';
//GA
var CLIENT_ID2 = '************************************';
var CLIENT_SECRET2 = '**************';
var VIEW_ID = '********';
with google search console and google analytics API enabled. All my functions are perfectly working with google search console.
The error is:{"error":{"status":"PERMISSION_DENIED","code":403,"message":"Request had insufficient authentication scopes."}} The first thing strange i noticed is that i use client ID and client secret from Google Search console for authentification for google analytics (see my OAuth2.0.gs file) but it seems to work; otherwise i 'll get a 401 error.
Upvotes: 1
Views: 1213
Reputation: 2225
When using Google API's from google apps script, you will want to use Advanced Google Services for the Analytics Service. Be sure to Enable the service in your script.
Once enabled, auto-completion in the script editor for the new methods become available. Type AnalyticsReporting.
to see it.
For Analytics Reporting batchGet the method would be AnalyticsReporting.Reports.batchGet(resource)
Example use:
function get_ga(){
var now = new Date();
var start_date=getstart(now);
var end_date=getend(now);
var request = {
"reportRequests":
[
{
"viewId": VIEW_ID,
"dateRanges": [{"startDate": start_date, "endDate": end_date}],
"metrics": [{"expression": "ga:users"}]
}
]
}
var response = AnalyticsReporting.Reports.batchGet(JSON.stringify(request));
Logger.log(response)
}
[Note: Im using your request object and assuming it is correct, as I do not personally use analytics and have not tested the code. However, Advanced Google Services all work the same within google apps script. Basically, just piece together the JSON representation objects from the Google Analytics Reporting API and use it as the argument in the desired API advanced service method.]
Upvotes: 2