如何使用多阶段构建减少python(docker)图像大小? (** python具体**)

时间:2018-01-31 13:54:10

标签: python docker dockerfile docker-multi-stage-build

我正在寻找一种使用python和Dockerfile创建多级构建的方法:

例如,使用以下图像:

第一张图片:安装所有编译时需求,并安装所有需要的python模块

第二张图片:将所有已编译/构建的包从第一张图片复制到第二张图片,没有编译器本身(gcc,postgers-dev,python-dev等...)

最后的目标是拥有一个较小的图像,运行python和我需要的python包。

简而言之:我怎样才能包装'在第一张图片中创建的所有已编译模块(site-packages / external libs),将它们复制到' clean'方式,到第二张图片。

4 个答案:

答案 0 :(得分:10)

好吧所以我的解决方案是使用wheel,它让我们在第一张图片上编译,为所有依赖项创建wheel文件并在第二张图片中安装它们,而无需安装编译器

FROM python:2.7-alpine as base

RUN mkdir /svc
COPY . /svc
WORKDIR /svc

RUN apk add --update \
    postgresql-dev \
    gcc \
    musl-dev \
    linux-headers

RUN pip install wheel && pip wheel . --wheel-dir=/svc/wheels

FROM python:2.7-alpine

COPY --from=base /svc /svc

WORKDIR /svc

RUN pip install --no-index --find-links=/svc/wheels -r requirements.txt

您可以在以下博文中看到我的答案

https://galnevis.wixsite.com/website/single-post/2018/02/10/Python-and-Docker-multistage-build

答案 1 :(得分:1)

我推荐this article(第2节)中详细介绍的方法。他使用virtualenv,因此pip install将所有python代码,二进制文件等存储在一个文件夹中,而不是散布在整个文件系统中。然后,很容易将一个文件夹复制到最终的“生产”映像中。总结:

编译图像

  • 在您选择的某些路径中激活virtualenv。
  • 将该路径添加到您的Docker ENV。这是virtualenv需要用于将来所有docker RUN和CMD操作的功能。
  • 像往常一样安装系统开发软件包和pip install xyz

生产图片

  • 从“编译映像”中复制virtualenv文件夹。
  • 将virtualenv文件夹添加到Docker的PATH

答案 2 :(得分:-4)

我希望以下示例有帮助

FROM yourbaseimage as builder

RUN echo install dependencies etc. \
 && echo build

FROM yoursmallbaseimage

RUN mkdir -p /bin/

COPY --from=builder /bin/binary /bin/binary

#[...]

ENTRYPOINT ["/bin/binary"]

您还可以在第一个建筑物图像中对它们进行焦油化,并在较小的基础图像中提取图像。 或创建像deb,rpm这样的官方软件包,只有最少的文件。 也许你只需要基础python和一个你可以转移为tar等的venv。

更容易找到信息为您的任务制作一个干净的包 - 所以你可以谷歌最好的项目,也许安装包

答案 3 :(得分:-4)

这方面的文档解释了如何做到这一点。

https://docs.docker.com/engine/userguide/eng-image/multistage-build/#before-multi-stage-builds

基本上你完全按照自己的意思行事。多级构建功能的神奇之处在于您可以从一个dockerfile完成所有这些操作。

即:

FROM golang:1.7.3
WORKDIR /go/src/github.com/alexellis/href-counter/
RUN go get -d -v golang.org/x/net/html  
COPY app.go .
RUN CGO_ENABLED=0 GOOS=linux go build -a -installsuffix cgo -o app .

FROM alpine:latest  
RUN apk --no-cache add ca-certificates
WORKDIR /root/
COPY --from=0 /go/src/github.com/alexellis/href-counter/app .
CMD ["./app"]  

这构建了一个go二进制文件,然后下一个图像运行二进制文件。第一个图像包含所有构建工具,而seccond只是一个可以运行二进制文件的基本linux机器。