非標準Jsonを解析する方法は?

非標準Jsonを解析する方法は?

データを取得するために使用しますcurl。出力はJson出力ですが、標準ではありません。試してみましたが、空のjq出力が表示されます。たとえば、

この出力からすべてのIDを抽出して配列に保存したいと思います。

  {"jsonrpc":"3","result":[{"hostid":"16729"},{"hostid":"16736"},{"hostid":"16731"},{"hostid":"16732"},{"hostid":"16733"},{"hostid":"16734"},{"hostid":"16735"},{"hostid":"16736"},{"hostid":"16738"},{"hostid":"16739"},{"hostid":"16746"},{"hostid":"16741"},{"hostid":"16742"},{"hostid":"16743"},{"hostid":"16744"},{"hostid":"16745"},{"hostid":"16746"},{"hostid":"16747"},{"hostid":"16748"},{"hostid":"16749"},{"hostid":"16756"},{"hostid":"16751"},{"hostid":"16752"},{"hostid":"16753"},{"hostid":"16754"},{"hostid":"16755"},{"hostid":"16756"},{"hostid":"16757"},{"hostid":"16758"},{"hostid":"16759"},{"hostid":"16766"},{"hostid":"16761"},{"hostid":"16762"},{"hostid":"16763"},{"hostid":"16764"},{"hostid":"16765"},{"hostid":"16766"},{"hostid":"16767"},{"hostid":"16768"},{"hostid":"16769"},{"hostid":"16776"},{"hostid":"16771"},{"hostid":"16772"},{"hostid":"16773"},{"hostid":"16774"},{"hostid":"16775"},{"hostid":"16776"},{"hostid":"16777"},{"hostid":"16778"},{"hostid":"16779"},{"hostid":"16786"},{"hostid":"16781"},{"hostid":"16782"},{"hostid":"16783"},{"hostid":"16784"},{"hostid":"16785"},{"hostid":"16786"},{"hostid":"16787"},{"hostid":"16788"},{"hostid":"16789"},{"hostid":"16796"},{"hostid":"16791"},{"hostid":"16792"},{"hostid":"16793"},{"hostid":"16794"},{"hostid":"16795"},{"hostid":"16796"},{"hostid":"16797"},{"hostid":"16798"},{"hostid":"16799"},{"hostid":"16866"},{"hostid":"16861"},{"hostid":"16862"},{"hostid":"16863"},{"hostid":"16864"},{"hostid":"16865"},{"hostid":"16866"},{"hostid":"16867"},{"hostid":"16868"},{"hostid":"16869"},{"hostid":"16816"},{"hostid":"16811"},{"hostid":"16812"},{"hostid":"16813"},{"hostid":"16814"},{"hostid":"16815"},{"hostid":"16816"},{"hostid":"16817"},{"hostid":"16818"},{"hostid":"16819"},{"hostid":"16826"},{"hostid":"16821"},{"hostid":"16825"},{"hostid":"16826"},{"hostid":"16827"},{"hostid":"16828"},{"hostid":"16829"},{"hostid":"16836"},{"hostid":"16831"},{"hostid":"11572"},{"hostid":"11573"},{"hostid":"11575"},{"hostid":"11576"},{"hostid":"11586"},{"hostid":"11629"},{"hostid":"11636"},{"hostid":"11632"},{"hostid":"11634"},{"hostid":"11736"},{"hostid":"11737"}],"id":1}  

次のような結果を期待しています。

  ( 16732 16733 ... 11737 )  

Pythonを使用しても正しい結果が得られません。続けてjsonrpcを返します。たとえば、

この出力からIP値を抽出したいです。

  {"jsonrpc":"3","result":[{"interfaceid":"400","hostid":"16796","main":"3","type":"3","useip":"3","ip":"192.168.23.43","dns":"","port":"100","details":[]}],"id":1}

これは長い連結文字列にすぎません。または、他のコマンドを使用して目的のsed効果を得る方法はありますかawk

答え1

JSONドキュメントには非標準的な内容はありません。どちらも完全に有効で正しい形式のJSON文書であり、JSON対応ライブラリまたはコマンドラインツールを使用してクエリできます。ここの例ではjqコマンドラインを使用しています。

jqすべての値を配列hostidに保存するには:bash

readarray -t hostid_values < <( jq -r '.result[].hostid' file.json )

これにより、hostidJSONドキュメントの配列からすべての値を抽出して読み込みます。配列内の既存の値はすべて削除されます。resulthostid_valuesbash

同様に、2番目のJSONドキュメントの値をip配列ip_valuesとして読み込みますbash

readarray -t ip_values < <( jq -r '.result[].ip' file.json )

どちらのシェルコードも、値に新しい行またはnullが含まれていないと仮定します。


値に改行文字を挿入したら、次のことを試すことができます。

unset -v hostid_values
eval "$( jq -r '@sh "hostid_values+=( \(.result[].hostid | tonumber) )"' file.json )"

jqこれは配列の割り当てステートメントを作成するために使用されますhostid_values。その後、シェルはこれらのディレクティブを評価します。このtonumber呼び出しは、数値を含む文字列の代わりにコマンド配列を送信し、悪意のある文書がスクリプトにコードを挿入できないようにします(この場合はエラーが発生します)。

ip2番目の文書の値も同じです。

unset -v hostid_values
eval "$( jq -r '@sh "ip_values+=( \(.result[].ip | tostring) )"' file.json )"

答え2

データを含む配列を作成するには、sed次のコマンドを試してください。

array=($(sed 's/{"hostid":"\([0-9]*\)"},/\1 /g;s/{.*\[//;s/{.*:"\(.*\)"}/\1/;s/\].*//' input_file))

IPを抽出するには、以下を試してください。sed

ip=$(sed 's/.*"ip":"\(.[^"]*\).*/\1/' iput_file)

出力

echo ${array[@]}
16729 16736 16731 16732 16733 16734 16735 16736 16738 16739 16746 16741 16742 16743 16744 16745 16746 16747 16748 16749 16756 16751 16752 16753 16754 16755 16756 16757 16758 16759 16766 16761 16762 16763 16764 16765 16766 16767 16768 16769 16776 16771 16772 16773 16774 16775 16776 16777 16778 16779 16786 16781 16782 16783 16784 16785 16786 16787 16788 16789 16796 16791 16792 16793 16794 16795 16796 16797 16798 16799 16866 16861 16862 16863 16864 16865 16866 16867 16868 16869 16816 16811 16812 16813 16814 16815 16816 16817 16818 16819 16826 16821 16825 16826 16827 16828 16829 16836 16831 11572 11573 11575 11576 11586 11629 11636 11632 11634 11736 11737
$ echo $ip
192.168.23.43

関連情報