无法验证服务帐户 - Google 云

Unable to authenticate service account - Google Cloud

我假设在写作之前我已经用谷歌搜索并阅读了文档,我注意到这也是 Whosebug 上的热门讨论,但是 none 已经给出的答案有帮助我.

我创建了一个 Google 云帐户来使用 API:Google Vision。

为此,我按照创建项目的步骤进行操作,添加上述内容 API,最后创建一个带有密钥的服务帐户。

我下载了密钥,放在PC上java项目的一个文件夹里。

然后,因为它是一个 Maven 项目,所以我按照教程中的描述将依赖项添加到 pom。

此时我插入了建议的代码段以开始使用 API。

一切似乎都很好,一切都被阅读了,各种libraries/interfaces被导入。

但是当我尝试 运行 程序时出现错误:

The Application Default Credentials are not available. They are available if running in Google Compute Engine. Otherwise, the environment variable GOOGLE_APPLICATION_CREDENTIALS must be defined pointing to a file defining the credentials.

我必须承认我不知道 'Google Compute Engine' 是什么,但由于有替代方案并且我有一些凭据,我想尝试并遵循它。

所以我按照说明操作:

After creating your service account, you need to download the service account key to your machine(s) where your application runs. You can either use the GOOGLE_APPLICATION_CREDENTIALS environment variable or write code to pass the service account key to the client library.

好的,我尝试了第一种方式,通过环境变量传递凭据:

$env:GOOGLE_APPLICATION_CREDENTIALS="my key path"
set GOOGLE_APPLICATION_CREDENTIALS=my key path

所以我尝试了第二种方法,使用代码传递凭据,如果我在这里,肯定是其他地方出了问题,事实上,我所拥有的只能导入 io.grpc.Context,而其他一切给出错误“无法解析符号 ..”。

import com.google.common.collect.Lists;
import io.grpc.Context;

import java.io.FileInputStream;
import java.io.IOException;

public class Main
{
    static void authExplicit(String jsonPath)
    {
        GoogleCredentials credentials = GoogleCredentials.fromStream(new FileInputStream(jsonPath))
                .createScoped( Lists.newArrayList("https://www.googleapis.com/auth/cloud-platform"));
        Context.Storage storage = StorageOptions.newBuilder().setCredentials(credentials).build().getService();

        System.out.println("Buckets:");
        Page<Bucket> buckets = storage.list();
        for (Bucket bucket : buckets.iterateAll()) {
            System.out.println(bucket.toString());
        }
    }

    public static void main(String[] args) throws IOException
    {
        OCR.detectText();
    }
}

(我不认为我可以上传代码屏幕来显示它给我错误的地方,但就是这样)

PS:我也已经安装了 Cloud SDK 并重新启动了 PC,因为一些评论说这样做可以解决问题。

我也试过手动设置环境变量,但没有任何改变:

解决方案

我不知道这一切是否都成功了,因为我为这个命令行执行了一系列操作,无论如何,为了后代:

gcloud auth activate-service-account your_account_email_id --key-file=json_file_path

之后还帮我重启了电脑。

你的做法是正确的。

要验证代码,您应该使用服务帐户。

Google 提供了一种称为应用程序默认凭证 (ADC) 的有用机制。参见 finding credentials automatically。当您使用 ADC 时,Google 的 SDK 使用预定义机制尝试以服务帐户身份进行身份验证:

  1. 正在检查您的环境中的 GOOGLE_APPLICATION_CREDENTIALS。正如您所尝试的那样;
  2. 当 运行 在 GCP 服务(例如计算引擎)上时,通过查找服务的(服务帐户)凭据。使用 Compute Engine,这是通过检查所谓的元数据服务来完成的。

对于 #1,您可以在进程环境中使用 GOOGLE_APPLICATION_CREDENTIALS 您可以在代码中尝试手动加载文件。

综上所述:

  1. 我没看到你的代码将 GoogleCredentials 导入到哪里?
  2. 您是否授予服务帐户合适的角色(权限)以便它可以访问它需要的任何其他 GCP 服务?

应该能够使用这个List objects示例。

上面的link,finding credentials automatically,show show创建一个Service Account,给它分配一个角色然后export它。

您可能希望从 roles/storage.objectAdmin(参见 IAM roles for Cloud Storage)开始(用于开发!)并在部署前进行完善。

请考虑阅读 ImageAnnotationClient class 级别 javadocs,它为您提供了有关如何完成身份验证过程的正确指导。我修改了提供的代码以提供完整示例:

// Please, set the appropriate path to your JSON credentials file here
String credentialsPath = "..."; 
// The credentials could be loaded as well as this.getClass().getResourceAsStream(), for example
GoogleCredentials credentials = GoogleCredentials.fromStream(new FileInputStream(credentialsPath))
    .createScoped(Lists.newArrayList("https://www.googleapis.com/auth/cloud-platform"));

// Use that credentials to build your image annotation client
ImageAnnotatorSettings imageAnnotatorSettings =
  ImageAnnotatorSettings.newBuilder()
    .setCredentialsProvider(FixedCredentialsProvider.create(credentials))
    .build()
;

ImageAnnotatorClient imageAnnotatorClient = ImageAnnotatorClient.create(imageAnnotatorSettings);
// Perform the stuff you need to...

您需要在 pom.xml 中提供的唯一依赖项是 this:

<dependency>
    <groupId>com.google.cloud</groupId>
    <artifactId>google-cloud-vision</artifactId>
    <version>2.0.18</version>
</dependency>

无论如何,请考虑参考 Cloud Vision 示例中提供的pom.xml

Cloud Vision 示例存储库在 Detect class 中为检测过程本身提供了一些有用的代码片段。

确保您用于连接到 Google Cloud 的服务帐户具有必要的权限。

尽管此解决方案可行,但它的缺点是您可能需要将凭据文件存储在计算机中的某个位置,可能在您的源代码存储库中,等等,并且它可能存在安全风险。如果您是 运行 来自 Google Cloud 的程序,始终建议向您正在使用的 VM 或服务授予必要的权限并使用默认的应用程序凭据。

使用 GOOGLE_APPLICATION_CREDENTIALS 也可能更可取。如果您尝试使用此变量,请首先尝试使用 IDE 提供的机制而不是 cmdPSbash 来配置它,然后查看它是否有效。

对于使用最后提到的两个解决方案中的任何一个,您在构建 ImageAnnotatorClient:

时无需提供任何其他信息
ImageAnnotatorClient imageAnnotatorClient = ImageAnnotatorClient.create();