LoginSignup
4
6

More than 1 year has passed since last update.

アプリを Docker 、Docker Compose でコンテナを動かしてみる

Last updated at Posted at 2022-07-23

はじめに

記載情報は CI/CD に関連します。
実務上関わった環境・機能を身近な情報としてお届けしたく、投稿をはじめました。
各学習上、お金のかからない方法を選択していきます。

以下の手順を実施することで、アプリケーション開発者がアプリを Docker 、Docker Compose でコンテナを動かしてみる工程を模倣します。

対象者と関連環境・機能

この記事は下記のような人を対象にしています。

  • CI/CD 初学者
  • プログラミング初学者
  • 駆け出しエンジニア

記載している環境・機能は以下です。

  • Java
  • Spring Boot
  • Spring Web
  • Docker
  • Docker Compose

事前準備

  • 検証用 OS(ここでは ubuntu) を準備する
  • ubuntu に Docker をインストールする Install Docker Engine on Ubuntu
  • ubuntu に Docker Compose をインストールする(お好みでどうぞ) Install Docker Compose
  • サンプルアプリケーションをコピーする

サンプルアプリケーション

Dockerfile 追加

最新はこちらとなりますが、clone 後に初期状態を遡って確認頂けます。
サンプルアプリ の最新

事前準備

Dockerfile を作成する

FROM openjdk:11

# アプリケーションディレクトリを作成
WORKDIR /usr/src/myapp

# アプリケーション配置
COPY ./build/libs/application-springboot-0.0.1-SNAPSHOT.jar ./application-springboot-0.0.1-SNAPSHOT.jar

# コンテナの公開ポート
EXPOSE 8080

# アプリケーション起動
CMD [ "java", "-jar", "application-springboot-0.0.1-SNAPSHOT.jar" ]

Docker build をする。
「/build/libs/application-springboot-0.0.1-SNAPSHOT.jar」が存在しない場合、「gradlew build」を実行して生成しておきます。
最後の「.」が Dockerfile のパスを指し、カレントディレクトリに Dockerfile が存在する状態で実行しています。
(後々、パイプライン上で gradlew build、docker build、docker push と一連流れる処理を個別に手動実行しているイメージとなっています。)

$ docker build -t oad3jp999/application-springboot:0.0.1 .
Sending build context to Docker daemon   19.9MB
Step 1/5 : FROM openjdk:11
 ---> e782567c0965
Step 2/5 : WORKDIR /usr/src/myapp
 ---> Using cache
 ---> ac967f34611a
Step 3/5 : COPY ./build/libs/application-springboot-0.0.1-SNAPSHOT.jar ./application-springboot-0.0.1-SNAPSHOT.jar
 ---> 7cf31c6b2dca
Step 4/5 : EXPOSE 8080
 ---> Running in e621abd4f320
Removing intermediate container e621abd4f320
 ---> 46bceec1e334
Step 5/5 : CMD [ "java", "-jar", "application-springboot-0.0.1-SNAPSHOT.jar" ]
 ---> Running in 359899160e01
Removing intermediate container 359899160e01
 ---> d43e7721a88d
Successfully built d43e7721a88d
Successfully tagged oad3jp999/application-springboot:0.0.1

docker image が作成されました。

$ docker images
REPOSITORY                                   TAG                IMAGE ID       CREATED         SIZE
oad3jp999/application-springboot             0.0.1              d43e7721a88d   4 seconds ago   667MB

コンテナを動かしてみます。

$ docker run -itd d43e7721a88d
37840a75bb94fef3f7f249053d7a74cebfb59a22632822481f5614b9e1f9fbd3
$ docker ps
CONTAINER ID   IMAGE          COMMAND                  CREATED         STATUS         PORTS      NAMES
37840a75bb94   d43e7721a88d   "java -jar applicati…"   6 seconds ago   Up 3 seconds   8080/tcp   modest_tharp

コンテナのログを見てみます。
冒頭に「Hello LibraryJar!」が表示され、作成ライブラリを取り込んだ形でビルドが行われています。

$ docker logs 37840a75bb94
 =========================================
 Hello LibraryJar!
 =========================================


  .   ____          _            __ _ _
 /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
 \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |_\__, | / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::                (v2.6.7)

2022-04-30 22:26:32.027  INFO 1 --- [           main] com.example.demo.DemoApplication         : Starting DemoApplication using Java 11.0.12 on 37840a75bb94 with PID 1 (/usr/src/myapp/application-springboot-0.0.1-SNAPSHOT.jar started by root in /usr/src/myapp)
2022-04-30 22:26:32.032  INFO 1 --- [           main] com.example.demo.DemoApplication         : No active profile set, falling back to 1 default profile: "default"
2022-04-30 22:26:34.319  INFO 1 --- [           main] o.s.b.w.embedded.tomcat.TomcatWebServer  : Tomcat initialized with port(s): 8080 (http)
2022-04-30 22:26:34.349  INFO 1 --- [           main] o.apache.catalina.core.StandardService   : Starting service [Tomcat]
2022-04-30 22:26:34.349  INFO 1 --- [           main] org.apache.catalina.core.StandardEngine  : Starting Servlet engine: [Apache Tomcat/9.0.62]
2022-04-30 22:26:34.741  INFO 1 --- [           main] o.a.c.c.C.[Tomcat].[localhost].[/]       : Initializing Spring embedded WebApplicationContext
2022-04-30 22:26:34.741  INFO 1 --- [           main] w.s.c.ServletWebServerApplicationContext : Root WebApplicationContext: initialization completed in 2524 ms
2022-04-30 22:26:35.183  INFO 1 --- [           main] o.s.b.a.w.s.WelcomePageHandlerMapping    : Adding welcome page template: index
2022-04-30 22:26:35.469  INFO 1 --- [           main] o.s.b.w.embedded.tomcat.TomcatWebServer  : Tomcat started on port(s): 8080 (http) with context path ''
2022-04-30 22:26:35.497  INFO 1 --- [           main] com.example.demo.DemoApplication         : Started DemoApplication in 4.632 seconds (JVM running for 8.231)

コンテナの IP を確認すると、ホストから「172.17.0.2」で見えている事が確認できます。

$ docker exec -it 37840a75bb94 /bin/bash
root@37840a75bb94:/usr/src/myapp# ip -d a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 promiscuity 0 minmtu 0 maxmtu 0 numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
12: eth0@if13: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:ac:11:00:02 brd ff:ff:ff:ff:ff:ff link-netnsid 0 promiscuity 0 minmtu 68 maxmtu 65535
    veth numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
    inet 172.17.0.2/16 brd 172.17.255.255 scope global eth0 ※ホストからみれば「172.17.0.2」で見えている
       valid_lft forever preferred_lft forever
root@37840a75bb94:/usr/src/myapp# exit

ホストからコンテナに http アクセスしたところ index.html の内容が返り結果良好。
このイメージを利用して、Docker Hub へ docker image をプッシュできるように環境を整えます。

$ curl http://172.17.0.2:8080/
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>Hello SpringBoot Web Page</title>
</head>
<body>
    <H1>Hello SpringBoot Web Page</H1>
    </br>
    <form method="post" action="/result">
        Please input name<br>
        <input type="text" name="inputvalue"/>
        <input type="submit" value="submit" />
    </form>
</body>

前提作業
Docker Hub アカウントの登録
Docker Hub にログイン

$ docker login
Authenticating with existing credentials...
WARNING! Your password will be stored unencrypted in /home/xxx/.docker/config.json.
Configure a credential helper to remove this warning. See
https://docs.docker.com/engine/reference/commandline/login/#credentials-store

Login Succeeded

Docker Hub へ作成したイメージをプッシュ。
(Docker Hub で全公開することはほぼないものかと思いますが、お見せするのに手ごろな例として利用させてもらいます)

$ docker push oad3jp999/application-springboot:0.0.1
The push refers to repository [docker.io/oad3jp999/application-springboot]
0a37caee56e1: Pushed
52a5b831373a: Mounted from ・・・
0.0.1: digest: sha256:1b2c6bc37e1784f9fcf9c8c12fc75b76295cef4b457e60bb9a60c0fcf5faef92 size: 2213

UseDockerImage_001.png

以下はお掃除につきおまけ情報です。(コンテナ停止、ローカルイメージ削除)

$ docker ps ※動いているコンテナを表示
CONTAINER ID   IMAGE          COMMAND                  CREATED          STATUS          PORTS      NAMES
37840a75bb94   d43e7721a88d   "java -jar applicati…"   33 minutes ago   Up 32 minutes   8080/tcp   modest_tharp
$ docker stop 37840a75bb94 ※動いているコンテナを停止
37840a75bb94
$ docker ps ※コンテナが動いていないことを確認
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES
$ docker images ※docker imageを確認
REPOSITORY                                   TAG                IMAGE ID       CREATED          SIZE
oad3jp999/application-springboot             0.0.1              d43e7721a88d   34 minutes ago   667MB
$ docker rmi -f d43e7721a88d ※先ほどビルドして動かしていたローカルイメージを消します。今後は Docker Hub にプッシュしたイメージを使います。
Untagged: oad3jp999/application-springboot:0.0.1
Untagged: oad3jp999/application-springboot@sha256:1b2c6bc37e1784f9fcf9c8c12fc75b76295cef4b457e60bb9a60c0fcf5faef92
Deleted: sha256:d43e7721a88df9d6f431630eed6c364c74e4919343bee586771c86faff44ff29
Deleted: sha256:46bceec1e33486061f54dbbe6616f60bbde8299ffd773fe58c0d534799e34ff3
Deleted: sha256:7cf31c6b2dcac8c4a8b296420a32fb840730485021ab85fbab4e6f24e8a45798
$ docker images
REPOSITORY                                   TAG                IMAGE ID       CREATED         SIZE

ここまで行うと環境をまたいで Docker Image の利用が行いやすくなってきます。
別の Docker ランタイム環境でイメージを利用する例として、docker-compose をご紹介。

サンプルアプリケーション
manifest-files 追加

docker-compose.yml を作成

docker-compose.yml
version: '3'
services:
  myapp:
    image: oad3jp999/application-springboot:0.0.1
    container_name: application-springboot
    ports:
     - "8080:8080"

作成した yml の配置階層で、docker-compose コマンドを使用し、コンテナを起動する形です。

$ docker-compose --version
docker-compose version 1.29.2, build unknown
$ docker-compose up -d ※作成したymlの配置階層で、docker-composeコマンドを使用し、コンテナを起動
Creating network "application-springboot_default" with the default driver
Pulling myapp (oad3jp999/application-springboot:0.0.1)...
0.0.1: Pulling from oad3jp999/application-springboot
627b765e08d1: ...
Digest: sha256:1b2c6bc37e1784f9fcf9c8c12fc75b76295cef4b457e60bb9a60c0fcf5faef92
Status: Downloaded newer image for oad3jp999/application-springboot:0.0.1
Creating application-springboot ... done
$ docker-compose ps ※立ち上がったコンテナを確認
         Name                       Command               State                    Ports
----------------------------------------------------------------------------------------------------------
application-springboot   java -jar application-spri ...   Up      0.0.0.0:8080->8080/tcp,:::8080->8080/tcp
$ docker ps ※dockerコマンドでも確認可能
CONTAINER ID   IMAGE                                    COMMAND                  CREATED          STATUS          PORTS                                       NAMES
96f6d7f1c9be   oad3jp999/application-springboot:0.0.1   "java -jar applicati…"   28 seconds ago   Up 25 seconds   0.0.0.0:8080->8080/tcp, :::8080->8080/tcp   application-springboot
$ docker exec -it 96f6d7f1c9be /bin/bash ※コンテナ内の情報収集
root@96f6d7f1c9be:/usr/src/myapp# ip -d a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 promiscuity 0 minmtu 0 maxmtu 0 numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
15: eth0@if16: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default
    link/ether 02:42:ac:13:00:02 brd ff:ff:ff:ff:ff:ff link-netnsid 0 promiscuity 0 minmtu 68 maxmtu 65535
    veth numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
    inet 172.19.0.2/16 brd 172.19.255.255 scope global eth0
       valid_lft forever preferred_lft forever
</html>root@96f6d7f1c9be:/usr/src/myapp# exit
exit
$ curl http://172.19.0.2:8080/ ※curlで接続良好
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>Hello SpringBoot Web Page</title>
</head>
<body>
    <H1>Hello SpringBoot Web Page</H1>
    </br>
    <form method="post" action="/result">
        Please input name<br>
        <input type="text" name="inputvalue"/>
        <input type="submit" value="submit" />
    </form>
</body>
$ docker-compose stop ※コンテナ停止
Stopping application-springboot ... done
$ docker ps ※稼働コンテナなし
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES

関連記事

4
6
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
4
6