【问题标题】:HashiCorp Vault AppRole based authentication Unwrap secret_id got permission denied基于 HashiCorp Vault AppRole 的身份验证 Unwrap secret_id 的权限被拒绝
【发布时间】:2022-12-16 12:06:37
【问题描述】:

我以这段代码为例,使用基于 App Role 的身份验证来访问 Vault。因为秘密是我想使用包装令牌来更安全

    import unittest
    from hvac import Client

    URL = "https://p.vault.myfine-company.de"
    JENKINS_TOKEN = "mylovelytoken"

    def test_ci_startup(self):

      # Jenkins authentifies with token as secure instance
      jenkins_client = Client(url=URL, token=JENKINS_TOKEN)

      # fetch the role_id and stores this somewhere in the image of the app
      resp = jenkins_client.auth.approle.read_role_id(role_name='workshop')
      role_id = resp["data"]["role_id"]

      # get a wrapped secret_id and passes this to the starting app
      result = jenkins_client.write(path='auth/approle/role/workshop/secret-id',wrap_ttl="2s")
      unwrap_token = result['wrap_info']['token']

      # No the app comes in place
      app_client = Client(url=URL) # , token=JENKINS_TOKEN)

      # unwrap the secret_id
      unwrap_response = app_client.sys.unwrap(unwrap_token) # !!! Here I get permission denied
      secret_id = unwrap_response['data']['secret_id']

      # use role_id and secret_id to login
      login_result = app_client.auth.approle.login(role_id=role_id, secret_id=secret_id)
      client_token = login_result['auth']['client_token']

      # Read the database credential
      read_response = app_client.secrets.kv.v2.read_secret_version(path='test/webapp')
      self.assertEqual("users", read_response['data']['data']['db_name'])

      return

不幸的是,当我尝试使用 app_client.sys.unwrap(unwrap_token) 解包 secret_id 时,会出现 403“权限被拒绝” 当我将 app_client-Connection 与 app_client = Client(url=URL), token=JENKINS_TOKEN) 一起使用时,一切正常。但这当然不是应该使用基于 AppRole 的身份验证的方式。所有这些都基于以下教程和最佳实践:

https://developer.hashicorp.com/vault/tutorials/recommended-patterns/pattern-approle https://developer.hashicorp.com/vault/tutorials/auth-methods/approle?in=vault%2Fauth-methods

我觉得跟政策有点关系。但是我还没有找到解决方案。

【问题讨论】:

  • 是的,客户端需要使用授权令牌展开的关联策略进行身份验证。该政策应该在您在问题底部链接的那些教程中。
  • 是的,本教程按预期工作。我可以在第一个窗口中获取一个 wrapped_token,TTL 为 10s。然后使用另一个窗口解包,获取 secret_id,将其与 role_id 一起使用以获得 VAULT_TOKEN,最后使用此令牌读取秘密。这只是我的 python 东西得到了permission denied
  • 好的,我现在看到了“拉”方法实现的问题:第一个客户端被授权解包,而不是第二个。第一个客户端解开令牌并传递给第二个客户端进行身份验证。第二个客户端根本没有经过身份验证,因此无法解包。
  • @MattSchuchard 看到我的回答。第二个客户端解包令牌并使用它来获取secret-id。在这种情况下,应用程序没有将 secret-id 存储在某处

标签: authentication hashicorp-vault


【解决方案1】:

狂欢窗口 1:

$ export VAULT_ADDR="https://p.vault.myfine-company.de"
$ export VAULT_TOKEN="my-fine-token"
$ # This creates a secret 
$ vault kv put secret/mysql/webapp db_name="users" username="admin" password="passw0rd" 
$ # this writes the policy to access the secret
$ vault policy write jenkins -<<EOF
# Read-only permission on secrets stored at 'secret/data/mysql/webapp'
path "secret/data/mysql/webapp" {
  capabilities = [ "read" ]
}
EOF

$ # This creates an approle jenkins
$ vault write auth/approle/role/jenkins token_policies="jenkins" \n    token_ttl=1h token_max_ttl=4h

$ # this reads the role-id
$ vault read auth/approle/role/jenkins/role-id
  Key        Value
  ---        -----
  role_id    fcff5e13-wonderfull-my-fine-role-id
$ This creates a wrapping token with TTL 120s 
$ vault write -wrap-ttl=120s -force auth/approle/role/jenkins/secret-id
  Key                              Value
  ---                              -----
  wrapping_token:                  hvs.wonderfull-msgiIp9nu91c1fLrcwGh4KHGh2cy5HMmw4bkh2-my-fine-wrapping-token
  wrapping_accessor:               ddXZLPFmy-fine-accessor
  wrapping_token_ttl:              2m
  wrapping_token_creation_time:    2022-11-23 12:19:46.958503493 +0000 UTC
  wrapping_token_creation_path:    auth/approle/role/jenkins/secret-id
  wrapped_accessor:                5superp-6-my-fine-wrapped-accessor

role_idwrapping_token 现在用于 bash 窗口 2:

$ # unwrap token to obtain the secret-id
$ VAULT_TOKEN=hvs.wonderfull-msgiIp9nu91c1fLrcwGh4KHGh2cy5HMmw4bkh2-my-fine-wrapping-token vault unwrap
  Key                   Value
  ---                   -----
  secret_id             ac8b3594-my-wundervolles-secret-id
  secret_id_accessor    485423my-wundervolles-secret-accessor
  secret_id_ttl         0s
$ # login to vault and get a APP_TOKEN to be used to read secrets
$ vault write auth/approle/login role_id=fcff5e13-wonderfull-my-fine-role-id secret_id=ac8b3594-my-wundervolles-secret-id
  Key                     Value
  ---                     -----
  token                   hvs.CAESIEW-so-a-nice-token-lEgXb9ZIf-my-wonderfull-token
  token_accessor          MehfK-my-wonderfull-accessor
  token_duration          1h
  token_renewable         true
  token_policies          ["default" "jenkins"]
  identity_policies       []
  policies                ["default" "jenkins"]
  token_meta_role_name    jenkins
$ export APP_TOKEN=hvs.CAESIEW-so-a-nice-token-lEgXb9ZIf-my-wonderfull-token
$ # Read a secret
$ VAULT_TOKEN=$APP_TOKEN vault kv get secret/mysql/webapp
  ====== Secret Path ======
  secret/data/mysql/webapp
  ======= Metadata =======
  Key                Value
  ---                -----
  created_time       2022-11-23T09:44:24.429733013Z
  custom_metadata    <nil>
  deletion_time      n/a
  destroyed          false
  version            1
  ====== Data ======
  Key         Value
  ---         -----
  db_name     users
  password    passw0rd
  username    admin

这个 wrapped_token 的优点是 CI 管道将这个短暂的令牌传递给应用程序。应用程序使用此令牌检索secret-id(通过解包)并与role-id一起执行登录以获取访问令牌以读取数据库机密。

解决方案 :

问题通过向 app_client = Client(url=URL) token=unwrap_token 提供 unwrap_token 来解决,如对 hvac 的仍然开放的拉取请求中所述(截至 2022 年 11 月 30 日):

import hvac

client = hvac.Client(url='https://127.0.0.1:8200')
client.token = "hvs.wonderfull-msgiIp9nu91c1fLrcwGh4KHGh2cy5HMmw4bkh2-my-fine-wrapping-token"

# When authenticating with just the wrapping token, should not pass token into unwrap call
unwrap_response = client.sys.unwrap()
print('Unwrapped approle role token secret id accessor: "%s"' % unwrap_response['data']['secret_id_accessor'])

【讨论】:

    猜你喜欢
    • 2022-11-20
    • 2019-01-21
    • 1970-01-01
    • 2017-12-15
    • 1970-01-01
    • 1970-01-01
    • 2020-09-08
    • 2014-02-02
    • 2022-08-11
    相关资源
    最近更新 更多