打印不带ansible_host的对象

时间:2019-05-07 14:21:37

标签: jq ansible-inventory

我正在尝试使用jq处理来自VMware Ansible清单模块的JSON,以便生成未定义ansible_host的对象(VM)列表。

我能得到的最接近的是:

{
  "config.cpuHotAddEnabled": true,
  "config.cpuHotRemoveEnabled": false,
  "config.hardware.numCPU": 1,
  "config.instanceUuid": "500e4e98-50ec-a3a7-9d45-b0ac36c2d192",
  "config.name": "tu-openldap-01",
  "config.template": false,
  "guest.guestId": "rhel6_64Guest",
  "guest.guestState": "notRunning",
  "guest.hostName": "tu-openldap-01",
  "guest.ipAddress": null,
  "name": "tu-openldap-01",
  "runtime.maxMemoryUsage": 2048
}
{
  "config.cpuHotAddEnabled": true,
  "config.cpuHotRemoveEnabled": false,
  "config.hardware.numCPU": 1,
  "config.instanceUuid": "500efaa5-baac-163b-65c0-7ed2a19f1d7d",
  "config.name": "tu1vcm7tst2001",
  "config.template": false,
  "guest.guestId": "rhel7_64Guest",
  "guest.guestState": "running",
  "guest.hostName": "rhel7-template",
  "guest.ipAddress": null,
  "name": "tu1vcm7tst2001",
  "runtime.maxMemoryUsage": 4096
}

使用以下内容:

jq '._meta.hostvars[] | select(.ansible_host | not)' prod-inventory_201905070920.json

这几乎是我想要的,但是问题是如何打印这些以及对象本身的键?

如果我这样做:

jq '._meta.hostvars | select(.ansible_host | not)' prod-inventory_201905070920.json

我得到这些:

"tw1pttest1001_420e92f4-453e-1267-4331-d6253d771882": {
    "ansible_host": "<omitted>",
    "config.cpuHotAddEnabled": true,
    "config.cpuHotRemoveEnabled": false,
    "config.hardware.numCPU": 2,
    "config.instanceUuid": "500ef630-16c1-cb91-be9c-e9e667b551d9",
    "config.name": "tw1pttest1001",
    "config.template": false,
    "guest.guestId": "windows9Server64Guest",
    "guest.guestState": "running",
    "guest.hostName": "<omitted>",
    "guest.ipAddress": "<omitted>",
    "name": "tw1pttest1001",
    "runtime.maxMemoryUsage": 49152
  },
  "tw1swsrm1001_420e18d2-0c96-0df5-e6c7-1ff8fc070cdb": {
    "ansible_host": "<omitted>",
    "config.cpuHotAddEnabled": true,
    "config.cpuHotRemoveEnabled": false,
    "config.hardware.numCPU": 4,
    "config.instanceUuid": "500e231d-1eda-4e66-3f4a-8c68392a70b5",
    "config.name": "tw1swsrm1001",
    "config.template": false,
    "guest.guestId": "windows9Server64Guest",
    "guest.guestState": "running",
    "guest.hostName": "<omitted>",
    "guest.ipAddress": "<omitted>",
    "name": "tw1swsrm1001",
    "runtime.maxMemoryUsage": 16384
  },

有什么建议吗?我觉得这很简单,我很想念。

2 个答案:

答案 0 :(得分:0)

如果您愿意考虑替代方案,请使用基于walk-path的Unix实用程序 jtc

***我从您展示的那两段中自由地编译了源JSON示例:

bash $ <prod-inventory_201905070920.json jtc -w'<ansible_host>l: [-1]' -p
{
   "tw1pttest1001_420e92f4-453e-1267-4331-6d52d3778128": {
      "config.cpuHotAddEnabled": true,
      "config.cpuHotRemoveEnabled": false,
      "config.hardware.numCPU": 1,
      "config.instanceUuid": "500e4e98-50ec-a3a7-9d45-b0ac36c2d192",
      "config.name": "tu-openldap-01",
      "config.template": false,
      "guest.guestId": "rhel6_64Guest",
      "guest.guestState": "notRunning",
      "guest.hostName": "tu-openldap-01",
      "guest.ipAddress": null,
      "name": "tu-openldap-01",
      "runtime.maxMemoryUsage": 2048
   },
   "tw1swsrm1001_420e18d2-0c96-0df5-e6c7-f18fcf700dcb": {
      "config.cpuHotAddEnabled": true,
      "config.cpuHotRemoveEnabled": false,
      "config.hardware.numCPU": 1,
      "config.instanceUuid": "500efaa5-baac-163b-65c0-7ed2a19f1d7d",
      "config.name": "tu1vcm7tst2001",
      "config.template": false,
      "guest.guestId": "rhel7_64Guest",
      "guest.guestState": "running",
      "guest.hostName": "rhel7-template",
      "guest.ipAddress": null,
      "name": "tu1vcm7tst2001",
      "runtime.maxMemoryUsage": 4096
   }
}
bash $ 

弄清步行路径(-w

  • <ansible_host>l:-将找到所有带有标签ansible_host的JSON值
  • [-1]将为每个找到的标签选择一个父JSON元素,从而有效地选择包含标签ansible_host的整个记录​​

-p将清除所有找到的记录,从而仅将那些没有包含ansible_host记录的记录保留给源JSON

PS>披露:我是jtc工具的创建者

答案 1 :(得分:0)

假设您要搜索在._meta.hostvars对象中找到的项目,则可以使用诸如with_entries/1之类的键/值来过滤对象。

$ jq '._meta.hostvars | with_entries(select(.value.ansible_host | not))
' prod-inventory_201905070920.json

这实际上将采用hostvars对象,并且仅保留符合该条件的属性(不具有ansible_host属性值)。