--
You received this message because you are subscribed to the Google Groups "Ruby or Rails Oceania" group.
To unsubscribe from this group and stop receiving emails from it, send an email to rails-oceani...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/rails-oceania/8a6bdd29-7ff3-457b-8a0c-9d42dedc4675%40googlegroups.com.
How often is your gemfile changing?
One approach I've used in the past is copying just the gemfile (and related stuff) in and creating that as a layer. Then copy the rest of the project in later.
COPY package.json yarn.lock /app/
RUN yarn install
# This is done to speed up CI builds. The base gem file should not be changing a lot so this will cache the whole thing
COPY Gemfile_base.rb /app/
#
## Install the builder gems, don't clean out the cache and delete the gemfile for the next step.
RUN bundle config path \
&& bundle install --gemfile Gemfile_base.rb
# Install gems
COPY Gemfile /app/
COPY Gemfile.lock /app/
RUN bundle config path \
&& bundle config --global frozen 1 \
&& bundle install --gemfile Gemfile \
# Remove unneeded files (cached *.gem, *.o, *.c)
&& rm -rf $BUNDLE_PATH/cache/ \
&& find $BUNDLE_PATH/gems/ -name "*.c" -delete \
#The last argument to eval makes exceptions in Gemfile.devel show up with the correct filename.
eval File.read('Gemfile_base.rb'), nil, 'Gemfile_base'
This allows me add the base gems as one layer and the second bundle install uses the already installed gems from the base layer so it goes faster. This allows all my gems to be defined in the same project (no base layer to pull from) but it's split into two files so that's not ideal.Also I use dockerignore basically in reverse to whitelist just the stuff that I want in there; not for size purposes (mainly) but so that it doesn't recreate layers when nothing important has changed.
It's not that the gemfile is changing it's that Gemfile.lock is changing because we have gems we are pulling from git.
That's what I am doing but I am doing it in two phases like this.
...
This allows me add the base gems as one layer and the second bundle install uses the already installed gems from the base layer so it goes faster. This allows all my gems to be defined in the same project (no base layer to pull from) but it's split into two files so that's not ideal.
I have a pretty robust dockerignore (I can post it if you want) but the build still take a long time and as I said the docker image is HUGE 1.2 gigs. I did a three stage docker build once and got the image to just a hair under 600 megs but that still seems insanely large for a rails app.
What about the asset precompilation? Can I skip that if I have done a yarn install? how about visa versa? Can I skip the yarn install if I do a asset precompile? Is there another way to avoid a database connection when I am doing asset precompile than using the nulldb adapter?
We're doing yarn install and asset precompilation for our docker build, and we run these steps on CI to prepare the source code, which is then packaged into a docker image.
This allows us to fully leverage CI's own caches (we're doing it on Gitlab as well btw), and basically we do with bundler what you already discussed here - cache the bundle plus Gemfile/Gemfile.lock, then we cache node_modules plus package.json/yarn.lock, and we also keep tmp/assets between builds to speed up assets precompilation. Can't comment on the database thing - we just let our build connect to the db, it didn't really bother us much.
If no dependencies changed between the builds – the installation steps are fast, and it's only asset compilation itself that takes some time.
It also removes the need for us to have yarn or raw assets in the docker image at all – we just add Rails bundle as a separate layer to cache it, and then copy project code with precompiled assets, but WITHOUT any raw assets - it speeds up the process and reduces final image size (no node_modules and all that in the image).
Hope this helps.
--
You received this message because you are subscribed to the Google Groups "Ruby or Rails Oceania" group.
To unsubscribe from this group and stop receiving emails from it, send an email to rails-oceani...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/rails-oceania/CAGD6pKZ89%2B9JTEH%3DYw-CKW7e_ZnyRvN-4S5oMpQXs%2BnTBsTLXw%40mail.gmail.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/rails-oceania/CAC-XhxXvASC4%3DHs0cY%3D8yv2zZU1r%3Dds%2Bx93-rXzX4-q9R%2BemEQ%40mail.gmail.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/rails-oceania/CAOOM5kx2PjvKCE6QdBAnFez4ygqBO5TpQTFLp4F2xGJ4B1o3rQ%40mail.gmail.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/rails-oceania/CAGuHJrPoRgVG420RiPqzEbiv5_P3UyHqN%2B2tbpOkPQ3JjU06og%40mail.gmail.com.
ARG BUNDLE_WITHOUT='development test'
ARG BUNDLER_VERSION='2.1.0'
ARG RUBYGEMS_VERSION='3.1.1'
ARG BUNDLE_INSTALL_PATH='/bundle'
ENV RAILS_ENV='production' \
RAILS_LOG_TO_STDOUT=true \
SECRET_KEY_BASE='foo' \
LANG='C.UTF-8' \
PATH="/app/bin:/${BUNDLE_INSTALL_PATH}/bin/:$PATH" \
GEM_HOME="${BUNDLE_INSTALL_PATH}" \
GEM_PATH="${BUNDLE_INSTALL_PATH}" \
BUNDLE_WITHOUT=${BUNDLE_WITHOUT} \
BUNDLE_JOBS=4 \
BUNDLE_RETRY=3 \
BUNDLE_PATH="${BUNDLE_INSTALL_PATH}" \
BUNDLE_APP_CONFIG="${BUNDLE_INSTALL_PATH}" \
BUNDLE_BIN="bin" \
BUNDLE_ALLOW_OFFLINE_INSTALL="true" \
BUNDLE_CLEAN="true" \
BUNDLE_DEPLOYMENT="true" \
BUNDLE_CACHE_ALL="true"
Despite all this the bundler installs fresh gems every time the dockerfile builds. The asset precompile does see the cache and runs a lot faster but for some strange reason it runs yarn install twice.
BTW the bundler documentation is outdated so some of the flags listed don't work.
To view this discussion on the web visit https://groups.google.com/d/msgid/rails-oceania/CAOOM5kx2PjvKCE6QdBAnFez4ygqBO5TpQTFLp4F2xGJ4B1o3rQ%40mail.gmail.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/rails-oceania/CAGuHJrPO1YmrRrA-DSVXhrc%3DWx66fMUnk%2BVCzmkFY4qON63X7A%40mail.gmail.com.