On a Ubuntu server I want to regularly execute a script which calls the Google Analytics Data API in order to extract the 20 most visited pages of a website.
gcloud
CLI (Google Cloud CLI) on my Ubuntu 24 server.According to the Google Cloud CLI Documentation i created the following bash script:
#!/bin/bash
# Set environment variables
export KEY_FILE="/home/yesitsme/utilities/scripts/gcloud.json"
export PROPERTY_ID="278767000"
# Authenticate using the service account
gcloud auth activate-service-account --key-file=$KEY_FILE
# Get access token
ACCESS_TOKEN=$(gcloud auth print-access-token)
# Make API request for page views in the last 24 hours
curl -X POST \
"https://analyticsdata.googleapis.com/v1beta/properties/$PROPERTY_ID:runReport" \
-H "Authorization: Bearer $ACCESS_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"dateRanges": [
{
"startDate": "yesterday",
"endDate": "today"
}
],
"dimensions": [
{
"name": "pagePath"
}
],
"metrics": [
{
"name": "screenPageViews"
}
],
"limit": 5
}'
If i execute the gcloud auth
command only, i see that the access token gets created successfully.
But when executing the script, i get this output with an error:
Activated service account credentials for: [zwischengas-google-cloud-api@zwischengas.iam.gserviceaccount.com]
{
"error": {
"code": 403,
"message": "Request had insufficient authentication scopes.",
"status": "PERMISSION_DENIED",
"details": [
{
"@type": "type.googleapis.com/google.rpc.ErrorInfo",
"reason": "ACCESS_TOKEN_SCOPE_INSUFFICIENT",
"domain": "googleapis.com",
"metadata": {
"method": "google.analytics.data.v1beta.BetaAnalyticsData.RunReport",
"service": "analyticsdata.googleapis.com"
}
}
]
}
}
So the question is clear: why does my newly created service account have not enough permissions? Any hint?
Thanks to the hint of @DazWilkin i found a working solution. Here is what I have done:
oauth2l --help
Here is the full shell script that accesses your Google Analytics:
#!/bin/bash
# Set variables
KEY_FILE="/home/myuser/gcloud-service-account-secret.json"
PROPERTY_ID="27yy67xxx"
SCOPE="https://www.googleapis.com/auth/analytics.readonly"
# Get an access token
ACCESS_TOKEN=$(oauth2l fetch --credentials=$KEY_FILE --scope=$SCOPE)
# Check if token retrieval was successful
if [ -z "$ACCESS_TOKEN" ]; then
echo "Failed to retrieve access token"
exit 1
fi
# Query Google Analytics Data API
curl -s -X POST \
"https://analyticsdata.googleapis.com/v1beta/properties/$PROPERTY_ID:runReport" \
-H "Authorization: Bearer $ACCESS_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"dateRanges": [
{
"startDate": "yesterday",
"endDate": "today"
}
],
"dimensions": [
{
"name": "pagePath"
}
],
"metrics": [
{
"name": "screenPageViews"
}
],
"dimensionFilter": {
"orGroup": {
"expressions": [
{
"filter": {
"fieldName": "pagePath",
"stringFilter": {
"matchType": "BEGINS_WITH",
"value": "/path1_i_want_to_include/"
}
}
},
{
"filter": {
"fieldName": "pagePath",
"stringFilter": {
"matchType": "BEGINS_WITH",
"value": "/path2/i/want/to_include/"
}
}
}
]
}
},
"limit": 50
}'
The result is simply a JSON file that you can store on disk and further process with your backend software.