如何使用服务帐户检索 Google 组成员资格?

How to retrieve Google group membership with a service account?

我正在尝试 retrieve/update Google 使用服务帐户在后台进程中对成员资格进行分组,但在执行查询时出现此错误。如何将这些权限添加到服务帐户?

Google.GoogleApiException: 'Google.Apis.Requests.RequestError
Not Authorized to access this resource/api [403]
Errors [
    Message[Not Authorized to access this resource/api] Location[ - ] Reason[forbidden] Domain[global]
]
'

C#代码:

using FileStream fileStream = File.OpenRead(@"key.json");
GoogleCredential googleCredential = GoogleCredential.FromStream(fileStream)
    .CreateScoped("https://www.googleapis.com/auth/admin.directory.group.member");
BaseClientService.Initializer initializer = new()
{
    HttpClientInitializer = googleCredential,
    ApplicationName = "My App",
};
DirectoryService service = new(initializer);
MembersResource.ListRequest listRequest = service.Members.List("my-group@example.com");
Members members = await listRequest.ExecuteAsync();

看来您必须使用 setServiceAccountUser,这在基于 JSON 的凭据中不受支持。你可以这样构建它:

import static com.google.api.client.googleapis.util.Utils.getDefaultJsonFactory;
import static com.google.api.client.googleapis.util.Utils.getDefaultTransport;

private static final String APPLICATION_NAME = "AnyAppName";

private final List<String> SCOPES = ImmutableList.of(
        DirectoryScopes.ADMIN_DIRECTORY_GROUP_MEMBER, DirectoryScopes.ADMIN_DIRECTORY_USER, DirectoryScopes.ADMIN_DIRECTORY_GROUP);

private Directory service;

@PostConstruct
void init() throws GeneralSecurityException, IOException {
    GoogleCredential credential;
    try (InputStream is = new FileInputStream("./config/client_secret.json")) {
        credential = GoogleCredential.fromStream(is);
    }
    GoogleCredential credentialWithUser = new GoogleCredential.Builder()
            .setTransport(getDefaultTransport())
            .setJsonFactory(getDefaultJsonFactory())
            .setServiceAccountUser("admin@yourdomain.ru")  // <--- mail of domain's admin
            .setServiceAccountId(credential.getServiceAccountId())
            .setServiceAccountScopes(SCOPES)
            .setServiceAccountPrivateKey(credential.getServiceAccountPrivateKey())
            .setServiceAccountPrivateKeyId(credential.getServiceAccountPrivateKeyId())
            .setTokenServerEncodedUrl(credential.getTokenServerEncodedUrl()).build();

    service = new Directory.Builder(getDefaultTransport(), getDefaultJsonFactory(), credentialWithUser).setApplicationName(APPLICATION_NAME).build();
}

public void members() throws IOException {
   Members members = service.members().list("groupName@yourdomain.ru").execute();
   System.out.println(members);
}

参考:

  • Google Directory API returns Not Authorized when call users().list().execute()

谢谢,我已经更改了这些行,现在可以使用了!

GoogleCredential googleCredential = GoogleCredential.FromStream(fileStream)
    .CreateScoped("https://www.googleapis.com/auth/admin.directory.group.member")
    .CreateWithUser("my-user@example.com");