我正在寻找一种使用python和Dockerfile创建多级构建的方法:
例如,使用以下图像:
第一张图片:安装所有编译时需求,并安装所有需要的python模块
第二张图片:将所有已编译/构建的包从第一张图片复制到第二张图片,没有编译器本身(gcc,postgers-dev,python-dev等...)
最后的目标是拥有一个较小的图像,运行python和我需要的python包。
简而言之:我怎样才能包装'在第一张图片中创建的所有已编译模块(site-packages / external libs),将它们复制到' clean'方式,到第二张图片。
答案 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代码,二进制文件等存储在一个文件夹中,而不是散布在整个文件系统中。然后,很容易将一个文件夹复制到最终的“生产”映像中。总结:
编译图像
pip install xyz
。生产图片
答案 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机器。