SQLite CSV出力をJSONに変換

SQLite CSV出力をJSONに変換

コマンドラインでSQLite出力をJSON形式でフォーマットしたいと思います。現在私のCSV出力は次のとおりです。

label1,value1
label2,value2
label3,value3
...

では、次のように書式設定したいと思います。

{'label1' : 'value1',  'label2': 'value2', ... }

ありがとうございます!

答え1

私はこれをGNUでテストしましたawksed他のバージョンでも同じかどうかはよくわかりません。

awk -F, '{printf "'\''%s'\'' : '\''%s'\'', ", $1, $2} END {print "}" }' input.csv | sed -e 's/^/{/' -e 's/, }/}/' > output.json

答え2

有効なJSONは二重引用符を使用するため、次のようになります。

awk -F, 'BEGIN{print "{"} {if (notfirst) {print ","}; print "\"" $1 "\":\"" $2 "\""; notfirst=1} END {print "\"\":\"\"}" }' input.csv

sedを使用しない方が簡単です

答え3

私たちがこれを持っているとしましょう:

sqlite> .mode box
sqlite> SELECT * FROM mytable;
┌────────┬────────┐
│ field1 │ field2 │
├────────┼────────┤
│ label1 │ value1 │
│ label2 │ value2 │
│ label3 │ value3 │
└────────┴────────┘

...データをJSONに抽出してfield1フィールド名を変更keyできます。field2value

$ sqlite3 mydatabase.db '.mode json' 'SELECT field1 AS key, field2 AS value FROM mytable'
[{"key":"label1","value":"value1"},
{"key":"label2","value":"value2"},
{"key":"label3","value":"value3"}]

jqフィルタを介して直接実行してfrom_entries必要な出力を生成できます。

$ sqlite3 mydatabase.db '.mode json' 'SELECT field1 AS key, field2 AS value FROM mytable' | jq from_entries
{
  "label1": "value1",
  "label2": "value2",
  "label3": "value3"
}

気づくfrom_entriesフィルタリングjq「アイテム」配列、つまりkeyキーを持つオブジェクトが必要ですvalue

SQLiteはJSONを出力し、そのJSONを処理して、jq引用符、改行、その他の潜在的に問題のある文字を含むデータを正しく処理できるようにします。

sqlite> SELECT * FROM mytable;
┌─────────────────────┬────────────┐
│       field1        │   field2   │
├─────────────────────┼────────────┤
│ label1              │ value1     │
├─────────────────────┼────────────┤
│ label2              │ value2     │
├─────────────────────┼────────────┤
│ label3              │ value3     │
├─────────────────────┼────────────┤
│ label "with quotes" │ value with │
│                     │ newline    │
└─────────────────────┴────────────┘
$ sqlite3 mydatabase.db '.mode json' 'SELECT field1 AS key, field2 AS value FROM mytable' | jq from_entries
{
  "label1": "value1",
  "label2": "value2",
  "label3": "value3",
  "label \"with quotes\"": "value with\nnewline"
}

SQLiteでアクティブになっている間にSELECTクエリで生成された既存のCSVファイルがある場合でも、.mode csv同じトリックを使用してフィールドの名前を変更し、key最初にvalueMillerを使用してフィールドにタグを付け直すことでCSVからJSONに変換できます。from_entriesjq

$ mlr --c2j label key,value mydata.csv | jq from_entries
{
  "label2": "value2",
  "label3": "value3",
  "label \"with quotes\"": "value with\nnewline"
}

ヘッダー行を削除した場合は、無題のCSV入力を表示することをmlr選択できます。-N

明らかに、すでにMillerを使用している場合は、次のものを含めずにすべての作業を実行できますjq

$ mlr --c2j label key,value then put -q 'end { emit @record } @record[$key] = $value' then cut -x -f key,value mydata.csv
[
{
  "label2": "value2",
  "label3": "value3",
  "label \"with quotes\"": "value with\nnewline"
}
]

これにより、データが読み取られ、2つのフィールドのmydata.csvラベルが再割り当てされ、key各入力レコードのフィールド値によってフィールドが異なる新しいレコードのすべてのデータが収集されます。次に、2つのイニシャルkeyvalueフィールドを削除し、単一のJSONオブジェクトを含む配列で出力を作成します。

関連情報