【问题标题】:PermissionDenied: 403 IAM permission 'dialogflow.intents.list'PermissionDenied:403 IAM 权限“dialogflow.intents.list”
【发布时间】:2019-02-19 06:47:48
【问题描述】:

我正在尝试使用 Dialogflow 的 V2 API 在我的 Dialogflow 代理中获取意图列表,但出现以下错误:


PermissionDenied:“projects/xxxx/agent”上的 403 IAM 权限“dialogflow.intents.list”被拒绝。

我采取了以下步骤:

  1. 我创建了一个新代理(启用了 V2 API)和一个新的服务帐户。
  2. 我下载了 JSON 密钥并将我的 GOOGLE_APPLICATION_CREDENTIALS 变量设置为其路径。

以下是我的代码:

import dialogflow_v2 as dialogflow

os.environ["GOOGLE_APPLICATION_CREDENTIALS"]="/home/user/folder/service-account-key.json"

client=dialogflow.IntentsClient()

parent = client.project_agent_path('[PROJECT_ID]')

for element in client.list_intents(parent):
    pass

我已经创建了各种代理和服务帐户,甚至将角色从管理员更改为客户,但无法找到任何解决方案。我尝试了以下解决方案,但没有'工作

尝试解决方案:DialogFlow PermissionDenied: 403 IAM permission 'dialogflow.sessions.detectIntent'

【问题讨论】:

  • 我终于解决了这个问题:我一直在尝试从错误的 GCP 项目创建服务帐户。使其工作的最简单方法是转到聊天机器人代理设置,然后在 General 选项卡中单击 GOOGLE PROJECT 部分中的项目 ID 链接。

标签: google-cloud-platform chatbot dialogflow-es service-accounts


【解决方案1】:

我认为您可能错过了文档设置中的启用 API 部分。

这是链接: https://cloud.google.com/dialogflow/cx/docs/quick/setup#api

点击链接后,选择您创建的聊天机器人项目并填写此处提供的必要说明。

我为该项目授予的权限是所有者和编辑。

在此之后,尝试此链接中的代码: https://cloud.google.com/dialogflow/es/docs/quick/api#detect_intent 您应该得到聊天机器人的回复

希望这会有所帮助!

【讨论】:

    【解决方案2】:

    您需要创建以下内容作为环境变量 谷歌项目ID:“”, 对话流会话ID:“任何东西”, dialogFlowSessionLanguageCode: "en-US", googleClientEmail: "", googlePrivateKey:

    【讨论】:

      【解决方案3】:

      也尝试在 DialogFlow 控制台中创建项目 https://dialogflow.cloud.google.com/

      【讨论】:

        【解决方案4】:

        无需创建新代理。您可以编辑现有代理 IAM。

        1. 在 Dialogflow 的控制台中,转到设置 ⚙ > 在常规选项卡下,您会看到项目 ID 部分,其中包含用于打开 Google Cloud 控制台 > 打开 Google Cloud 的 Google Cloud 链接。
        2. 在谷歌云中,转到 IAM 管理员 > IAM 选项卡下的成员。找到您的代理的名称,然后单击编辑。
        3. 向代理授予管理员权限以授予列出意图的权限。

        【讨论】:

        • 是的,此解决方案也适用于 gcloud 终端 $gcloud alpha dialogflow intents list --impersonate-service-account=[SERVICE_ACCOUNT]
        • 这太有帮助了!谢谢!
        【解决方案5】:

        问题出在 GCP 的 IAM 部分。可能您正在使用没有必要授权的角色发出 POST 请求。

        1. 查看包含“client_email”字段的 key.json 文件
        2. 进入 IAM 页面并将与该电子邮件相关的角色设置为 具有发布功能的角色。 (例如管理员)

        这解决了我的问题。

        【讨论】:

          【解决方案6】:

          当您创建 intentClient 时,请使用以下内容:

          key_file_path = "/home/user/folder/service-account-key.json";
          client=dialogflow.IntentsClient({
                  keyFilename: key_file_path
          })
          

          Intents list

          【讨论】:

            【解决方案7】:
            1. 在 Dialogflow 的控制台中,转到设置 ⚙ > 在常规选项卡下,您会看到项目 ID 部分,其中包含用于打开 Google Cloud 控制台 > 打开 Google Cloud 的 Google Cloud 链接。
            2. (可选)在云控制台中,转到菜单图标 > API 和服务 > 库。选择任何 API(如果有)> 启用。
            3. 在 Cloud Console > 菜单图标下 ☰ > APIs & Services > Credentials > Create Credentials > Service Account Key。 在 Create service account key 下,从下拉列表中选择 New Service Account 并输入项目名称,并为角色选择 Owner > Create。
              • JSON 私钥文件将下载到您需要的本地计算机。

            对于 Javascript: 在 index.js 文件中,您可以使用 JWT 进行服务帐户身份验证:

            const serviceAccount = {};       // Starts with {"type": "service_account",...
            
            // Set up Google Calendar Service account credentials
              const serviceAccountAuth = new google.auth.JWT({
              email: serviceAccount.client_email,
              key: serviceAccount.private_key,
              scopes: 'https://www.googleapis.com/auth/xxxxxxx'
            });
            

            对于 Python: 通过pip install google-auth 可以使用Google Auth Python 库,您可以查看更多here

            【讨论】:

            • 您确定 Owner 角色吗?
            【解决方案8】:

            此错误消息通常在应用程序未正确验证时抛出,原因有多种,例如丢失文件、无效的凭据路径、不正确的环境变量分配等。请记住,当您在会话中设置环境变量值时,每次会话被删除时都会重置它。

            基于此,我建议您验证凭据文件和文件路径是否已正确分配,并遵循Obtaining and providing service account credentials manually 指南,以便将您的服务帐户文件直接明确指定到您的代码中;这样,您将能够永久设置它并验证您是否正确传递了服务凭据。

            在代码示例中将路径传递给服务帐户密钥:

            def explicit():
            from google.cloud import storage
            
            # Explicitly use service account credentials by specifying the private key
            # file.
            storage_client = storage.Client.from_service_account_json('service_account.json')
            
            # Make an authenticated API request
            buckets = list(storage_client.list_buckets())
            print(buckets)
            

            【讨论】:

            • 嗨@Armin_SC,感谢您的回复。我尝试了您的方法,但无法使其适用于对话流。您可以参考以下链接帮助我吗? dialogflow.com/docs/reference/v2-auth-setup
            • 如果您想在应用程序之外单独提供凭据,我建议您按照Setting the environment variable 指导步骤设置GOOGLE_APPLICATION_CREDENTIALS 环境变量并创建.bashrc 文件中提到的您之前提供的 Dialogflow 教程;否则,该变量将仅适用于当前的 shell 会话,因此如果您打开一个新会话,请再次设置该变量。
            • 我也设置了环境变量 GOOGLE_APPLICATION_CREDENTIALS。它适用于列出存储桶,但不适用于 Dialogflow API
            • 您应该查看DialogFlow V2 Authentication 指南和StackOverflow 帖子,其中建议使用 private_key、c​​lient_email 信息创建 Dialogflow 对象,并验证您的帐户是否具有需要roles 来执行这些任务。
            猜你喜欢
            • 2018-12-27
            • 2022-09-27
            • 1970-01-01
            • 1970-01-01
            • 2020-09-04
            • 1970-01-01
            • 2021-08-13
            • 1970-01-01
            • 2018-12-06
            相关资源
            最近更新 更多