# syntax = docker/dockerfile:1 # 1. Base Stage: Common dependencies ARG RUBY_VERSION=3.3.1 FROM ruby:$RUBY_VERSION-slim as base WORKDIR /rails ENV RAILS_ENV="production" \ BUNDLE_DEPLOYMENT="1" \ BUNDLE_PATH="/usr/local/bundle" \ BUNDLE_WITHOUT="development:test" # Install base packages (libvips for Active Storage, curl for healthchecks) RUN apt-get update -qq && \ apt-get install --no-install-recommends -y \ build-essential \ curl \ git \ libvips \ freetds-bin \ freetds-dev \ libjemalloc2 \ ruby-dev \ dos2unix && \ rm -rf /var/lib/apt/lists /var/cache/apt/archives # 2. Build Stage: Gems and Assets FROM base as build # Install packages needed to build gems and precompile assets RUN apt-get update -qq && \ apt-get install --no-install-recommends -y build-essential pkg-config less && \ rm -rf /var/lib/apt/lists /var/cache/apt/archives # Install application gems RUN bundle config set --local frozen false COPY Gemfile Gemfile.lock ./ RUN bundle install && \ rm -rf ~/.bundle/ "${BUNDLE_PATH}"/ruby/*/cache "${BUNDLE_PATH}"/ruby/*/bundler/gems/*/.git && \ bundle exec bootsnap precompile --gemfile # Copy application code COPY . . RUN bundle exec bootsnap precompile app/ # 3. Final Stage: Lean Runtime FROM base # Copy built artifacts: gems and precompiled assets # COPY --from=build /rails/public /rails/public # COPY --from=build /rails/app/javascript /rails/app/javascript # COPY --from=build /rails/config/importmap.rb /rails/config/importmap.rb COPY --from=build /usr/local/bundle /usr/local/bundle COPY --from=build /rails /rails # Run as a non-privileged user for security RUN useradd -ms /bin/bash rails RUN chown -R rails:rails /rails USER rails:rails # Entrypoint prepares the database. ENTRYPOINT ["/rails/bin/docker-entrypoint"] # Start the server EXPOSE 3005 CMD ["bundle", "exec", "puma", "-C", "config/puma.rb"]