Я хотел бы добавить несколько пар ключ: значение в существующую строку JSON. Значения передаются в мой скрипт в качестве аргументов командной строки.
Пока что у меня есть это
data='{"update": { "labels": [] } }'
for label in "${@}";do
objJSON=$(printf '%s\n' "{ "add": ${label} }" | jq -R . | jq -s .)
data=$(echo ${data} | jq --argjson jsonString "$objJSON" '.update.labels += $jsonString')
done
echo ${data} >output.txt
jq --color-output . output.txt
Мой вывод таков:
{
"update": {
"labels": [
"{ add: value1 }",
"{ add: value2 }"
]
}
}
но я пытаюсь получить это (обратите внимание на кавычки вокруг add и каждого значения):
{
"update": {
"labels": [
{ "add": "value1" },
{ "add": "value2" }
]
}
}
Я не понимаю, где я ошибаюсь. Может кто-нибудь помочь, пожалуйста?



Поскольку ваш ключ add статический, я бы передал value только того элемента, который вы хотите добавить, используя правильный ключ в качестве varibale.
Тогда вы можете добавить его, выполнив .. |= { $add }
:
jq --arg add "labelValue" '.update.labels |= { $add }' <<< "$data"
Почему бы не сделать все за один вызов jq, используя --args "$@" для передачи всех аргументов в jq и массив $ARGS.positional для ссылки на них:
#!/bin/bash
data='{"update": { "labels": [] } }'
jq '.update.labels += [{add: $ARGS.positional[]}]' --args "$@" <<< "$data" > output.json
Или, если вы позволите jq также сгенерировать исходный документ, на самом деле это всего лишь один вызов:
#!/bin/sh
jq -n '.update.labels = [{add: $ARGS.positional[]}]' --args "$@" > output.json
Обязательно экранируйте кавычки ключ/значение:
for label in "$@"; do
objJSON=$(echo "{ \"add\": \"$label\" }" | jq -c .)
### escape here-^----^---^-------^ compact-^
data=$(echo "$data" | jq --argjson jsonString "$objJSON" '.update.labels += [$jsonString]')
done
Вот скрипт Bash, который обрабатывает добавление новых объектов в массив меток обновлений.
#!/usr/bin/env bash
DEFAULT_OUTPUT_FILENAME=output.txt
# Function to display help
show_help() {
echo "Usage: $(basename "$0") [options] [label1] [label2] ... [labelN]"
echo
echo "This script takes key-value pair arguments and adds them to a JSON document."
echo
echo "Options:"
echo " -i, --input FILE Input JSON file to append labels to (default: ${DEFAULT_OUTPUT_FILENAME})."
echo " -o, --output FILE Output to FILE instead of ${DEFAULT_OUTPUT_FILENAME}."
echo " -h, --help Display this help message."
echo
echo "Arguments:"
echo " labelN The key-value pair to add to the JSON document."
echo
echo "Example:"
echo " $(basename "$0") \"label1\" \"label2\" \"label3\""
echo " $(basename "$0") -i existing.json -o updated.json \"label1\" \"label2\""
}
# Initialize variables
input_file=${DEFAULT_OUTPUT_FILENAME}
output_file=${DEFAULT_OUTPUT_FILENAME}
# Parse options
while [[ "$1" == -* ]]; do
case "$1" in
-i|--input)
input_file = "$2"
shift 2
;;
-o|--output)
output_file = "$2"
shift 2
;;
-h|--help)
show_help
exit 0
;;
*)
echo "Unknown option: $1"
show_help
exit 1
;;
esac
done
# Ensure at least one label is provided
if [[ $# -eq 0 ]]; then
echo "No labels provided. Use -h or --help for usage information."
exit 1
fi
# Initialize JSON data
if [[ -f "$input_file" ]]; then
data=$(cat "$input_file")
else
data='{"update": { "labels": [] } }'
fi
# Iterate over the labels
for label in "$@"; do
# Create JSON object from the label
objJSON=$(echo "{ \"add\": \"$label\" }" | jq -c .)
# Append the JSON object to the labels array
data=$(echo "$data" | jq --argjson jsonString "$objJSON" '.update.labels += [$jsonString]')
done
# Output the final JSON to a file
echo "$data" > "$output_file"
# Pretty print the JSON
jq --color-output . "$output_file"
Вот использование:
[user@host ~]$ ./json_add.sh --help
Usage: json_add.sh [options] [label1] [label2] ... [labelN]
This script takes key-value pair arguments and adds them to a JSON document.
Options:
-i, --input FILE Input JSON file to append labels to (default: output.txt).
-o, --output FILE Output to FILE instead of output.txt.
-h, --help Display this help message.
Arguments:
labelN The key-value pair to add to the JSON document.
Example:
json_add.sh "label1" "label2" "label3"
json_add.sh -i existing.json -o updated.json "label1" "label2"
Re: «Я не понимаю, в чем я ошибаюсь»:
printf '%s\n' "{ "add": ${label} }"выдает что-то вроде{ add: value2 }(который не является допустимым JSON, поскольку в нем отсутствуют кавычки вокруг строк ключа и значения), который затем передаетсяjq -R, который преобразует всю строку в строку JSON, которая в конечном итоге собирается в окончательный массив. Вместо этого использованиеprintf '{ "add": "%s" }' "${label}"сохранит кавычки (но все равно будет нарушено, если$labelсодержит неэкранированные символы, поэтому лучше, чтобы jq сам кодировал любой контент в JSON, а не пытался создать его самостоятельно).