How to build a Directus Docker Image with Custom Extensions
By Dmytro Laptiev • January 30, 2026

Directus is a powerful Headless CMS that offers incredible flexibility, but one common challenge developers face is deployment. While the official Directus Docker image is great for getting started, production environments often require something more specific.
If you have developed custom endpoints, hooks, or interfaces, you need a way to "bake" these extensions into your container.
In this guide, we will look at how to build a custom Directus Docker image that includes your own extensions, ensuring a consistent deployment across all your environments.
Why Build a Custom Image?
You might be asking, "Why not just map a volume to the extensions folder?"
While volume mapping works great for local development, it is often fragile in production. Building a custom Docker image offers several SEO and architectural benefits:
- Immutability: Your code and extensions are locked inside the image.
- Portability: You can deploy the exact same image to Kubernetes, AWS ECS, or DigitalOcean without worrying about missing files.
- Performance: Pre-building dependencies can reduce startup time.
Prerequisites
Before we dive into the code, ensure you have the following:
- Docker installed on your machine.
- A local Directus project with an
extensionsfolder containing your custom code.
The Solution: A Multi-Layer Dockerfile
To include your extensions, we need to create a Dockerfile in the root of your project. This file tells Docker to take the official Directus image and add your specific files on top of it.
Here is the Dockerfile code:
################################
## Build Packages
FROM node:18.20.4-alpine AS builder
WORKDIR /directus
COPY extensions/ extensions/
RUN for ext in $(ls extensions); do \
echo "Building extension: $ext"; \
cd extensions/$ext && \
npm install && \
npm run build || exit 1; \
cd -; \
done
################################
## Create Production Image
FROM directus/directus:11.1.0 as directus
COPY --from=builder --chown=node:node /directus/extensions /directus/extensions
COPY --chown=node:node ./database /directus/database
COPY --chown=node:node ./snapshots /directus/snapshots
COPY --chown=node:node ./uploads /directus/uploadsHow to Build and Run Your Image
docker build -t YOUR_IMAGE_NAME .After the build completes, you can run your new container:
docker run -p 8055:8055 \
-e KEY=your-random-key \
-e SECRET=your-random-secret \
YOUR_IMAGE_NAMEConclusion
Containerizing your Directus extensions is a crucial step in modernizing your deployment pipeline. By moving away from volume mapping in production and moving toward immutable Docker images, you ensure that your Headless CMS is stable, secure, and ready to scale.
