Google Admin sdk directory 403

2020-04-29 01:31发布

问题:

I'm trying to use googleapi 2.0 with service account to use Directory gooogle admin sdk on user on an entrprise domain. I've proceeded as suggested (this for instance) and prepared a "wish to work" poc java code.

Somthing like this...

package com.mc3info.google.api20.test;

import java.io.File;
import java.security.NoSuchAlgorithmException;
import java.security.UnrecoverableKeyException;
import java.security.cert.CertificateException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import com.google.api.client.googleapis.auth.oauth2.GoogleCredential;
import com.google.api.client.googleapis.javanet.GoogleNetHttpTransport;
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.admin.directory.Directory;
import com.google.api.services.admin.directory.Directory.Members;
import com.google.api.services.admin.directory.Directory.Users.Get;
import com.google.api.services.admin.directory.DirectoryScopes;
import com.google.api.services.admin.directory.Directory.Groups;
import com.google.api.services.admin.directory.Directory.Users;
import com.google.api.services.admin.directory.model.User;

public class TestUsersList {


    public static void main(String[] args) {

        try {
          File f = new File("config/xxxxxxx-privatekey.p12");
          System.out.println(f.getAbsolutePath());
          ArrayList<String> scopes = new ArrayList<String>();
//          scopes.add(DirectoryScopes.ADMIN_DIRECTORY_GROUP);
//          scopes.add(DirectoryScopes.ADMIN_DIRECTORY_GROUP_READONLY );
//          scopes.add(DirectoryScopes.ADMIN_DIRECTORY_GROUP_MEMBER);
//          scopes.add(DirectoryScopes.ADMIN_DIRECTORY_GROUP_MEMBER_READONLY);
          scopes.add(DirectoryScopes.ADMIN_DIRECTORY_USER );
          scopes.add(DirectoryScopes.ADMIN_DIRECTORY_USER_READONLY );
//          scopes.add(DirectoryScopes.ADMIN_DIRECTORY_USER_SECURITY);
            HttpTransport myHttpTransport = new NetHttpTransport();
            JsonFactory JSON_FACTORY = new JacksonFactory();
          GoogleCredential credential = (new GoogleCredential.Builder()
            .setTransport(myHttpTransport )
            .setJsonFactory(JSON_FACTORY)
              .setServiceAccountId("xxxxxxxxxxxx@developer.gserviceaccount.com")
            .setJsonFactory(JSON_FACTORY)
            .setServiceAccountPrivateKeyFromP12File(f )
            .setServiceAccountScopes(scopes)
            ).build();

            credential.refreshToken();
//          String at = credential.getAccessToken();
            String applicationName = "NYAPPLICATIONNAME"; 


            Directory dir = new Directory.Builder(myHttpTransport, JSON_FACTORY, credential)
                .setApplicationName(applicationName )
                .setHttpRequestInitializer(credential)
                .build();
            com.google.api.services.admin.directory.Directory.Users.List ures = dir.users().list();
            ures.setDomain("genericidoc.it");
            ures.setOrderBy("email");

//            ures.setSortOrder("ASCENDING");
//            ures.setFields("users(agreedToTerms,changePasswordAtNextLogin,creationTime,customerId,deletionTime,etag,hashFunction,id,includeInGlobalAddressList,ipWhitelisted,isAdmin,isDelegatedAdmin,isMailboxSetup,kind,lastLoginTime,name,orgUnitPath,password,primaryEmail,suspended,suspensionReason,thumbnailPhotoUrl");

            com.google.api.services.admin.directory.model.Users lures = ures.execute();
            //HERE print all data 
//            for (){
//              System.out.println("Utente : ");
//            }
//            
            Groups grp = dir.groups();

            com.google.api.services.admin.directory.model.Groups res = grp.list().execute();



//            Directory.Members.List members  = dir.members().list("someexisting email");

            /*
             * Values for getting GoogleCredential, found in the
             * "Service account section" at:
             * https://code.google.com/apis/console/#access
             */
            // serviceAccountId from the "Email address" field.


            // Name of group to get for testing the authentication

        } catch (Throwable t) {
            t.printStackTrace();
        }
    }
}

but getting a 403 error:

And ... Yes, refreshToken() invokation should not be requied but it ensures me thath al least handshake was ok...

403 Forbidden
{
 "code" : 403,
 "errors" : [ {
 "domain" : "global",
 "message" : "Not Authorized to access this resource/api",
 "reason" : "forbidden"
 } ],
 "message" : "Not Authorized to access this resource/api"
}

回答1:

Take a look at Google's docs on using service accounts with Admin SDK for domain-wide delegation.

  • You didn't mention it, but you definitely need to grant the service account's client id access to the Admin SDK scopes from your Google Apps Control Panel.

  • Your code is missing a line like .setServiceAccountUser(userEmail) which allows the service account to impersonate a user in your Google Apps domain who has rights to search the directory (probably a super admin user).