LoginSignup
3
0

More than 5 years have passed since last update.

CircleCI 2.0 + Docker Sbt Build

Posted at

Scala の Dockar Image を作る方法を考える。例として CircleCI 2.0 で Playframework 2.6 のアプリケーションのビルドを行う。

実験コード nokamoto/proposal-circileci2.0-sbt-docker

Dockerfile

Build

sbt universal:packageZipTarball

VERSION=$(cat VERSION | tr -d '\n')

docker build -t nokamoto/proposal-circileci2.0-sbt-docker:${VERSION} --build-arg VERSION=${VERSION} .

初めはコンテナ内での sbt ビルドを考えたが .ivy2 キャッシュの再利用など実行時間が問題となったので、外で作った tar をコピーする方法とした。

version := IO.readLines(file("VERSION")).head
docker build ... --build-arg VERSION=${VERSION} ...

sbtdocker でバージョン方法を共有するため VERSION ファイルを作成した。
Docker へのビルド時の変数共有は ARG によって可能となる。

COPY target/universal/${APP}-${VERSION}.tgz .

無駄なデータが入るとキャッシュが効かなくなる可能性が高まるので、sbt が作成した tar のみコピーする。

*
!./target/universal/*.tgz

上記のような .dockerignore により tgz ファイルのみをビルド時のコンテキストに取り込ませることができる。
今回のビルドでは tgz ファイルのみ利用するため単純な記述となるが、 git repo の構成次第では管理が煩雑となるかもしれない。少なくとも Scala での開発では target ディレクトリなど巨大なファイルが出来るので .dockerignore はあったほうが良さそうに思う。

実行結果

target/universal に変更がなければ Using cache となる。

$ VERSION=$(cat VERSION | tr -d '\n')
$ docker build -t nokamoto/proposal-circileci2.0-sbt-docker:${VERSION} --build-arg VERSION=${VERSION} .
Sending build context to Docker daemon  32.66MB
Step 1/8 : FROM openjdk:8u181-jre-slim
 ---> c32c7f04676c
Step 2/8 : ARG VERSION
 ---> Using cache
 ---> e4376ecb0a5c
Step 3/8 : ARG APP=proposal-circileci2-0-sbt-docker
 ---> Using cache
 ---> b909a0260c5d
Step 4/8 : COPY target/universal/${APP}-${VERSION}.tgz .
 ---> Using cache
 ---> 3cd6d6285625
Step 5/8 : RUN tar -zxvf ${APP}-${VERSION}.tgz && mv ${APP}-${VERSION} ${APP}
 ---> Using cache
 ---> ed10a36c35e6
Step 6/8 : RUN rm ${APP}-${VERSION}.tgz
 ---> Using cache
 ---> d203430f0b0b
Step 7/8 : ENTRYPOINT [ "proposal-circileci2-0-sbt-docker/bin/proposal-circileci2-0-sbt-docker" ]
 ---> Using cache
 ---> dca9f0c6f3cc
Step 8/8 : CMD [ "-h" ]
 ---> Using cache
 ---> fd1139d10b8b
Successfully built fd1139d10b8b
Successfully tagged nokamoto/proposal-circileci2.0-sbt-docker:0.0.0

CircleCI 2.0

Workflow

workflows:
  version: 2
  ci:
    jobs:
      - test
      - build:
          requires:
            - test

test を実行して tar を作成してから build で docker build & push を行う。
今回はデプロイまでは考えていないので上記の wrorkflow で完了する。

test

基本は Language Guide: Scala の流れと変わらない。

      - run:
          name: Install sbt-extras
          command: |
            curl -Ls https://git.io/sbt > /usr/local/bin/sbt
            chmod u+x /usr/local/bin/sbt

sbt のインストールを sbt-extras に変更した。

      - run:
          name: Sbt test & package
          command: sbt test universal:packageZipTarball
      - save_cache:
          key: sbt-universal-{{ .Revision }}
          paths:
            - "target/universal"

test ジョブで sbt の実行環境を整備しているのでここで tar を作成し Cachingsbt-universal-{{ .Revision }} としてキャッシュする。

build

      - restore_cache:
          key: sbt-universal-{{ .Revision }}
      - run:
          name: Docker build & push
          command: |
            VERSION=$(cat VERSION | tr -d '\n')
            TAG=nokamoto13/proposal-circileci2.0-sbt-docker:${VERSION}
            docker login -u $DOCKER_USER -p $DOCKER_PASS
            docker build -t ${TAG} --build-arg VERSION=${VERSION} .
            docker push ${TAG}

sbt-universal-{{ .Revision }} をリストアしてから docker build & push を実行する。

3
0
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
3
0