APIを介してgithub gistにデータを送信するツールを開発しようとしています。問題は、github apiがポイントを1行content
として扱い、すべてのエスケープシーケンスが次のように文字通り書き込まれることです。
{
"test.txt": {
"filename": "test.txt",
"type": "text/plain",
"language": "Shell",
"raw_url": "https://gist.githubusercontent.com/jessebutryn/5c8b2a95b4b016e2fa33edee294c732b/raw/474f72ad32c843c18e9a61a228a31df6b85a8da1/test.txt",
"size": 96,
"truncated": false,
"content": "#!/bin/sh\n\n# comment\nfunc () {\n\tfor ((i=1;i<10;i++)); do\n\t\t:\n\tdone\n}\n\nprintf '%s\\n' Foo bar baz\n"
}
}
内容は次のように表示されます。
#!/bin/sh
# comment
func () {
for ((i=1;i<10;i++)); do
:
done
}
printf '%s\n' Foo bar baz
これは次のように変換する必要があります。
#!/bin/sh\n\n# comment\nfunc () {\n\tfor ((i=1;i<10;i++)); do\n\t\t:\n\tdone\n}\n\nprintf '%s\\n' Foo bar baz\n
これを一度に実行できるツールはありますか?そうでない場合は、sed
標準のUNIXツールを使用してこれを行う方法を知っている人はいますか?
注:元のテキストのリテラルエスケープシーケンスはgithubが解釈できないようにエスケープする必要があります(ただし、この質問で解決する必要はないマイナーな問題ですが、次の場合には良いでしょう)。
つまり:
printf '%s\n' Foo bar baz
になる:
printf '%s\\n' Foo bar baz
答え1
jq -R -s '.' < datafile
datafile
これにより、すべての内容が文字列として読み取られ、jqはそれをJSON文字列として印刷します。内容をテンプレートに直接置き換えるのに適した引用文字列を提供しますdatafile
。データは、以下を含む正しいJSONによって参照されます。RFC 7159エスケープJSONは文字列リテラルが複数行にまたがることを許可しないため、およびを1つの大きな行に使用します。
テンプレートJSONファイルを使用してjq内の文書全体を組み合わせることもできます。
jq --arg f "$(cat datafile)" '.["test.txt"].content = $f' < template.json
最新バージョンには、コマンド置換を使用する代わりにファイルを文字列としてロードするオプションがjq
あります。また、を使って内容を変更することもできます。--rawfile f datafile
-R --slurp --slurpfile t template.json datafile
t["test.txt"].content = .
答え2
他のJSONに含めるには、いくつかのJSONをエスケープする必要があり、非常に簡単な解決策があります。
$ jq @json <<< '{"Hello": "World"}'
"{\"Hello\":\"World\"}"
答え3
既存のJSONドキュメントがあり、file.json
コンテンツを正しい場所に挿入したい場合はjq
、
jq --rawfile content test.txt '."test.txt".content |= $content' file.json
コンテンツをbase64でエンコードする必要がある場合:
base64 test.txt | jq --rawfile content /dev/stdin '."test.txt".content |= $content' file.json
(jo
おおよその合計出力のメタデータ)を使用して、最初からJSONを構築します。stat
file
#!/bin/sh
gist_url='some url'
filename=test.txt
jo -p "$filename"="$( jo \
filename="$filename" \
type="$( file -b --mime-type "$filename" )" \
language="$( file -b "$filename" )" \
raw_url="$gist_url" \
size="$( stat -c %s "$filename" )" \
truncated=false \
content=@"$filename" )"
Unixに基づく調整stat
とユーティリティ(上記のLinuxオプションを使用)file
出力:
{
"test.txt": {
"filename": "test.txt",
"type": "text/x-shellscript",
"language": "POSIX shell script, ASCII text executable",
"raw_url": "some url",
"size": 108,
"truncated": false,
"content": "#!/bin/sh\n\n# comment\nfunc () {\n for ((i=1;i<10;i++)); do\n :\n done\n}\n\nprintf '%s\\n' Foo bar baz"
}
}
%"$filename"
代わりに@"$filename"
キーのbase64エンコーディング値を取得するには、次のようにしますcontent
。
{
"test.txt": {
"filename": "test.txt",
"type": "text/x-shellscript",
"language": "POSIX shell script, ASCII text executable",
"raw_url": "some url",
"size": 108,
"truncated": false,
"content": "IyEvYmluL3NoCgojIGNvbW1lbnQKZnVuYyAoKSB7CiAgICBmb3IgKChpPTE7aTwxMDtpKyspKTsgZG8KICAgICAgICA6CiAgICBkb25lCn0KCnByaW50ZiAnJXNcbicgRm9vIGJhciBiYXoK"
}
}