Ansible json_query正在为字典值添加额外的字符

时间:2017-06-29 19:11:16

标签: amazon-web-services ansible amazon-iam ansible-2.x

我遇到了一个与ansible有关的奇怪问题,我确信这只是因为我缺乏经验,因为我对ansible相对较新(我只用了几个星期)

因此,简而言之,我要做的是使用命令模块运行AWS CLI命令以列出用户的AWS访问密钥,然后从该用户删除它们。我使用CLI而不是iam模块的原因是因为我认为IAM模块在删除访问密钥方面存在错误。即使我指定了状态更新和访问密钥以删除和访问密钥状态删除它仍然不会删除访问密钥,或者当我将访问密钥状态设置为非活动时使它们处于非活动状态。

第一个任务列出给定用户的访问键并注册输出:

- name: List the access keys (if any) of the user(s) we just created
  vars:
    use_key: "{{ enable_access_keys }}"
  command: "aws iam list-access-keys --user-name {{ item }}"
  with_items:
    - "{{ iam_user_name_list }}"
  when: not use_key
  register: list_key_output

^请记住,iam_user_name_list目前只包含1个用户,这就是我按照我的方式访问结果的原因。我知道将来需要改变。

由于list_key_output的stdout看起来像这样

    "stdout": "{\n    \"AccessKeyMetadata\": [\n        {\n            \"UserName\": \"other-guy\", \n            \"Status\": \"Active\", \n            \"CreateDate\": \"2017-06-29T18:45:04Z\", \n            \"AccessKeyId\": \"removed\"\n        }\n    ]\n}",

我调试msg stdout并将其注册到变量test以给它正确的json格式而没有斜线和换行符所以我可以使用json_query从stdout获取密钥。我正在使用json查询,因为无论出于何种原因,AccessKeyId都不会被识别为AccessKeyMetadata字典的键。

- name: list keys stdout
  debug:
    msg: "{{ list_key_output.results[0].stdout }}"
  register: test

- name: test variable output
  debug:
    msg: "{{ test.msg.AccessKeyMetadata | json_query('[].AccessKeyId') }}"

此时,我已成功从stdout

获取访问密钥
ok: [127.0.0.1] => {
    "changed": false,
    "msg": [
        "correct access key here"
    ]
}

现在,我将访问密钥提供给delete CLI命令,如此

- name: Remove any access keys our new console user might have
  vars:
    use_key: "{{ enable_access_keys }}"
  command: "aws iam delete-access-key --access-key {{ test.msg.AccessKeyMetadata | json_query('[].AccessKeyId') }} --user-name other-guy"
  when: not use_key
  register: delete_key_output

由于提供了无效的访问密钥,此任务失败。

fatal: [127.0.0.1]: FAILED! => {"changed": true, "cmd": ["aws", "iam", "delete-access-key", "--access-key", "[u********************]", "--user-name", "other-guy"], "delta": "0:00:00.388902", "end": "2017-06-29 18:59:13.308230", "failed": true, "rc": 255, "start": "2017-06-29 18:59:12.919328", "stderr": "\nAn error occurred (ValidationError) when calling the DeleteAccessKey operation: The specified value for accessKeyId is invalid. It must contain only alphanumeric characters.", "stderr_lines": ["", "An error occurred (ValidationError) when calling the DeleteAccessKey operation: The specified value for accessKeyId is invalid. It must contain only alphanumeric characters."], "stdout": "", "stdout_lines": []}

正如您所看到的,当我将访问密钥传递给命令时,[u被添加到访问密钥的前面,并且]被附加到它的后面。

为什么会这样?如果没有将3个字符添加到访问密钥使其无效,我怎样才能实现我的目标?我不明白为什么会发生这种情况,因为当我按照我向命令提供的方式调试msg访问密钥时,它只显示没有[u在前面和后面]的访问密钥。

很抱歉很长的帖子,但我觉得我真的必须描述一下能够在这里获得帮助的情况。提前感谢您的任何答案!

1 个答案:

答案 0 :(得分:0)

回答您的确切问题:

ok: [127.0.0.1] => {
    "changed": false,
    "msg": [
        "correct access key here"
    ]
}

请注意[中的]msg - 这意味着您打印的列表包含一个元素 - correct access key here字符串。

当您尝试将列表转换为字符串时,您可以获得它的Python解释[u'correct access key here']

您需要获取列表的第一个元素:

{{ test.msg.AccessKeyMetadata | json_query('[].AccessKeyId') | first }}

P.S。但是从我的角度来看,你走错了路。尝试使用iam模块解决您的问题。