6

I'm trying to get the list of files on Google Drive with curl, but OAuth 2 is getting the best of me.

Here are some of the things I tried:

curl -H "Authorization: Bearer $token" https://www.googleapis.com/drive/v2/files

Where $token is a 460 character string I got using:

https://www.google.com/accounts/ClientLogin

and this upload script (which works great). This is the error I received:

 {
  "error": {
   "errors": [
    {
      "domain": "global",
      "reason": "authError",
      "message": "Invalid Credentials",
      "locationType": "header",
      "location": "Authorization"
    }
   ],
   "code": 401,
   "message": "Invalid Credentials"
  }
 }

Also tried:

curl https://www.googleapis.com/drive/v2/files?key=apiKey

Error:

{
 "error": {
  "errors": [
   {
    "domain": "global",
    "reason": "required",
    "message": "Login Required",
    "locationType": "header",
    "location": "Authorization"
   }
  ],
  "code": 401,
  "message": "Login Required"
 }
}

And:

curl -H "Authorization: GoogleLogin auth=${token}" "https://www.googleapis.com/drive/v2/files"

Error:

{
 "error": {
  "errors": [
   {
    "domain": "usageLimits",
    "reason": "dailyLimitExceededUnreg",
    "message": "Daily Limit for Unauthenticated Use Exceeded. Continued use requires signup.",
    "extendedHelp": "https://code.google.com/apis/console"
   }
  ],
  "code": 403,
  "message": "Daily Limit for Unauthenticated Use Exceeded. Continued use requires signup."
 }
}

I had little success with both the JavaScript and PHP client libraries, both seem optimized for the situation where the user provides log/pass in order to authorize the app. What I need is a way to list the files from a single account, every time.

Tambourine Man
  • 311
  • 1
  • 2
  • 10

2 Answers2

13

I just spent like 30 minutes to figure this out myself for accessing contacts API and redid the steps for drive API and documented them for future reference. There are 5 steps and the first 4 are one time setup.

Step 1: Create new OAuth2 credentials

Create API Manager > Credentials > OAuth Client ID

Application type = Other, Name = curl-client

enter image description here

Note down the client ID and client secret.

Step 2: Request authorization with drive as scope.

Using the client ID and https://docs.google.com/feeds as scope, construct the below curl command:

$ curl -d "client_id=413437979384-05efiod756k5hp2eji5tsn2lmlg0qslc.apps.googleusercontent.com&scope=https://docs.google.com/feeds" https://accounts.google.com/o/oauth2/device/code
{
  "device_code" : "KRYU-NTVW4/qi6ysOpK2AtsmtZz4MB9LAthlYGGgAepxpBnGQLvhqo",
  "user_code" : "KRYU-NTVW",
  "verification_url" : "https://www.google.com/device",
  "expires_in" : 1800,
  "interval" : 5
}

Copy the user_code.

Step 3: Authorize the request.

Visit the verification URL https://www.google.com/device and enter the copied code.

Paste the code and press Next

Press Allow

Step 4: Obtain access_token.

Add the device_code obtained from the auth request to the client ID and client secret and construct the below curl command:

$ curl -d "client_id=413437979384-05efiod756k5hp2eji5tsn2lmlg0qslc.apps.googleusercontent.com&client_secret=0zWNribRJ4PcYWH-rDkCpCcm&grant_type=http://oauth.net/grant_type/device/1.0&code=KRYU-NTVW4/qi6ysOpK2AtsmtZz4MB9LAthlYGGgAepxpBnGQLvhqo" https://www.googleapis.com/oauth2/v4/token
{
 "access_token": "ya29.kgKW4Z4IDqK7lCjUQw-u5VT2uAx19MtgdoKeAC9ikKYGwKh7Nh46pY8nQsANQ5lRwA",
 "token_type": "Bearer",
 "expires_in": 3600,
 "refresh_token": "1/qinFVaMPYvhWtUtmjb1qCpnQt48XyvQhB_ILZJ4H1Uw"
}

We now have the required access_token, save it and use it with all the drive REST API requests.

Step 5: Drive API request.

$ curl -H 'GData-Version: 3.0' -H 'Authorization: Bearer ya29.kgKW4Z4IDqK7lCjUQw-u5VT2uAx19MtgdoKeAC9ikKYGwKh7Nh46pY8nQsANQ5lRwA' https://www.googleapis.com/drive/v2/files
{
 "kind": "drive#fileList",
...
haridsv
  • 9,065
  • 4
  • 62
  • 65
  • but the token has expiration, can I renew it without verifying the code on the browser? – Moshe Jan 23 '19 at 15:58
  • 1
    Great answer, Thank you. I was able to replicate the process. I am also, however, curious on how to refresh the `access_token`s when they expire. Any help on that? – daydreamer Jul 25 '19 at 15:09
  • One of the best answers on stackoverflow. – Arshad May 31 '21 at 15:25
7

For future googlers:

If you want to save yourself an afternoon of pain, forget google's doumentation and head over here

The gist of it, since I know stackoverflow prefers quoting the content to linking:

First, get your client ID in Google Developer Console for OAuth2. This will require to fill in the OAuth consent screen and after testing, you will have to get your domain verified. (Google will lead you in the process...)

In your browser:

https://accounts.google.com/o/oauth2/auth?scope=https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fanalytics&redirect_uri=urn:ietf:wg:oauth:2.0:oob&response_type=code&client_id=1234567890.apps.googleusercontent.com

Allow the access, of course, and copy the code which should look like 4/v6xr77ewYqjkslsdUOKwAzu

curl -H "Content-Type: application/x-www-form-urlencoded" -d 'code=4/v6xr77ewYqjkslsdUOKwAzu&client_id=1234567890.apps.googleusercontent.com&client_secret=xywzxywzxywzxywzxywz&redirect_uri=urn:ietf:wg:oauth:2.0:oob&grant_type=authorization_code' https://accounts.google.com/o/oauth2/token

You’ll get a JSON like this one:

{
  "access_token" : "ya29.AHES6Zkjhkjhahskjhskkskjh",
  "token_type" : "Bearer",
  "expires_in" : 3600,
  "refresh_token" : "1/HH9E7k5D0jakjhsd7askdjh7899a8sd989"
}

If you curl:

curl 'https://www.googleapis.com/oauth2/v1/tokeninfo?access_token=ya29.AHES6Zkjhkjhahskjhskkskjh'

you’ll get something like:

{
 "issued_to": "562211803675.apps.googleusercontent.com",
 "audience": "562211803675.apps.googleusercontent.com",
 "scope": "https://www.googleapis.com/auth/analytics",
 "expires_in": 3556
}

Done

curl 'https://www.googleapis.com/analytics/v3/management/accounts?access_token=ya29.AHES6Zkjhkjhahskjhskkskjh

Renew the token

You have to use the “refresh_token” received previously

curl -d "client_id=562211803675.apps.googleusercontent.com&client_secret=ZQxoOBGbvMGnZOYUrVIDXrgl&refresh_token=1/HH9E7k5D0jakjhsd7askdjh7899a8sd989&grant_type=refresh_token" https://accounts.google.com/o/oauth2/token

and you’ll get a new access_token.

Mikher
  • 33
  • 5
Tambourine Man
  • 311
  • 1
  • 2
  • 10
  • 1
    But this is analytics ... does it work the same way for drive.files? I wasn't able to get an access token for that scope using this description, yet. – Fildor Nov 02 '15 at 12:17
  • 2
    By the way, as 20 July 2022, the source link is dead. That is the reason why Stack Overflow prefers quoting content over just linking it, as a precaution in case that happens. – bayuah Jul 20 '22 at 12:12