Docker-first Python development (2019-04-12) ¶
See also
…
Except there’s one thing still bothering me: changes to the service code trigger a reinstallation of our test dependencies.
Yuck! Let’s take another whack at our Dockerfile
1 FROM python3 as service_deps
2 COPY requirements.txt ./
3 RUN pip install -r requirements.txt
4
5 FROM deps as test_deps
6 COPY test_requirements.txt ./
7 RUN pip install -r test_requirements.txt
8
9 FROM deps as builder
10 COPY src ./src
11
12 FROM test_deps as tests_builder
13 COPY src ./src
14 COPY tests ./tests
15
16 FROM tests_builder as localdev
17 ENTRYPOINT ["pytest"]
18 CMD ["tests"]
19
20 FROM tests_builder as tests
21 RUN pytest tests
22
23 FROM builder as service
24 COPY docker-entrypoint.sh ./
25 ENTRYPOINT ["docker-entrypoint.sh"]
26 EXPOSE 3000
Ok that seems pretty complicated, here’s a graph of our image topology:
service_deps
| \
| -\
| \
| -test_deps
| |
| |
builder tests_builder
| | -\
| | -\
| localdev -\
| --tests
service
I don’t love that the builder and tests_builder stages both copy over the source directory, but the real question is, does this still meet our initial goals while avoiding excessive re-installs of test dependencies ?
Yeah, it seems to work pretty well.
Thanks to Docker’s layer caching, we rarely have to re-install dependencies.