401 response when athenticating via Service Account and OAuth2 to GoogleDrive

雨燕双飞 提交于 2019-12-18 17:06:52

问题


I seem to have hit a wall trying to get a Java application to list of files stored in my GoogleDrive folder. The

I have a project setup in the Developer Console. I have enabled for that project the Drive API I have create Auth credentials for a Service Account - and am using the P12 key produced.

My code looks like this :

import com.google.api.client.auth.oauth2.Credential;
import com.google.api.client.auth.oauth2.CredentialRefreshListener;
import com.google.api.client.auth.oauth2.TokenErrorResponse;
import com.google.api.client.auth.oauth2.TokenResponse;
import com.google.api.client.googleapis.auth.oauth2.GoogleCredential;
import com.google.api.client.http.HttpTransport;
import com.google.api.client.http.javanet.NetHttpTransport;
import com.google.api.client.json.JsonFactory;
import com.google.api.client.json.jackson2.JacksonFactory;
import com.google.api.services.drive.Drive;
import com.google.api.services.drive.DriveScopes;
import com.google.api.services.drive.model.File;
import com.google.api.services.drive.model.FileList;

import java.io.IOException;
import java.security.GeneralSecurityException;
import java.util.Collections;
import java.util.List;

public class GoogleDriveTest {

    /** Global instance of the JSON factory. */
    private static final JsonFactory JSON_FACTORY = new JacksonFactory() ;

    /** instance of the HTTP transport. */
    private static final HttpTransport HTTP_TRANSPORT = new NetHttpTransport() ;

    /** Global instance of the Google Drive - the first connect will initialize */
    private static Drive drive;

    /*
     * instance variables
     */
    private String accessToken ;

    public static void main(String[] args) throws GeneralSecurityException, IOException {

        String CLIENTID = "XXXXXXXXXXX-XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX@developer.gserviceaccount.com" ;
        String CLIENTUSER = "XXXXXXXX@gmail.com" ;
        String P2FILE = "random/src/main/resources/test.p12" ;

        try {
            GoogleCredential credential = new GoogleCredential.Builder().setTransport(HTTP_TRANSPORT)
                    .setJsonFactory(JSON_FACTORY)
                    .setServiceAccountId(CLIENTID)
                    .setServiceAccountScopes(Collections.singleton(DriveScopes.DRIVE_FILE))
                    .setServiceAccountPrivateKeyFromP12File(new java.io.File(P2FILE))
                    .setServiceAccountUser(CLIENTUSER)
                    .addRefreshListener(new CredentialRefreshListener() {
                        @Override
                        public void onTokenResponse(
                                Credential credential,
                                TokenResponse tokenResponse) throws IOException {

                            String token = tokenResponse.getAccessToken();
                            System.out.println("GOOGLEDRIVE token refreshed " + tokenResponse.getTokenType() + " successfully");
                        }

                        @Override
                        public void onTokenErrorResponse(
                                Credential credential,
                                TokenErrorResponse tokenErrorResponse) throws IOException {

                            System.out.println("GOOGLEDRIVE token refresh failure : " + tokenErrorResponse);
                        }
                    })
                    .build();

            /*
             * set up the global Drive instance
             */
            drive = new Drive.Builder(HTTP_TRANSPORT, JSON_FACTORY, credential).setApplicationName("API Project").build();

            /*
             * output results
             */
            Drive.Files.List fileRequest = drive.files().list() ;
            FileList afiles = fileRequest.execute() ;
            List<File> bFiles = afiles.getItems() ;
            for(File file : bFiles) {
                System.out.println(file.getTitle()) ;
             }
        }
        catch (GeneralSecurityException | IOException e) {
            e.printStackTrace();
        }

    }

}

But the output I see is this :

GOOGLEDRIVE token refresh failure : null
com.google.api.client.auth.oauth2.TokenResponseException: 401 Unauthorized
    at com.google.api.client.auth.oauth2.TokenResponseException.from(TokenResponseException.java:105)
    at com.google.api.client.auth.oauth2.TokenRequest.executeUnparsed(TokenRequest.java:287)
    at com.google.api.client.auth.oauth2.TokenRequest.execute(TokenRequest.java:307)
    at com.google.api.client.googleapis.auth.oauth2.GoogleCredential.executeRefreshToken(GoogleCredential.java:384)
    at com.google.api.client.auth.oauth2.Credential.refreshToken(Credential.java:489)
    at com.google.api.client.auth.oauth2.Credential.intercept(Credential.java:217)
    at com.google.api.client.http.HttpRequest.execute(HttpRequest.java:859)
    at com.google.api.client.googleapis.services.AbstractGoogleClientRequest.executeUnparsed(AbstractGoogleClientRequest.java:419)
    at com.google.api.client.googleapis.services.AbstractGoogleClientRequest.executeUnparsed(AbstractGoogleClientRequest.java:352)
    at com.google.api.client.googleapis.services.AbstractGoogleClientRequest.execute(AbstractGoogleClientRequest.java:469)
    at GoogleDriveTest.main(GoogleDriveTest.java:81)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:483)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:134)

Process finished with exit code 0

Can anyone provide some pointers on Service Account access to Google Drive and what I might be doing wrong here ?

As the Service Account is created under my Google Account (XXXXXXXX@gmail.com) I assumed it would have access to the Drive once the API was enabled.

I have seen other posts about granting access to Service Accounts to a domain account via an admin console - but my account is a plain / standard google account. I'm not even sure what a domain account is !

All help would be greatly appreciated.

来源:https://stackoverflow.com/questions/29277025/401-response-when-athenticating-via-service-account-and-oauth2-to-googledrive

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!