我正在尝试使用jq解析 JSON(oc process ...实际上是 OpenShift命令的输出),并使用新的键/值对添加/更新 a的env数组container。
样本输入:
{
"kind": "List",
"apiVersion": "v1",
"metadata": {},
"items": [
{
"apiVersion": "v1",
"kind": "Service",
"metadata": {
"annotations": {
"description": "Exposes and load balances the node.js application pods"
},
"name": "myapp-web"
},
"spec": {
"ports": [
{
"name": "web",
"port": 3000,
"protocol": "TCP",
"targetPort": 3000
}
],
"selector": {
"name": "myapp"
}
}
},
{
"apiVersion": "v1",
"kind": "Route",
"metadata": {
"name": "myapp-web"
},
"spec": {
"host": "app.internal.io",
"port": {
"targetPort": "web"
},
"to": {
"kind": "Service",
"name": "myapp-web"
}
}
},
{
"apiVersion": "v1",
"kind": "DeploymentConfig",
"metadata": {
"annotations": {
"description": "Defines how to deploy the application server"
},
"name": "myapp"
},
"spec": {
"replicas": 1,
"selector": {
"name": "myapp"
},
"strategy": {
"type": "Rolling"
},
"template": {
"metadata": {
"labels": {
"name": "myapp"
},
"name": "myapp"
},
"spec": {
"containers": [
{
"env": [
{
"name": "A_ENV",
"value": "a-value"
}
],
"image": "node",
"name": "myapp-node",
"ports": [
{
"containerPort": 3000,
"name": "app",
"protocol": "TCP"
}
]
}
]
}
},
"triggers": [
{
"type": "ConfigChange"
}
]
}
}
]
}
Run Code Online (Sandbox Code Playgroud)
在这个 JSON 中,我想执行以下操作:
DeploymentConfig对象env在第一个容器中有数组{"name": "B_ENV", "value": "b-value"}在其中添加一个新对象env 阵列,与对象{"name": "B_ENV", "value": "b-value"}在它到目前为止,我能够解决其中的一部分,在那里我能够找到相关的对象,并将新的 env var 添加到容器中:
{
"kind": "List",
"apiVersion": "v1",
"metadata": {},
"items": [
{
"apiVersion": "v1",
"kind": "Service",
"metadata": {
"annotations": {
"description": "Exposes and load balances the node.js application pods"
},
"name": "myapp-web"
},
"spec": {
"ports": [
{
"name": "web",
"port": 3000,
"protocol": "TCP",
"targetPort": 3000
}
],
"selector": {
"name": "myapp"
}
}
},
{
"apiVersion": "v1",
"kind": "Route",
"metadata": {
"name": "myapp-web"
},
"spec": {
"host": "app.internal.io",
"port": {
"targetPort": "web"
},
"to": {
"kind": "Service",
"name": "myapp-web"
}
}
},
{
"apiVersion": "v1",
"kind": "DeploymentConfig",
"metadata": {
"annotations": {
"description": "Defines how to deploy the application server"
},
"name": "myapp"
},
"spec": {
"replicas": 1,
"selector": {
"name": "myapp"
},
"strategy": {
"type": "Rolling"
},
"template": {
"metadata": {
"labels": {
"name": "myapp"
},
"name": "myapp"
},
"spec": {
"containers": [
{
"env": [
{
"name": "A_ENV",
"value": "a-value"
}
],
"image": "node",
"name": "myapp-node",
"ports": [
{
"containerPort": 3000,
"name": "app",
"protocol": "TCP"
}
]
}
]
}
},
"triggers": [
{
"type": "ConfigChange"
}
]
}
}
]
}
Run Code Online (Sandbox Code Playgroud)
这能够按预期插入新的 env var,但输出是一个数组,如下所示。此外,它不处理env数组可能根本不存在的部分。
我希望能够产生与输入相同的输出,但添加了新的 env var。
示例输出:
[
{
"apiVersion": "v1",
"kind": "Service",
"metadata": {
"annotations": {
"description": "Exposes and load balances the node.js application pods"
},
"name": "myapp-web"
},
"spec": {
"ports": [
{
"name": "web",
"port": 3000,
"protocol": "TCP",
"targetPort": 3000
}
],
"selector": {
"name": "myapp"
}
}
},
{
"apiVersion": "v1",
"kind": "Route",
"metadata": {
"name": "myapp-web"
},
"spec": {
"host": "app.internal.io",
"port": {
"targetPort": "web"
},
"to": {
"kind": "Service",
"name": "myapp-web"
}
}
},
{
"apiVersion": "v1",
"kind": "DeploymentConfig",
"metadata": {
"annotations": {
"description": "Defines how to deploy the application server"
},
"name": "myapp"
},
"spec": {
"replicas": 1,
"selector": {
"name": "myapp"
},
"strategy": {
"type": "Rolling"
},
"template": {
"metadata": {
"labels": {
"name": "myapp"
},
"name": "myapp"
},
"spec": {
"containers": [
{
"env": [
{
"name": "A_ENV",
"value": "a-value"
},
{
"name": "B_ENV",
"value": "b-value"
}
],
"image": "node",
"name": "myapp-node",
"ports": [
{
"containerPort": 3000,
"name": "app",
"protocol": "TCP"
}
]
}
]
}
},
"triggers": [
{
"type": "ConfigChange"
}
]
}
}
]
Run Code Online (Sandbox Code Playgroud)
这是可行的,还是与jq.
编辑 1:
我刚刚意识到env数组的条件添加/更新已经由|=语法处理了!所以,我基本上只需要能够获得与输入相同的结构,并在相关数组中添加相关的 env var。
您几乎拥有它,但您需要重新构建过滤器以保留完整结果。您要确保没有任何过滤器更改上下文。通过从 开始.items,您将它从根对象更改为items数组。这本身并不是什么大问题,但你用它做什么很重要。请记住,由于应用了更改,分配/更新会保留原始上下文。因此,如果您根据更新编写过滤器,它将对您有用。
为此,您需要找到项目中env第一个容器的数组DeploymentConfig。首先让我们发现:
.items[] | select(.kind == "DeploymentConfig").spec.template.spec.containers[0].env
Run Code Online (Sandbox Code Playgroud)
您不需要在错误处理方面做任何其他事情,因为它select不会产生任何结果。从那里,您只需要通过添加新值来更新数组。
(.items[] | select(.kind == "DeploymentConfig").spec.template.spec.containers[0].env) +=
[{name:"B_ENV",value:"b-value"}]
Run Code Online (Sandbox Code Playgroud)
如果数组存在,它将添加新项目。如果没有,它将创建一个新env数组。如果env不是数组,那将是一个不同的问题。
| 归档时间: |
|
| 查看次数: |
3823 次 |
| 最近记录: |