RDS for PostgreSQL で SJISのCSVファイルをインサートする

Amazon RDS

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

はじめに

オペ部の高橋です。

RDS for PostgreSQL で SJISのCSVファイルをインサートし データが文字化けしないか検証しました。
SQL Serverを使用していてデータ移行を行いたい場合などのユースケースがあるかと思います。

環境準備

RDS for PostgreSQLを用意

パラメータグループ等はデフォルト バージョン9.4.9

EC2インスタンスを用意してpsqlをインストール

Amazon Linux AMI release 2016.09

$ sudo yum install postgresql94 -y

SJISのCSVファイルの準備

以下の内容をinsert.csvとして保存してEC2インスタンスへアップロードしました。

insert-sjis

$ nkf -g insert.csv
Shift_JIS (CR)

検証

DBへ接続してテーブルを作成

$ psql -h test.czv2xmjmsjwx.ap-northeast-1.rds.amazonaws.com -p 5432 -U test test

test=> create table test_table (id INTEGER, moji VARCHAR(20));
CREATE TABLE
test=> \d
          List of relations
 Schema |    Name    | Type  | Owner
--------+------------+-------+-------
 public | test_table | table | test
(1 row)

test=> \d test_table;
         Table "public.test_table"
 Column |         Type          | Modifiers
--------+-----------------------+-----------
 id     | integer               |
 moji   | character varying(20) |

SJISのCSVファイルをインサート

・encodingを指定しないでデータ入れるとエラーが出ます。

test=> \copy test_table from '/home/ec2-user/work/insert.csv' with csv;
ERROR:  invalid byte sequence for encoding "UTF8": 0x82
CONTEXT:  COPY test_table, line 1

・encodingを指定してデータを入れます。

test=> \copy test_table from '/home/ec2-user/work/insert.csv' with encoding 'sjis' csv
COPY 4

無事COPYコマンドによりデータが入りましたので select 文にて確認して行きます。

結果

以下方法で確認します。

  • DBへ繋いでから select 文で確認
  • コマンドライン(psql) からselect 文で確認

クライアント(TeraTerm)の文字コードをSJISにしてSJISとして表示できるか確認

TeraTerm-sjis

DBへ繋いでから select 文で確認

select * from test_table;

select-sjis

クライアントエンコーディングがUTF8のままなので文字化けしました。
コマンドでクライアントエンコーディングをSJISにして確認します。

test=> set client_encoding to sjis;
SET
test=> \encoding
SJIS

select-sjis-2

コマンドライン(psql) からselect 文で確認

psql-select-sjis

こちらもクライアントエンコーディングがUTF8のままなので文字化けしました。
クライアント環境でPGCLIENTENCODING環境変数をSJISに設定します。

$ export PGCLIENTENCODING=SJIS
$ psql -h test.xxxxxxxxxxxx.ap-northeast-1.rds.amazonaws.com -p 5432 -U test test -c 'show client_encoding'
Password for user test:
 client_encoding
-----------------
 SJIS
(1 row)

psql-select-sjis-2

検証からSJISのファイルをインサートしてデータもSJISで確認できることがわかりました。

クライアント(TeraTerm)の文字コードをUTF8にしてUTF8として表示できるか確認

TeraTerm-utf8

DBへ繋いでから select 文で確認

select * from test_table;

select-utf8

コマンドライン(psql) からselect 文で確認

先ほど、クライアント環境はSJISに設定していましたのでPGCLIENTENCODING環境変数をUTF8に設定して確認します。
$ export PGCLIENTENCODING=UTF8
$ psql -h test.xxxxxxxxxxxx.ap-northeast-1.rds.amazonaws.com -p 5432 -U test test -c 'show client_encoding'
Password for user test:
 client_encoding
-----------------
 UTF8
(1 row)

psql-select-utf8

UTF8でも問題ないことがわかりました。

まとめ

今回、SJISのCSVをPostgreSQLのDBヘインサートし文字化けが発生するかどうか確認してみました。
PostgreSQLはDBエンコーディングとしてはUTF-8とEUC_JPですが
クライアントエンコーディングを指定することでSJISのデータも使用できることがわかりました。

参考URL

PostgreSQL 9.4.5文書 第 22章多言語対応
[PostgreSQL][SQL] csvファイルのインポート
PostgreSQL データをcsvファイルに出力する

AWS Cloud Roadshow 2017 福岡