首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Ansible中的多重json_query?

Ansible中的多重json_query?
EN

Stack Overflow用户
提问于 2020-05-05 08:37:19
回答 1查看 1.8K关注 0票数 2

我有下面的yaml文件。

代码语言:javascript
复制
resources:
  - apiVersion: v1
    kind: Deployment
    metadata:
      labels:
        app: test
      name: test-cluster-operator
      namespace: destiny001
    spec:
      selector:
        matchLabels:
          name: test-cluster-operator
          test.io/kind: cluster-operator
      strategy:
        type: Recreate
      template:
        metadata:
          labels:
            name: test-cluster-operator
            test.io/kind: cluster-operator
        spec:
          containers:
          - args:
            - /path/test/bin/cluster_operator_run.sh
            env:
            - name: MY_NAMESPACE
              valueFrom:
                fieldRef:
                  apiVersion: v1
                  fieldPath: metadata.namespace
            imagePullPolicy: IfNotPresent
            livenessProbe:
              failureThreshold: 3
              httpGet:
                path: /healthy
                port: 8080
                scheme: HTTP
              initialDelaySeconds: 10
              periodSeconds: 30
              successThreshold: 1
              timeoutSeconds: 1
            name: test-cluster-operator
            readinessProbe:
              failureThreshold: 3
              httpGet:
                path: /ready
                port: 8080
                scheme: HTTP
              initialDelaySeconds: 10
              periodSeconds: 30
              successThreshold: 1
              timeoutSeconds: 1
            resources:
              limits:
                cpu: '1'
                memory: 256Mi
              requests:
                cpu: 200m
                memory: 256Mi
            terminationMessagePath: /dev/termination-log
            terminationMessagePolicy: File
            volumeMounts:
            - mountPath: /var/data
              name: data-cluster-operator
          dnsPolicy: ClusterFirst
          restartPolicy: Always
          schedulerName: default-scheduler
          securityContext: {}
          serviceAccount: test-cluster-operator
          serviceAccountName: test-cluster-operator
          terminationGracePeriodSeconds: 30
          volumes:
          - name: data-cluster-operator
            persistentVolumeClaim:
              claimName: data-cluster-operator

我正在尝试获取名为MY_NAMESPACE的env变量的值。这就是我在Ansible中尝试到env树路径的方法。

代码语言:javascript
复制
- name: "set test fact"
  set_fact:
    myresult: "{{ yaml_file_variable | json_query(\"resources[?metadata.name=='test-cluster-operator'].spec.template.spec\") | json_query(\"containers[?name=='test-cluster-operator'].env\") }}"

- name: "debug"
  debug:
    msg: "{{ myresult }}"

这会产生一个空列表,但是第一个json_query工作得很好。

在这种情况下,如何正确使用json_query?我只需要一个json_query就能实现这一点吗?

编辑:--我似乎更接近解决方案,但结果是列出了一个列表,而不是字符串,我觉得这很烦人。

代码语言:javascript
复制
- name: "set test fact"
  set_fact:
    myresult: "{{ yaml_file_variable | json_query(\"resources[?metadata.name=='test-cluster-operator'].spec.template.spec\") | json_query(\"[].containers[?name=='test-cluster-operator']\") | json_query(\"[].env[?name=='MY_NAMESPACE'].name\") }}"

这将打印- - MY_NAMESPACE,而不仅仅是MY_NAMESPACE

我每次在first之后都要使用json_query过滤器吗?我确信只有一个containers元素。我不明白为什么json_query会返回一个列表。

这终于起作用了,但不知道这样做是否正确。

代码语言:javascript
复制
- name: "set test fact"
  set_fact:
    myresult: "{{ yaml_file_variable | json_query(\"resources[?metadata.name=='test-cluster-operator'].spec.template.spec\") | first | json_query(\"containers[?name=='test-cluster-operator']\") | first | json_query(\"env[?name=='MY_NAMESPACE'].valueFrom \") | first }}"
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2020-05-05 12:12:23

json_query使用jmespath,jmespath总是返回一个列表。这就是为什么第一个例子不起作用的原因。第一个查询返回一个列表,第二个查询试图查询一个键。您在第二次使用[].时已经更正了这一点

您还缺少jmespath管道表达式:|,它的使用与您预期的差不多--第一个查询的结果可以管道到一个新的查询中。请注意,这与使用相同字符的ansible过滤器是分开的。

此查询:

代码语言:javascript
复制
resources[?metadata.name=='test-cluster-operator'].spec.template.spec | [].containers[?name=='test-cluster-operator'][].env[].valueFrom

应该为您提供以下输出:

代码语言:javascript
复制
[
  {
    "fieldRef": {
      "apiVersion": "v1",
      "fieldPath": "metadata.namespace"
    }
  }
]

您的任务应该如下所示:

代码语言:javascript
复制
- name: "set test fact"
  set_fact:
    myresult: "{{ yaml_file_variable | json_query(\"resources[?metadata.name=='test-cluster-operator'].spec.template.spec | [].containers[?name=='test-cluster-operator'][].env[].valueFrom\") | first }}"

要回答你的另一个问题,是的,你需要first过滤器。如前所述,jmespath将始终返回一个列表,因此,如果您只想要一个键的值,则需要将其提取出来。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/61609051

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档