第一次用 dockerfile 打包 go 项目时,都是在网上随便找一个例子拿来改改,运气好的话基本上也没啥问题,例如像下面这样
FROM golang:latest
# docker中的工作目录
WORKDIR $GOPATH/src/gin_docker
# 将当前目录同步到docker工作目录下,也可以只配置需要的目录和文件(配置目录、编译后的程序等)
ADD . ./
# 由于所周知的原因,某些包会出现下载超时。这里在docker里也使用go module的代理服务
ENV GO111MODULE=on
ENV GOPROXY=https://goproxy.cn,direct
# 指定编译完成后的文件名,可以不设置使用默认的,最后一步要执行该文件名
RUN go build -o rental-service-gin .
#设置时区为上海
RUN ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
RUN echo 'Asia/Shanghai' >/etc/timezone
RUN cp config/config-982-pro config/config
EXPOSE 9000
# 这里跟编译完的文件名一致
ENTRYPOINT ["./rental-service-gin"]
这样在通常情况下是没有问题的,但是既然听说了分阶段构建,就要动手实现分阶段构建并且要弄清楚分阶段构建能够减小镜像的原因
分阶段构建:
FROM golang:latest as builder
# docker中的工作目录
WORKDIR /go/src/gin_docker
# 将当前目录同步到docker工作目录下,也可以只配置需要的目录和文件(配置目录、编译后的程序等)
ADD . ./
# 由于所周知的原因,某些包会出现下载超时。这里在docker里也使用go module的代理服务
ENV GO111MODULE=on
ENV GOPROXY=https://goproxy.cn,direct
# 指定编译完成后的文件名,可以不设置使用默认的,最后一步要执行该文件名
RUN go build -o rental-service-gin .
#运行阶段
FROM alpine:latest as runner
WORKDIR /root/
COPY --from=builder /go/src/gin_docker/rental-service-gin .
RUN cp config/config-982-pro config/config
#设置时区为上海
RUN ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
RUN echo 'Asia/Shanghai' >/etc/timezone
EXPOSE 9000
# 这里跟编译完的文件名一致
ENTRYPOINT ["./rental-service-gin"]
两个文件除了两个FROM之外几乎没什么不同,我来解释一下为什么下面这个能给镜像瘦身
知识点:
1.同一个 dockerfile 文件的多个FROM 是多个不同的image,不同的 image 之间数据隔离,包括环境变量,但是不同的 image 之间可以通过 --from 来传递数据
2.同一个dockerfile 的多个 FROM 只有最后一个FROM 才会生成最终的镜像,因此编译阶段的环境没有在第二阶段中,第二阶段只是引用了第一阶段的生成物----二进制文件,所以最终生成的镜像文件比写一个 FROM 要小得多
网友评论