使用jq选择的更清洁方式

时间:2018-10-29 23:41:04

标签: amazon-web-services ansible terraform jq

我的问题的背景已经载入;但是我只想关注当前文章中的jq部分(尽管如果您能提供全部帮助,将非常欢迎和赞赏)。

我有一个Terraform规范,该规范已成功应用于在AWS中创建自动缩放组(例如:Terraform Provisioning,我将在一个单独的问题上提出,也许比我正在做的更好的方法)。我曾想在每个产生的实例中运行一些配置,因此,我决定将其与ansible命令结合使用。

您可能知道,Ansible在清单/主机文件上运行。因此,每次AWS放大或缩小时,我都必须更新我的主机文件,以便成功运行以下可使用的临时命令ansible -i ./myansible.hostfile myawsinstances -a "reprovisioning_command"(它本身有一系列问题,待定)。

在创建ansible主机文件的过程中,我使用以下命令获得了所需的内容:

命令示例1

aws ec2 describe-instances | jq .Reservations[].Instances[].PublicIpAddress | sed 's/"//g' | awk '{print "inst"$1 " ansible_ssh_host="$1 " ansible_ssh_user=ubuntu"}' > myansible.hostfile

myansible.hostfile中输出样本1

inst[ip_no1] ansible_ssh_host=[ip_no1] ansible_ssh_user=ubuntu
inst[ip_no2] ansible_ssh_host=[ip_no2] ansible_ssh_user=ubuntu

在我看来,它相当长且有些令人费解。

如果我只使用jq及其字符串操作工具,例如:

命令示例2

aws ec2 describe-instances | jq '"inst" + .Reservations[].Instances[].PublicIpAddress + " ansible_ssh_hosts=" + .Reservations[].Instances[].PublicIpAddress + " ansible_ssh_user=ubuntu"' > myansible.hostfile

我会收到类似输出的重复信息:

myansible.hostfile中输出样本2

inst[ip_no1] ansible_ssh_host=[ip_no1] ansible_ssh_user=ubuntu
inst[ip_no2] ansible_ssh_host=[ip_no2] ansible_ssh_user=ubuntu
inst[ip_no1] ansible_ssh_host=[ip_no1] ansible_ssh_user=ubuntu
inst[ip_no2] ansible_ssh_host=[ip_no2] ansible_ssh_user=ubuntu

大概是因为我在同一命令中两次调用了对象选择器。 问题是:

a。 是否可以使用更简洁的命令表达式代替(命令样本1)来实现相同的效果(输出样本1)?

b。 严格地使用jq命令(如(命令样本2)中的命令)以产生所需的(输出样本1)而不像(输出样本2)那样重复的正确方法是什么?

非常感谢。

2 个答案:

答案 0 :(得分:2)

首先,jq的-r选项将从JSON字符串输出中删除最外面的引号。

第二,下面的jq过滤器(与前面提到的-r选项一起使用)应该足以实现您的目标,尽管由于没有提供MCVE而很难验证:< / p>

.Reservations[].Instances[].PublicIpAddress
| "inst" + . + " ansible_ssh_hosts=" + . + " ansible_ssh_user=ubuntu"

答案 1 :(得分:1)

我不确定您为什么要设置一个包含IP地址的Ansible库存名称,因为这对我来说似乎毫无意义,因为与使用IP相比,它没有人可读的名称或添加了任何有用的名称地址。

如果您对放弃此要求感到满意,那么实际上您可以使用query option of the AWS CLI和沟jq以及您的格式:

cat <<EOF > hosts-file.ini
[all:vars]
ansible_ssh_user=ubuntu

[all]
EOF
aws ec2 describe-instances --query 'Reservations[*].Instances[*].PublicIpAddress' --output text >> hosts-file.ini

这将在所有级别上设置一些内联var,以将SSH用户设置为ubuntu,然后在all块下转储所有EC2实例的公共IP地址。