himorogiの日記

主にプログラミングに関することなど。少々ハード(電子工作)についても。

【macOS】PowerShell から SQLite を使うための備忘録【.import】

CSV の import なら SQLite の DotCommand でもできるけど…

昨日書いたのは、要するに CSV のデータを PowerShell で読み込んで INSERT Query 生成して SQLite に読み込ませる手順。
CSV import なら SQLite 自身、.import コマンドで対応できる…が…

とにかく一度やってみよう。

まずCSV を準備(昨日の使いまわし)

Proverb.csv

"ID","name","phrase"
"1","厩戸皇子","以和爲貴"
"2","釈迦","天上天下唯我独尊"
"3","孔子","有朋自遠方来不亦楽乎"
"4","杜甫","国破山河在"

CSV にもいろいろなフォーマットがあるが、普通はこういう形。
ところが、SQLite では separator の default は '|' なので、昨日 INSERT した結果を SELECT したら…

PS /Users/hoge/handleProverb> ./selectProverb.ps1
1|厩戸皇子|以和爲貴
2|釈迦|天上天下唯我独尊
3|孔子|有朋自遠方来不亦楽乎
4|杜甫|国破山河在
PS /Users/hoge/handleProverb>

こうなる。

.import の実例

.import でそのまま Proverb.csv を読むと、カラムの判別ができないので、.separetor , で変更しないといけない。
*1
面倒なんで、CREATE TABLE から .import , SELECT を一括して処理したのが以下の通り。

importProverb.ps1

@"
CREATE TABLE Proverb ( id, name, phrase );
.separator ,
.import ./Proverb.csv Proverb
SELECT * FROM Proverb;
"@ | sqlite3 ./myFirst.db $_

実行結果は…

PS /Users/hoge/handleProverb> ./importProverb.ps1
ID,name,phrase
1,厩戸皇子,以和爲貴
2,釈迦,天上天下唯我独尊
3,孔子,有朋自遠方来不亦楽乎
4,杜甫,国破山河在
PS /Users/hoge/handleProverb>

はい、読み込めてます…が、最初のレコード、header が入ってる。
つまり、.import で読み込む CSV には header 入れちゃ拙い。 .import のパラメータには header 無視するとかいう指定はない(はず)。
まぁ、予め CSV の一行削除するとか、DELETE 文で header 削除するとかやりようはあるけど、要するに手間が一つ余計にかかる(とはいっても、上記の例なら .import の直後に DELET 文一行追加するだけなので大した手間ではないけど、これを忘れてうっかり header 残したままにすることが、実は一番の問題だと思う)。

そういうわけで私はあんまり .import 使わないのだけど、大量のレコードを読み込む必要があって PowerShell の遅さに我慢できないときは、予め CSV の header 削除するか、DELETE文追加するくらいの手間と header 消し忘れるリスクは許容できる…かもしれない。

【追記】

せっかくなので、CSV の header 行削除板を…

importProverbHeaderless.ps1

get-content ./Proverb.csv | Select-Object -skip 1 | set-content ./ProverbHeaderless.csv
@"
CREATE TABLE Proverb ( id, name, phrase );
.separator ,
.import ./ProverbHeaderless.csv Proverb
SELECT * FROM Proverb;
"@ | sqlite3 ./myFirst.db $_

実行結果も…

PS /Users/hoge/handleProverb> ./importProverbHeaderless.ps1 
1,厩戸皇子,以和爲貴
2,釈迦,天上天下唯我独尊                                                                                                    
3,孔子,有朋自遠方来不亦楽乎
4,杜甫,国破山河在
PS /Users/hoge/handleProverb>

*1:【2021/01/13 追記】 .separator による default 値の変更は session 中のみ有効なので、毎回指定する必要がある(はず)。