Introduce a base docker image for layer caching purposes #3593
This will drastically improve docker dev environment initial setup speed. Rather than building locally, the local docker build (built from Dockerfile.dev) is now based on the public, automated exercism/exercism.io build (built from Dockerfile). With this as a starting point, a developer's
@kytrinyx: Before merging this, you will need to create an Automated Build on Docker Hub. The new
Based on #3590 to avoid conflicts.
This enables the use of defaults with variable interpolation. Followed procedure documented at https://docs.docker.com/compose/compose-file/compose-versioning/#version-1-to-2x
This will drastically improve docker dev environment initial setup speed. Rather than building locally, the local docker build (built from Dockerfile.dev) is now based on the public, automated exercism/exercism.io build (built from Dockerfile). With this as a starting point, a developer's `docker-compose build` need only install any new gems that are introduced in the feature branch. With no local changes, a local docker build, excluding download time, now takes approximately 6 seconds, vs. 50 minutes before. Changes: - .dockerignore vendor/ Vendored gems make the docker context directory size large (+1.1 G in vendor/), causing longer build times. Additionally, as individual developers, rather than being able to inherit most or all gems from an application base image, we are forced to install the full set of gems when first setting up a development environment. - Dockerfile is now used by the automated build to build the exercism/exercism.io base image. See https://hub.docker.com/r/exercism/exercism.io/ - docker-compose builds Dockerfile.dev, which is built FROM the public exercism/exercism.io docker image. This Dockerfile need only contain commands specific to the development environment and changes from the local git repository that need to be built. Presently, it checks for new gems to install. - Dockerfile: Set WORKDIR before RUN bundle install to invalidate one fewer layer when the bundle is updated.
node_modules can get large and adds time to the context upload to the Docker engine. In our development environment, node_modules is mounted from the host with the rest of the application source and will always be present.
There are good reasons for vendoring gems for production deployments, but in my experience, vendoring in development has given my teams more trouble than the default behavior installing gems on the system. Existing development environments will continue to use vendor/ until they modify/remove .bundle/config, because these are mounted with the source code. This will now slow docker image builds, since .dockerignore now includes vendor/ and .bundle/.