如何用Shell的jq工具替换嵌套JSON数组中的PR_DESCRIPTION内容?
使用jq替换JSON中的指定文本内容
问题背景
现有两个文件:
payload.json:包含Slack消息格式的JSON结构,其中blocks数组内有一个section元素的text.text字段值为PR_DESCRIPTION,需要替换。pr_body.txt:包含格式化的Markdown文本,需要作为替换内容填入JSON中。
payload.json内容:
{ "text":"Deployment started :rocket:", "blocks":[ { "type":"header", "text":{ "type":"plain_text", "text":":computer: Deployment release :computer:" } }, { "type":"context", "elements":[ { "type":"mrkdwn", "text":"*${{ steps.date.outputs.date }} | STAGING*" } ] }, { "type":"divider" }, { "type":"section", "text":{ "type":"mrkdwn", "text":"PR_DESCRIPTION" } }, { "type":"divider" }, { "type":"actions", "elements":[ { "type":"button", "text":{ "type":"plain_text", "text":"🚰 Pipeline" }, "url":"${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}" } ] } ], "attachments":[ { "color":"warning", "fields":[ { "title":"Statut", "short":true, "value":"Deploying ..." } ] } ] }
pr_body.txt内容:
### TITLE **bold text** - qsqds - qsdqds - qsdqsd - qsdqsd 1. qsdqsd 2. qsdqsd 3. qsdqsd 4. qsdqsd `some code here`
需求:用jq工具将payload.json中的PR_DESCRIPTION替换为pr_body.txt的格式化文本,优先使用Shell命令实现。
解决方法
可以通过jq的字符串处理和数组遍历功能实现,步骤如下:
1. 处理文本内容为JSON兼容格式
先将pr_body.txt的内容读取并转义为符合JSON规范的字符串(自动处理换行、双引号等特殊字符):
PR_BODY=$(jq -Rs . pr_body.txt)
-R:读取原始字符串,不解析为JSON-s:将所有输入行合并为单一字符串.:输出处理后的字符串
2. 更新JSON文件
使用jq遍历blocks数组,匹配目标元素并替换内容:
jq --arg pr_body "$PR_BODY" ' .blocks |= map( if .type == "section" and .text.text == "PR_DESCRIPTION" then .text.text = $pr_body else . end ) ' payload.json > updated_payload.json
--arg pr_body "$PR_BODY":将处理后的文本内容作为变量传入jq.blocks |= map(...):对blocks数组进行映射遍历,匹配到类型为section且text.text为PR_DESCRIPTION的元素时,替换其text.text值为变量内容,其余元素保持不变- 结果输出到
updated_payload.json,保留原文件
简化版(直接覆盖原文件)
如果你的jq版本支持-i(原地编辑)选项,可以直接修改原文件:
PR_BODY=$(jq -Rs . pr_body.txt) jq -i --arg pr_body "$PR_BODY" ' .blocks |= map( if .type == "section" and .text.text == "PR_DESCRIPTION" then .text.text = $pr_body else . end ) ' payload.json
内容的提问来源于stack exchange,提问作者Howins
相关产品推荐
相关产品推荐

