Report this

What is the reason for this report?

Best practices for reducing Docker image size for Node.js apps?

Posted on October 7, 2024

I’ve been using Docker to containerize my Node.js application, but my image size is quite large, and it’s affecting build times and deployments.

What are some best practices or strategies for reducing the size of a Docker image for a Node.js app? Should I be concerned about using specific base images, and are there any tips for cleaning up unnecessary files during the build process? Thanks in advance for your help!



This textbox defaults to using Markdown to format your answer.

You can type !ref in this text area to quickly search our full set of tutorials, documentation & marketplace offerings and insert the link!

These answers are provided by our Community. If you find them useful, show some love by clicking the heart. If you run into issues leave a comment, or add your own answer to help others.

Hey there! 👋

Reducing the size of Docker images is always a good idea, especially when working with Node.js apps since smaller images help speed up your builds and deployments! Here are a few things that I usually do:

  1. Instead of using the default node image, you can opt for node:alpine, which is a minimal version of the Node.js image based on Alpine Linux. It’s significantly smaller than the regular images:

    FROM node:alpine
    
  2. Use multi-stage builds. This allows you to keep your final image clean and only include the necessary production dependencies. Here’s a basic example:

    # First stage: Build the app
    FROM node:alpine AS build
    WORKDIR /app
    COPY package*.json ./
    RUN npm install
    COPY . .
    RUN npm run build
    
    # Second stage: Production
    FROM node:alpine
    WORKDIR /app
    COPY --from=build /app .
    CMD ["node", "server.js"]
    

    With this, you only ship the final built app, excluding any development dependencies or unnecessary files which can help a lot!

  3. Just like .gitignore, a .dockerignore file can prevent unnecessary files (like node_modules, logs, or .git) from being copied into your Docker image. Here’s an example .dockerignore:

    node_modules
    logs
    .git
    
  4. Combine commands into a single RUN statement to reduce the number of layers in the final image:

    RUN apk add --no-cache bash && \
        npm install && \
        npm cache clean --force
    
  5. When installing packages, make sure you clean up caches and unnecessary files. For example:

    RUN npm install && npm cache clean --force
    
  6. When building for production, use the NODE_ENV environment variable to exclude dev dependencies:

    ENV NODE_ENV=production
    RUN npm install
    

Let me know if you need any more help!

- Bobby

Heya,

Without a more indepth knowledge of the image itself we could only provide you with some general tips like:

Use a Minimal Base Image

  • Alpine Linux: This is a minimal base image that can significantly reduce the size of your image compared to larger images like node or ubuntu. You can use the official Node.js Alpine image:
FROM node:18-alpine
Alpine-based images are much smaller but may require some additional setup for native modules since they don’t include all system dependencies by default.

Multi-Stage Builds

Multi-stage builds allow you to separate the build environment from the production environment, meaning you can install and compile dependencies in one stage and then copy only the necessary files to the final image.

# Build Stage
FROM node:18-alpine AS builder
WORKDIR /app
COPY package*.json ./
RUN npm install --only=production
COPY . .

# Production Stage
FROM node:18-alpine
WORKDIR /app
COPY --from=builder /app /app
CMD ["node", "app.js"]

###Clean Up Node Modules

  • roduction Dependencies Only: Ensure you only install production dependencies in your final image:
RUN npm ci --only=production
This prevents the inclusion of unnecessary development dependencies in the final build.
  • Prune Dev Dependencies: After installing dependencies, prune anything not required in production:
RUN npm prune --production

The developer cloud

Scale up as you grow — whether you're running one virtual machine or ten thousand.

Get started for free

Sign up and get $200 in credit for your first 60 days with DigitalOcean.*

*This promotional offer applies to new accounts only.