本記事は、前回の記事の続きである。本記事では、実際に自分のローカル環境を使い、Pythonの簡単な環境を構築するコンテナイメージをS2Iを使ってビルドしていく。
使用した環境
S2Iのダウンロード
WSL2のubuntuへS2Iをダウンロード手順を以下に示す:
- まず、S2Iを配置するための一時的なディレクトリを用意し、そのディレクトリへ移動する:
mkdir /tmp/s2i/ && cd /tmp/s2i/
- 次に、S2Iのバイナリパッケージアーカイブをダウンロードし、バイナリファイルを適切なディレクトリへ置く。S2Iのリリース情報はリリース情報にあるので、自分の環境に合わせてS2Iのバージョンは選んでいく。
ディレクトリ/tmp/s2i/
内でcurl
を使用し、ここでは最新バージョンのS2Iをダウンロードする:
$ curl -s https://api.github.com/repos/openshift/source-to-image/releases/latest| grep browser_download_url | grep linux-amd64 | cut -d '"' -f 4 | wget -qi -
- 次に、バイナリファイルの解凍を行う
$ tar xvf source-to-image*.gz
- S2IのPATHを次のように通す。例えば
s2i
という実行ファイルを/usr/local/bin
へ移動する:
sudo mv s2i /usr/local/bin
rm -rf /tmp/s2i/
ここで、一時的に作成したディレクトリ/tmp/s2i/
は必要ないので、削除した。
- 最後に、S2Iの場所を以下で確認すると
which s2i
>
/usr/local/bin/s2i
と表示される。S2Iのバージョンを確認すると以下のように出力されるはずである:
$ s2i version
s2i v1.3.8
S2Iビルドの実行
手順1. S2Iビルドを実行するためのディレクトリ作成
まず、S2Iのs2i create
コマンドを使い、S2Iビルド実行用のひな形のディレクトリを作成する:
$ s2i create python-test python-test
今回はpython-test
というディレクトリを作成した。実際にpython-test
のディレクトリ構造を確認する:
$ cd python-test
~/python-test$ tree
.
├── Dockerfile
├── Makefile
├── README.md
├── s2i
│ └── bin
│ ├── assemble
│ ├── run
│ ├── save-artifacts
│ └── usage
└── test
├── run
└── test-app
└── index.html
S2I builder imageをビルドするためには、Dockerfileに加え、S2Iスクリプトが必要である。directory構造では、s2i/bin
配下にs2iで実行するためのS2I scriptが配置されている。必須のスクリプトはassemble
とrun
この2種類である。
手順2. Pythonを実行するファイルの作成
今回はtest/test-app
ディレクトリ内のアプリケーションソースコードをpythonの実行ファイルsample.py
、requirements.txt
というファイルを追加しておく:
.
├── Dockerfile
├── Makefile
├── README.md
├── s2i
│ └── bin
│ ├── assemble
│ ├── run
│ ├── save-artifacts
│ └── usage
└── test
├── run
└── test-app
├── sample.py
└── requirements.txt
実際のPython用スクリプト sample.py
、requirements.txt
を以下に示す:
print("Hellow World!")
numpy
手順3. DockerfileとS2I scriptの作成
今回、使用したDockerfileを以下に示す:
Dockerfile
FROM python:latest
USER root
# TODO: Set labels used in OpenShift to describe the builder image
LABEL io.openshift.s2i.scripts-url=image://usr/libexec/s2i \
io.openshift.tags="builder,python"
COPY ./s2i/bin/ /usr/libexec/s2i
# TODO: Set the default CMD for the image
CMD ["/usr/libexec/s2i/usage"]
次に、S2I scriptを作成していく。assemble.sh
とrun.sh
を作成していく。
assembleについて
assemble
では、ソースコードからアプリケーションのアーティファクト(成果物)をビルドし、それらをイメージ内の適切なディレクトリに配置する。
実際にPythonのコンテナイメージを作成するためのスクリプト例 assemble.sh
を示す:
assemble scriptの実際の中身を実際に見てみると以下のようになっている。
#!/bin/bash -e
if [[ "$1" == "-h" ]]; then
exec /usr/libexec/s2i/usage
fi
# アプリケーション、例えば、sample.py, requirements.txtをアプリの実行を行うディレクトリへコピーし配置している
echo "---> Installing application source..."
cp -Rf /tmp/src/. ./
# requirements.txtを用いて、pip installでライブラリのインストールを行っている
echo "---> Building application from source..."
pip install --upgrade pip
if [ -f requirements.txt ]; then
pip install -r requirements.txt
fi
上記にようにassembleではPythonモジュールのインストールを実施している。
runについて
実際にpythonスクリプト sample.py
を実行するスクリプトである:
#!/bin/bash -e
python sample.py
手順4. S2I image builderを作成する
S2Iビルドを実行するために、docker build
を使って、S2I image builderをビルドする。docker build
はDockerfile
があるディレクトリ内で実行する必要がある。今回は、S2I image builderの名前はpython-builder
という名前にする:
$ docker build -t python-builder ./python-test
コマンドの説明
-
docker build
: Dockerfileを使い、コンテナイメージをビルドする -
-t python-builder
: タグ付きでコンテナイメージ名をpython-builder
にする -
./python-test
: Dockerビルドを実行するディレクトリを指定する
実際にビルドされたコンテナイメージを確認してみる:
$ docker images
>
REPOSITORY TAG IMAGE ID CREATED SIZE
python-builder latest 039c8d89b767 2 minutes ago 426MB
手順5. S2Iビルド実行
手順2、3でアプリケーションソースコードとPython環境用のS2I builder imegaを作成した。これらを用いて、S2Iビルドにより、新たなコンテナイメージをビルドする。
$~/python-test s2i build test/test-app/ python-builder python-app
>
`WARNING: could not inspect the builder image for labels: reading manifest latest in docker.io/library/python-builder: requested access to the resource is denied`
---> Installing application source...
---> Building application from source...
Build completed successfully
コマンド説明
-
s2i build
: S2Iビルドを実行し、新たなコンテナイメージをビルドする -
test/test-app/
: アプリケーションソースコードのディレクトリを指定 -
python-builder
: S2I builder imageのイメージ名を指定 -
python-app
: 新しくS2Iビルドされるコンテナイメージの名前を指定
実際にビルドされたコンテナイメージを確認してみる:
$~/s2i-test/python-test$ docker images
>
REPOSITORY TAG IMAGE ID CREATED SIZE
python-app latest 7561a8bc9e5a 10 seconds ago 426MB
python-builder latest 039c8d89b767 3 minutes ago 426MB
python-app
という最終的来なコンテナイメージがビルドされた。
注意点
S2Iでコンテナイメージのビルドを行う際の注意点を説明する。結論から言うと、S2Iビルド用のDockerfile
のLABEL
にイメージの場所io.openshift.s2i.scripts-url
を指定する必要がある。実際Dockerfileに書いたように
LABEL io.openshift.s2i.scripts-url=image://usr/libexec/s2i
と記述する必要がある。
起きた問題
はじめ、Dockerfileを以下のように記述し:
FROM python:latest
USER root
COPY ./s2i/bin/ /usr/libexec/s2i
CMD ["/usr/libexec/s2i/usage"]
S2Iビルドすると以下のようなエラーメッセージが出てきた:
could not inspect the builder image for labels: reading manifest latest in docker.io/library/pybuilder: requested access to the resource is denied
An error occurred: failed to install [assemble run]
Suggested solution: set the scripts URL parameter with the location of the S2I scripts, or check if the image has the "io.openshift.s2i.scripts-url" label set
まず、1つめのエラーは、イメージがdocker.ioに無かったのでローカルから探すという意味であり、これは無視する。2つ目のエラーはassemble runのインストールに失敗したことを意味する。3つ目のエラーはs2iスクリプトの場所を指定しろという意味をもつ。
そこで、エラーにある通りに、s2i builder imageを作成するためのDockerfileのLABELを以下のように記述し:
LABEL io.openshift.scripts-url=image://usr/libexec/s2i
と記述するが、再び、同じエラーが出てしまった。
解決策
s2i buildをopenshift上ではなく、ローカル上で実行する場合、作成したs2i builder image(今回はpython-builder
のこと)内のs2iスクリプトの場所をio.openshift.s2i.scripts-url
で指定する必要がある。
今回、Openshiftによって、用意されたベースイメージ(例えばopenshift/base-centos7
)ではなく、Openshift以外によって用意されたベースイメージ(今回の場合だとpython:latest
)を使用した。そのため、ローカルで用意したDockerfile
にイメージの場所io.openshift.s2i.scripts-url
をLABEL
で指定する必要があった。そのため、Dockerfile
へ
LABEL io.openshift.s2i.scripts-url=image://usr/libexec/s2i
を記述すればよい。また、io.s2i.scripts-url
というLABELによる指定でも、ビルドは成功するが、現在は廃止されており、使わなことをお勧めする。
次回はS2Iの機能の一つである増分ビルドというものについて説明します
参考文献
- OpenShift徹底活用ガイド
- Source-To-Image (S2I)公式ドキュメント
- [OpenShift]自作のS2Iスクリプトを使ってローカルにあるPerlスクリプトをS2Iビルドしてデプロイする
- Minishiftで遊んでみよう!手軽にkubernetesを体験するの巻
- MACOSにS2IコマンドをインストールしてS2Iビルドする
- OpenShift v3 と source-to-image (s2i)
- S2I work flow
- 第5章 S2I イメージのテスト
- S2Iに再入門
- OpenShift Origin構築手順メモ
- OpenShift OriginによるDockerイメージ管理(1)〜イメージストリームを理解する
- OpenShift OriginによるDockerイメージ管理(2)〜Dockerfileによるイメージビルドを自動化
- OpenShift OriginによるDockerイメージ管理(3)〜Dockerfileからイメージを作成する際のお作法
- OpenShift OriginによるDockerイメージ管理(4)〜S2Iによるイメージビルド