RDSにあるデータをembulkを使ってBigQueryに飛ばすようにテストを繰り返していたところ、digdag run時に以下のエラーが出ました。
1 |
message=>"Error while reading data, error message: JSON parsing error in row starting at position 0: Could not convert value 'boolean_value: false' to integer. Field: hoge; Value: 0", |
そもそもinteger型のカラムにインサートできないそうですね。今回はその対処方法をブログします。
■CAST or Boolean
https://cloud.google.com/bigquery/sql-reference/functions-and-operators?hl=ja#top_of_page
tinyint,boolで定義されたカラムの値がEmbulkではtrueやfalseとして扱われるため、BigQueryのinteger型のカラムにインサートできない仕様になっています。回避策として、signed型にキャストするSQLを書くか、BigQueryのカラムをbooleanにする必要があります。
※今回はキャスト型に変換しましょう。
■use CAST
https://cloud.google.com/bigquery/sql-reference/functions-and-operators?hl=ja#casting
キャスト(CAST)はSQLで書いた結果を他の型に変換と覚えておきましょう。今回はhogeカラムとしてSQ:書いてみます。
1 |
> SELECT cast(hoge as SIGNED) AS hoge FROM adachintb; |
■embulk
・adachintb.json
1 2 3 4 5 6 7 8 9 10 11 |
[ { "name": "xxx", "type": "xxxxx" }, { "name": "hoge", #こいつだ! "type": "INT64" } ~省略~ ] |
・adachintb.yml.liquid
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
in: type: mysql {% if env.EMBULK_ENV == 'dev' %} {% include 'db/prod_adachindb' %} {% else %} {% include 'db/dev_adachindb' %} {% endif %} query: | SELECT id,cast(hoge as SIGNED) AS hoge FROM FROM adachintb out: type: bigquery mode: replace auth_method: json_key json_keyfile: /opt/digdag/mysql_to_bigquery/config/bq.key {% if env.EMBULK_ENV == 'dev' %} {% include 'db/prod_bigquery' %} {% else %} {% include 'db/dev_bigquery' %} {% endif %} auto_create_dataset: true auto_create_table: true dataset: adachin-db table: adachintb schema_file: /opt/digdag/mysql_to_bigquery/embulk/db/adachintb.json open_timeout_sec: 300 send_timeout_sec: 300 read_timeout_sec: 300 auto_create_gcs_bucket: false gcs_bucket: {{ env.EMBULK_OUTPUT_GCS_BUCKET }} compression: GZIP source_format: NEWLINE_DELIMITED_JSON default_timezone: "Asia/Tokyo" |
DBにあるテーブルを丸ごと持ってきて、BigQueryに上書きします。これでエラーなくBigQuery側にカラムとデータがぶちこまれました!
■まとめ
となるとMySQLのカラムの型定義とBigQueryの型定義が全く違うので、互換性のある型を指定する必要があるということが分かりますね。他にもBigQueryのタイムゾーンはUTC固定なので、JSTなどの他のタイムゾーンのDBのデータは時刻補正が必要とか。BigQueryはなかなか特殊なのでドキュメント理解しないとツライですな。
column_optionsでもできるそうです!
もちろんcastでもいいんですが、column_options使う方法もつかえる気がします。https://t.co/t6G81lY9bd
— Hiroyuki Sato (@hiroysato) July 13, 2018
0件のコメント