仕事でDataflowで動かすApache BeamのPythonスクリプトを書いてたんですがコードを共通化する時にArtifact Registryを使う必要がありそうだったのでローカルでPython共通パッケージをビルドしてArtifact RegistryにpushできるDocker環境を作りました。
方針として基本ローカルにhomebrewなどでPython環境を構築していかず基本何をするにもDockerでチームメンバー間の開発環境の差分を吸収したかったのでDockerで作ってます。
用意するファイル
サービスアカウントの認証キーとenvファイル
Artifact Registryへの権限を許可したサービスアカウントの認証キーをjsonでダウンロードしてルート直下に配置する必要があります。名前は任意ですが今回はcredentials.jsonという名前で置いてます。
envファイル
.envファイルにGOOGLE_APPLICATION_CREDENTIALSいうキー名で先ほどの認証キーのパスを指定します。今回はDockerのWORKDIRを/workspaceというフォルダ名にしているので/workspace/credentials.jsonを指定します。
GOOGLE_APPLICATION_CREDENTIALS=/workspace/credentials.json
Dockerfile
pythonイメージのDockerfileです。 COPYコマンドで先ほどの認証キーを配置します。requirements.txtの内容は後述します。
FROM python:3.10 WORKDIR /workspace COPY . . RUN pip install -r requirements.txt
compose.yml
コンテナが1つかないのでcomposeはなくてもさほど苦労せず運用できそうですが個人的にcompose用意した方がDockerコマンドにオプション並べるよりも扱いやすいので用意してます。upコマンドでコンテナにattachしてデバッグしやすいようにcommandに tail -f /dev/nullを記載しています。
version: '3.8'
services:
artifact_repository_python:
build: .
env_file: .env
command: tail -f /dev/null
container_name: artifact_repository_python
volumes:
- .:/workspace
requirements.txt
setuptools、wheel、twineはPythonの共通パッケージをビルドしてArtifact Registryにpushするのに使います。
keyringとkeyrings.google-artifactregistry-authはArtifact Registryの接続認証に必要となります。
setuptools wheel twine keyring keyrings.google-artifactregistry-auth
.gitignore
GCPの認証キーはgitに含めるとまずいのでgitignoreしてください。
また後述するPythonコードの共通パッケージをbuildする際にできるファイルもgitignoreしたいですがこの辺りの記載をそのまま使うと楽です。
共通パッケージの例
dataflow_custom_optionというApache Beamのオプションを返却する共通パッケージを作る例です。
Pythonの共通パッケージについてはここでは詳しく触れませんのでざっくり書きます。
Pythonの共通パッケージについて参考
https://packaging.python.org/ja/latest/discussions/setup-py-deprecated/ packaging.python.org
dataflow_custom_optionというフォルダを用意して以下のファイルを配置します。
setup.py
rom setuptools import setup, find_packages
setup(
name='dataflow_custom_option',
version="1.0.0",
packages=find_packages(where='src'),
package_dir={'': 'src'},
install_requires=open('requirements.txt').read().splitlines()
)
dataflow_custom_optionフォルダに以下配置
init.py
from .custom_option import configure_pipeline_options __all__ = ["configure_pipeline_options"]
custom_option.py
コードの中身は適当です。共通化したいコードを記述してください。
from apache_beam.options.pipeline_options import PipelineOptions
def configure_pipeline_options(job_name, gcp_project_id, runner='DataflowRunner'):
options = PipelineOptions(
job_name = job_name,
runner = 'runner',
project = gcp_project_id,
region = 'asia-northeast1',
)
return options
ここまで用意したら以下コマンドでArtifact Registryにpushできます。
# ビルド docker-compose run --rm artifact_repository_python bash -c "cd dataflow_custom_option && python setup.py sdist bdist_wheel" # GCPのArtifact Repositoryへのpush docker-compose run --rm artifact_repository_python twine upload --skip-existing --repository-url https://asia-northeast1-python.pkg.dev/development-severus/dataflow-python dataflow_custom_option/dist/* --verbose
pushした共通パッケージのインストール
Dockerで実行するPythonコードでArtifact Registryにpushしたコードを使う場合
使う側でもArtifact Registryへのpush環境と同じように認証付きの環境を用意する必要があります。Dockerで作る場合このようになります。
FROM python:3.10 WORKDIR /workspace COPY . . ENV GOOGLE_APPLICATION_CREDENTIALS /workspace/credentials.json RUN pip install keyring keyrings.google-artifactregistry-auth RUN pip install -r requirements.txt
requirements.txtには以下のように--extra-index-urlとしてArtifact Registryのレポジトリパスを記載します。
--extra-index-url https://asia-northeast1-python.pkg.dev/hoge-project/hoge-repository/simple dataflow-custom-option
末尾にsimpleと付けるのはpipの仕様のようです。
コード上でのimport
from severus_dataflow_custom_option import configure_pipeline_options
options = configure_pipeline_options(job_name, gcp_project_id, runner='DirectRunner')
# Dataflowのパイプライン記載
with beam.Pipeline(options=options) as p:
(p
以上。