Обновите строковое поле JSON в yaml, используя yq

Есть файл sample.yaml

---
action: "want-to-update"
foo: |-
    {
        "a" : "actual A",
        "b" : "actual B",
        "c" : "actual C"
    }
---
action: "dont-want-to-update"
foo: |-
.
.
.

Необходимо обновить значение в поле a с actual a на updated a

Пытался обновить с помощью yq и jq

yq 'select(.action == "want-to-update").foo' sample.yaml | jq '.a = "updated a" | tostring' | xargs -0 -n1 -I{} yq 'select(.action == "want-to-update").foo = {}' -i sample.yaml

Получение вывода, как показано ниже:

---
action: "want-to-update"
foo: |-
  {"a":"updated a","b":"actual B","c":"actual C"}
---
.
.

Но я хочу более красивую версию выше:

---
action: "want-to-update"
foo: |-
    {
        "a" : "updated A",
        "b" : "actual B",
        "c" : "actual C"
    }
---
Шаблоны Angular PrimeNg
Шаблоны Angular PrimeNg
Как привнести проверку типов в наши шаблоны Angular, использующие компоненты библиотеки PrimeNg, и настроить их отображение с помощью встроенной...
Создайте ползком, похожим на звездные войны, с помощью CSS и Javascript
Создайте ползком, похожим на звездные войны, с помощью CSS и Javascript
Если вы веб-разработчик (или хотите им стать), то вы наверняка гик и вам нравятся "Звездные войны". А как бы вы хотели, чтобы фоном для вашего...
Документирование API с помощью Swagger на Springboot
Документирование API с помощью Swagger на Springboot
В предыдущей статье мы уже узнали, как создать Rest API с помощью Springboot и MySql .
Начала с розового дизайна
Начала с розового дизайна
Pink Design - это система дизайна Appwrite с открытым исходным кодом для создания последовательных и многократно используемых пользовательских...
Шлюз в PHP
Шлюз в PHP
API-шлюз (AG) - это сервер, который действует как единая точка входа для набора микросервисов.
14 Задание: Типы данных и структуры данных Python для DevOps
14 Задание: Типы данных и структуры данных Python для DevOps
проверить тип данных используемой переменной, мы можем просто написать: your_variable=100
1
0
53
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

В общем, удалить tostring

json=$(
    yq 'select(.action == "want-to-update").foo' sample.yaml \
    | jq '.a = "updated a"'
)
escaped_quotes=${json//\"/\\\"}
yq 'select(.action == "want-to-update").foo = "'"${escaped_quotes}"'"' sample.yaml
---
action: "want-to-update"
foo: |-
  {
    "a": "updated a",
    "b": "actual B",
    "c": "actual C"
  }

---
action: "dont-want-to-update"
foo: |-
  "ok"

Ответ принят как подходящий

Используя fromjson и tojson, вы можете декодировать и кодировать JSON на лету, поэтому все это можно сделать всего одним вызовом yq (без jq и подстановки команд не требуется):

yq -i 'select(.action == "want-to-update").foo |= (
  fromjson | .a = "updated a" | tojson
)' sample.yaml

Примечание. Чтобы получить это одноразовое решение с компактным форматированием данных JSON, замените tojson на @json (а для эстетической симметрии также fromjson на @jsond).

pmf 18.11.2022 20:07

Примечание № 2: tojson также принимает размер отступа в качестве параметра, поэтому, возможно, tojson(4) будет лучше соответствовать исходному форматированию данных JSON.

pmf 18.11.2022 20:18

Другие вопросы по теме