I work on a Rails project, using Webpack to bundle the assets. Each time I make a change in JS or CSS, I run docker-compose exec web bundle exec rake assets:precompile;
to compile all the assets.
After that, I have to restart the docker containers, and run the docker-compose exec web bundle exec npm run dev;
Only after that, I can see the change, and it can take up to 10 minutes. What am I missing? How can I speed up my development process?
My docker-compose.yml:
version: '2'
services:
chromedriver:
image: selenium/standalone-chrome-debug
volumes:
# use hosts shared memory to prevent crashes
# https://github.com/SeleniumHQ/docker-selenium
- /dev/shm:/dev/shm
postgres:
image: postgis/postgis:12-3.0
volumes:
- ./bin/docker/postgres/init-test-db.sh:/docker-entrypoint-initdb.d/init-test-db.sh
- .:/project
logging:
driver: "json-file"
options:
max-size: "10k"
max-file: "1"
redis:
image: redis:5.0.5
logging:
driver: "json-file"
options:
max-size: "10k"
max-file: "1"
worker:
build: .
volumes:
- .:/usr/src/app
- bundle-cache:/usr/local/bundle
command: bundle exec sidekiq
logging:
driver: "json-file"
options:
max-size: "100k"
max-file: "1"
web:
tty: true
stdin_open: true
build: .
volumes:
- .:/usr/src/app
- bundle-cache:/usr/local/bundle
logging:
driver: "json-file"
options:
max-size: "10k"
max-file: "1"
volumes:
bundle-cache:
3
Answers
When you are working with a docker-compose, it’s really useful to use volumes to also change files from your computer, and to start your compose with a
docker-compose up
.It looks weird to rebuild assets during a development stage. Is it not possible to bypass this step? I don’t know about Rails, but in python Django it’s possible to "collect the static" only for production.
At the core, there’s an issue that’s unrelated to Docker: If your app is configured correctly, you shouldn’t need to manually compile your assets – ever! And even if you have to, 10 minutes sound like way too much.
So the first thing you should do is make sure the following things:
development
environment (= doesRails.env
returndevelopment
)? If not, try settingRAILS_ENV=development
– this can, for instance, be done in theenvironment
setting in yourdocker-compose.yml
(or alternatively in a.env.development
file, if you’re using the dotenv-rails gem).development
environment? By default, this should be the case, but you might have accidentally/on purpose changed it. Check thatconfig/environments/development.rb
doesn’t containconfig.assets.compile = false
(or, generally, checkRails.application.config.assets.compile
and potentially even the wholeRails.application.config.assets
setting).I’m happy to investigate further and provide more insights, but I think for this you’d have to share more things (e.g. your Gemfile and environment configurations).
As for Docker, when using the asset pipeline (or newer Rails versions’ webpack integration), I’d suggest to the compiled assets into volumes, so they’re effectively cached. This could be done like so:
Since you have webpack, why not use webpack to compile?
Also you can add
speed-measure-webpack-plugin
for your webpack to see details of time spend on complieIn your
config/webpack/development.js
Last in your application.html.erb make sure to use
<%= javascript_pack_tag 'application' %>
to link the webpack compiled jsAlso you should look into webpack dev server with rails, so you don’t need to restart every time you make changes