LoginSignup
8
2

RDSのデータをBigQueryに転送してみた(ECS,Embulk)

Posted at

実現したこと

MySQLの特定のテーブルをBigQueryへ毎日転送する

雑ですがイメージこんな感じです!
定期実行には、EventBridge Schedulerを使いました!
CleanShot 2023-12-02 at 17.23.09@2x.png

Embulkとは

Embulkは、さまざまなデータベースやクラウドサービス間のデータ転送を可能にする並列バルクデータローダーです。
今回で言うと、AWS->GCP でのデータ転送に使いました!

作業手順

1. Embulkを起動するECS TaskをDockerfileで作成

embulkのインストールがもっとスッキリいくはずだったのですが、上手くいかず結局手動で必要なものをインストールしました・・・・

FROM openjdk:8-jre-slim
WORKDIR /home

ENV EMBULK_VERSION 0.9.25

RUN apt-get update && apt-get install -y \
        curl \
    # Install embulk
    && curl -o /usr/local/bin/embulk --create-dirs -L "http://dl.embulk.org/embulk-${EMBULK_VERSION}.jar" \
    && chmod +x /usr/local/bin/embulk \
    # Install independencies for embulk-output-bigquery
    && embulk gem install faraday -v 0.17.4 \
    && embulk gem install multi_json -v 1.15.0 \
    && embulk gem install jwt -v 2.3.0 \
    && embulk gem install public_suffix -v 4.0.7 \
    && embulk gem install addressable -v 2.7.0 \
    && embulk gem install signet -v 0.11.0 \
    && embulk gem install multipart-post -v 2.1.1 \
    && embulk gem install multipart-post -v 2.1.1 \
    && embulk gem install declarative-option -v 0.1.0 \
    && embulk gem install declarative -v 0.0.20 \
    && embulk gem install uber -v 0.1.0 \
    && embulk gem install representable -v 3.0.4 \
    && embulk gem install retriable -v 3.1.2 \
    && embulk gem install mini_mime -v 1.0.2 \
    && embulk gem install memoist -v 0.16.2 \
    && embulk gem install os -v 1.1.0 \
    && embulk gem install googleauth -v 0.9.0 \
    && embulk gem install httpclient -v 2.8.3 \
    && embulk gem install google-api-client -v 0.32.1 \
    && embulk gem install google-cloud-env -v 1.2.1 \
    && embulk gem install google-cloud-core -v 1.3.0 \
    # Install gem at ~/.embulk
    && embulk gem install embulk-input-mysql \
    && embulk gem install embulk-output-bigquery

# Embulk用の設定ファイルを定義
COPY ./config ./config
# TODO:GPCでサービスアカウントを発行する
COPY ./service-account.json ./service-account.json

COPY ./entrypoint.sh ./entrypoint.sh
RUN chmod +x entrypoint.sh
CMD ["/bin/sh", "entrypoint.sh"]
# entrypoint.shファイル

#!/bin/bash
# Use -Xmx800m option to prevent Java heap error
java -Xmx800m -jar /usr/local/bin/embulk run ./config/mysql.yml.liquid

2. Embulk用の設定ファイルの作成

embulkの設定が結構大変でした、、、

# config/mysql.yml.liquidファイル
in:
  type: mysql
  host: {{ env.DB_HOST }}
  user: {{ env.DB_USER }}
  password: {{ env.DB_PASSWORD }}
  database: {{ env.DB_NAME }}
  table: {{ env.table }}
  ssl: true
  options: { enabledTLSProtocols: TLSv1.2 }
  parser:
   type: json
out:
  type: bigquery
  mode: replace
  auth_method: service_account
  json_keyfile: /home/service-account.json
  file_ext: .jsonl.gz
  source_format: NEWLINE_DELIMITED_JSON
  auto_create_dataset: true
  dataset: mysql
  auto_create_table: true
  table: {{ env.table }}
  formatter: {type: jsonl}
  encoders: 
    - {type: gzip}

3. 定期実行の設定

EventBridge Schedulerはこれがわかりやすかったです!
<参考にさせていただいた記事>

躓いたところ

①タスクが起動しない・・・

ポリシーにこれが必要だった AmazonECSTaskExecutionRolePolicy

とにかく動かすことベースで良いなら下記あたりを付与すると良いと思います!
CleanShot 2023-12-02 at 17.57.32@2x.png

<参考にさせていただいた記事>

②やっぱりタスクが起動しない・・・

タスク定義時にCloudWatch Logsを設定して、起動時のエラーを確認すると、タスク起動時に以下のエラーが出ていました。
(ECSデバッグしにくい・ログ見にくいのが辛い。。。)

exec /docker-entrypoint.sh: exec format error

ちょっと調べてみると、多分ECRのイメージのプラットフォームと、実行するプラットフォームに互換性が無い場合に発生するエラーらしいです(多分)

■手元で確認してみると
タスク定義で設定したplatformがx86_64で
作成したコンテナイメージがarm64だった(んだと思います)

■解決方法 ECR上げ直し
プッシュコマンドは基本コピペだと思いますが、buildするときに

docker build --platform linux/x86_64 -t test-ecr .

のように --platform linux/x86_64 を入れてあげると治りました。

終わりに

EmbulkやECS/ECRの知見があまりなく、、、もっと良い方法があったら是非教えてください!
ここまで読んでいただきありがとうございました!

8
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
8
2