使用服务账号导入 Google Cloud SQL 的权限

23

我已经成功按照MySQL导出指南导出了MySQL数据库。

现在,我正在尝试按照MySQL导入指南导入MySQL数据库。

我已经检查了我正在使用的service_account_email的权限,并且已经允许了Admin SQLAdmin Storage权限。

我能够成功地使用以下命令在本地激活我的服务帐户:

gcloud auth activate-service-account <service_account_email> --key-file=<service_account_json_file>  

我运行了这个命令:

gcloud sql import sql <instance> <gstorage_file> --database=<db_name> --async

我得到了这个信息:

{
  "error": {
    "errors": Array[1][
      {
        "domain": "global",
        "reason": "required",
        "message": "Login Required",
        "locationType": "header",
        "location": "Authorization"
      }
    ],
    "code": 401,
    "message": "Login Required"
  }
}

我尝试过的其他方法

我还尝试使用我的SQL实例的service_account_email,该邮件地址来自于:

gcloud sql instances describe <instance_name>

但是,似乎出现了同样的错误。

问题

根据我收到的REST API JSON错误,如何使用service_account_email "登录",以便我不会收到401错误


一些问题:您是否在同一项目中拥有CloudSQL和GCS? 您是否拥有第二代实例? 如果所有问题都是肯定的,您是否提供了手册中步骤6(将服务帐户添加到存储桶ACL作为编写器)和7(将服务帐户添加到导入文件作为读取器)中提到的权限? - Rubén C.
是的,我在同一个项目中拥有CloudSQL和GCStorage。我的MySQL实例是第二代实例。我已经成功将我的服务帐户添加为编写者和读者(遵循MySQL导入指南)。 - Franz Noel
5个回答

48

问题是数据库实例服务帐户对创建的存储桶没有写入权限。解决此问题的步骤如下:

1)转到您的Cloud SQL实例并复制实例的服务帐户(Cloud SQL -> {实例名称} -> 概述->服务帐户)

2)复制服务帐户后,转到要转储的Cloud Storage存储桶,并为该帐户设置所需的权限(存储->{存储桶名称}->权限->添加成员)。


1
在挣扎了一个小时后,它终于像魔法一样运行了。谢谢! - Paul Kenjora
目前为止,它是<存储桶名称> - 权限->授予访问。要添加的确切角色是“存储对象创建者”。 - Fakeer
谢谢!这些错误信息中应该明确显示相关的服务账户电子邮件。 - bonnal-enzo
如果您需要将存储桶中的文件导入到CloudSQL,则需要具备存储对象查看器权限。 - Edeph

11
云SQL实例正在使用不属于您项目的Google服务帐户运行。 您需要向这个用户授予在Cloud Storage中要导入的文件的权限。 这是一个方便的bash代码片段,可以完成此操作。
SA_NAME=$(gcloud sql instances describe YOUR_DB_INSTANCE_NAME --project=YOUR_PROJECT_ID --format="value(serviceAccountEmailAddress)")
gsutil acl ch -u ${SA_NAME}:R gs://YOUR_BUCKET_NAME;
gsutil acl ch -u ${SA_NAME}:R gs://${YOUR_BUCKET_NAME}/whateverDirectory/fileToImport.sql;

第一行获取服务账号的电子邮件地址。 接下来一行为该服务帐户授予对存储桶的读取权限。 最后一行为服务帐户授予文件的读取权限。


2
如果您想要删除权限(删除所有权限),请执行以下操作: gsutil acl ch -d ${SA_NAME} gs://YOUR_BUCKET_NAMEgsutil acl ch -d ${SA_NAME} gs://YOUR_BUCKET_NAME/file.sql - Kirk

4

谷歌也有一些最糟糕的错误报告。如果你看到这个错误信息,可能是你输入的路径有误。在我的情况下,是我对存储桶目录的路径有误。不过,谁能想到呢,我没有权限访问一个不存在的存储桶。从技术上说是正确的,但几乎没有任何用处。


2
谢谢,这对我来说就是这样了。我很感激我一直向下滚动。 - Mwangi Kabiru
遇到了这个问题。希望这能为某些人节省时间...PROJECT_ID=$(gcloud info --format='value(config.project)') SA_NAME=$(gcloud sql instances describe ${DB_NAME} --project=${PROJECT_ID} --format="value(serviceAccountEmailAddress)") gsutil acl ch -u ${SA_NAME}:R gs://${PROJECT_ID} gsutil acl ch -u ${SA_NAME}:R gs://${PROJECT_ID}/${DB_NAME}.sql gcloud sql import sql ${DB_NAME} gs://${PROJECT_ID}/${DB_NAME}.sql --database ${DB_NAME} - jpswade

1
根据谷歌文档,进行以下操作:
  • 描述要导入的实例:
    gcloud sql instances describe INSTANCE_NAME
  • 复制serviceAccountEmailAddress字段。
  • 使用gsutil iam将storage.objectAdmin IAM角色授权给存储桶的服务帐号。
    gsutil iam ch serviceAccount:SERVICE-ACCOUNT:objectAdmin gs://BUCKET-NAME
  • 然后导入数据库。

0

可能不是这样的。我已经尝试了所有这些方法。可能与我们的SQL或.gz转储文件有关,尽管备份.gz文件来自SQL本身,但我仍在与支持团队一起解决。我会让你知道的。但是,这是正确的方法。 - Franz Noel
我也支持GCP技术支持。如果问题能够通过技术支持解决,那么这将是更好的选择,因为他们拥有更多的信息和工具。一旦问题得到解决,请在此帖子中分享答案,以便社区从中受益。 - Rubén C.

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接