如何将IAM服务帐户连接到Cloud SQL实例



在Google Cloud SQL上,PostgreSQL的IAM数据库认证最近普遍可用。

所以,我仔细地按照这里的说明:云SQL IAM数据库身份验证概述。

我认为我已经正确配置了我的云SQL实例,因为对于一个用户帐户,它工作得很好。简而言之:

  1. 我在我的Google Cloud项目中使用我自己的用户帐户,并将角色CloudSQL Instance Viewer添加到其中
  2. 我添加它作为我的CloudSQL实例的用户
  3. 我给它所有的特权,我的db表
  4. 使用下面描述的命令:https://cloud.google.com/sql/docs/postgres/iam-logins,我可以登录到我的db:
PGPASSWORD=$(gcloud auth print-access-token) psql --host=HOSTNAME 
                                                  --username=EMAIL 
                                                  --dbname=DATABASE_NAME

很棒!

但是现在,我真正不明白的是它应该如何在我的应用程序中工作,运行一个服务帐户?医生没怎么说。这是否意味着我必须以编程方式执行此gcloud auth print-access-token的等效操作,并将其结果作为连接到我的db的密码传递?

为了在实例上使用IAM User或IAM Service Account User身份验证,用户或SA电子邮件(或我们在这种情况下处理的SA电子邮件片段)在与数据库进行身份验证时取代了传统的username参数。

此外,密码组件也发生了变化,因为您不为IAM用户设置密码,而是使用OAuth2访问令牌,该令牌必须由客户端通过单独的API调用请求。这些访问令牌仅在60分钟内有效,之后它们过期-然而,一旦令牌过期,它不会断开客户端,但如果客户端连接断开并且必须重新连接到实例,并且已经超过一个小时,那么需要提取新的访问令牌并在新的连接尝试中提供。

对于这个用例,例如,一个无人值守的应用程序,一个服务帐户IAM用户是最好的方法。您的客户端实现将希望使用API客户端库(例如java),它提供了一个方便的类,用于通过JSON密钥文件(可从您的云控制台为SA下载)拉入服务帐户凭据,即

GoogleCredential credential = GoogleCredential.fromStream(new FileInputStream("MyProject-1234.json")).createScoped(Collections.singleton(SQLAdminScopes.SQLSERVICE_ADMIN)).refreshIfExpired();

注意,为了获得适当的访问令牌,必须将作用域设置为Cloud SQL Admin API——上面的示例显示了在上述库和初始化器的上下文中如何工作。请注意,必须在访问令牌可用之前调用'refreshIfExpired()'。

一旦你有了GoogleCredential实例,你可以通过调用getAccessToken()从它获得访问令牌,然后可以提供给你的DB客户端的连接参数/字符串作为服务帐户IAM用户名的密码,即

AccessToken token = credential.getAccessToken();

这里需要强烈考虑的是该流对您的客户机应用程序是否有意义。如果您的客户端应用程序通过连接池或其他连接管理库访问数据库,这些连接管理库会自动重试或使用静态凭据建立新的连接-使用Postgres IAM用户身份验证可能不太合适,因为需要在每次连接尝试时生成一个新的"密码"(访问令牌),其中没有访问令牌可用(即,第一次登录尝试)或访问令牌已经过期。这最终意味着在客户端代码中承担更多的责任来管理连接建立,在断开/关闭连接时重新连接,并且牺牲了在更传统的静态凭据环境中设计的库的许多效率和便利。

最新更新