2
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

Goで作ったWebアプリをDockerで動かす

Last updated at Posted at 2019-12-07

概要

golangで作ったAPIをDocker上で動かします。
作ったAPIについて: GolangでシンプルなRESTful APIを作ってみた

サンプルはここ

Dockerfileを用意する

FROM golang:latest

WORKDIR /app
ADD . /app/

RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -a -ldflags="-s -w" -installsuffix cgo -o hello main.go

CMD ["./hello"]

Docker Compose ファイルを用意する

docker-compose.yml
version: "3.1"

services:
  api:
    build: .
    ports:
      - 1323:1323
    environment:
      DATA_SOURCE_NAME: root:root@tcp(db:3306)/sample
      PORT: :1323
  db:
    image: mysql
    command: --default-authentication-plugin=mysql_native_password
    restart: always
    environment:
      MYSQL_ROOT_PASSWORD: root
      MYSQL_DATABASE: sample
    volumes:
      - ./migration:/docker-entrypoint-initdb.d
    ports:
      - "3306:3306"

起動

コンテナ作成に必要なファイルは揃ったのでbuildして起動する

$ docker-compose up --build -d

イメージが作られているか確認する

$ docker images
REPOSITORY                           TAG                 IMAGE ID            CREATED             SIZE
helloworld_api                       latest              eaa02e55c990        11 seconds ago      908MB

実行できているか確認する

$ curl http://127.0.0.1:1323/users/1
{"ID":1,"Name":"suzuki"}

イメージサイズを小さくする

イメージサイズを抑えるためにalpineを使う
multi stage buildという機能があるので、それを使う
次のようにFROMが2つあるようにし、中間ステージのものに対してはas builderのように名前をつけておく

FROM golang:alpine as builder

WORKDIR /app
ADD . /app/

RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -a -ldflags="-s -w" -installsuffix cgo -o hello main.go

FROM alpine:latest

COPY --from=builder /app/hello /bin/hello

CMD ["/bin/hello"]

buildし、imageを確認する

$ docker-compose build
...
$ docker images
REPOSITORY                           TAG                 IMAGE ID            CREATED             SIZE
helloworld_api                       latest              0dada9b8827e        25 seconds ago      12.2MB

908MB→12.2MBに!
約98.6%の削減!!

オマケ

さらにイメージを小さくする

scratchという何も含まれないイメージを元に、静的リンクしたバイナリを配置する
※ 使うときに証明書、タイムゾーン等に気をつけないといけない

参考) GoとDockerでscratchを使うときに気をつけること


FROM golang:alpine as builder

WORKDIR /app
ADD . /app/

RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -a -ldflags="-s -w" -installsuffix cgo -o hello main.go

FROM scratch 

COPY --from=builder /app/hello /bin/hello

CMD ["/bin/hello"]

REPOSITORY                           TAG                 IMAGE ID            CREATED             SIZE
helloworld_api                       latest              d96e6246972c        8 seconds ago       6.6MB

upxを使ってさらに小さくする

FROM golang:alpine as builder

RUN apk --update add upx

WORKDIR /app
ADD . /app/

RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -a -ldflags="-s -w" -installsuffix cgo -o hello main.go &&\
    upx /app/hello

FROM scratch 

COPY --from=builder /app/hello /bin/hello

CMD ["/bin/hello"]


$ docker images
REPOSITORY                           TAG                 IMAGE ID            CREATED             SIZE
helloworld_api                       latest              0b7c833abf5c        9 seconds ago       2.58MB
イメージサイズ 1つ上からの削減率 golangからの削減率
golang 908MB - -
alpine 12.2MB 98.6% 98.6%
scratch 6.6MB 45.9% 99.2%
scratch & upx 2.58MB 60.9% 99.7%

めっちゃ小さくなったw

2
5
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
2
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?