FROM golang:1.19-alpine as builder WORKDIR /app ADD go.mod . ADD go.sum . RUN go mod download ADD . . RUN CGO_ENABLED=0 GOOS=linux go build -a -installsuffix cgo -o app . FROM alpine:latest as prod RUN apk update && apk add --no-cache ca-certificates WORKDIR /app COPY --from=builder /app/app . #COPY config/config.yaml . CMD ["./app"]
这个 Dockerfile 由两个阶段组成。第一个阶段使用 golang:1.17-alpine
作为基础镜像,设置工作目录为 /app
,并将项目的所有文件复制到工作目录中。然后使用 go mod download
下载依赖库,并使用 go build
命令编译出可执行文件。
第二个阶段使用 alpine:3.15
作为基础镜像,并安装了 ca-certificates
。然后将工作目录设置为 /app
,从第一个阶段中复制编译出来的可执行文件 app
和配置文件 config/config.yaml
到镜像中,并设置容器启动时的默认命令为 ./app
。
注意,在第二个阶段中使用了 --from=build
参数来指定复制源,这意味着只复制第一个阶段构建出来的文件,而不会复制构建环境中的任何文件,从而实现了分层编排。
对应的 docker-compose.yaml
version: '3' services: app: build: context: . dockerfile: Dockerfile volumes: - ./config:/app/config ports: - "8080:8080"
指令RUN go mod download
执行的时候,会构建一层缓存,包含了该项所有的依赖。之后再次提交的代码中,若是go.mod
、go.sum
没有变化,就会直接使用该缓存,起到加速构建的作用,也不用重复的去外网下载依赖
了。若是这两个文件发生了变化,就会重新构建这个缓存分层。
=> CACHED [builder 2/7] WORKDIR /app 0.0s
=> CACHED [builder 3/7] ADD go.mod . 0.0s
=> CACHED [builder 4/7] ADD go.sum . 0.0s
=> CACHED [builder 5/7] RUN go mod download