Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/directus/directus/llms.txt

Use this file to discover all available pages before exploring further.

Installation Guide

This guide covers detailed installation instructions for Directus, including Docker deployment, npm/pnpm installation, and production environment configuration.
Requirements: Directus requires Node.js 22 or higher. Check your version with node -v

Installation Methods

Choose the installation method that best fits your needs:

Docker Installation

Docker is the recommended method for production deployments. Directus provides official Docker images.

Quick Start with Docker

1

Pull the Directus Image

docker pull directus/directus
2

Run with SQLite (Development)

For quick testing with SQLite:
docker run -d \
  --name directus \
  -p 8055:8055 \
  -e KEY="replace-with-random-value" \
  -e SECRET="replace-with-random-value" \
  -e ADMIN_EMAIL="admin@example.com" \
  -e ADMIN_PASSWORD="d1r3ctu5" \
  -e DB_CLIENT="sqlite3" \
  -e DB_FILENAME="/directus/database/database.sqlite" \
  -v directus_data:/directus/database \
  directus/directus
SQLite is great for development but not recommended for production. Use PostgreSQL or MySQL for production deployments.

Production Docker Compose Setup

For production, use Docker Compose with PostgreSQL:
1

Create docker-compose.yml

Create a docker-compose.yml file:
version: '3.8'

services:
  directus:
    image: directus/directus:latest
    ports:
      - 8055:8055
    volumes:
      - ./uploads:/directus/uploads
      - ./extensions:/directus/extensions
    environment:
      KEY: 'replace-with-random-value'
      SECRET: 'replace-with-random-value'

      DB_CLIENT: 'pg'
      DB_HOST: 'postgres'
      DB_PORT: '5432'
      DB_DATABASE: 'directus'
      DB_USER: 'directus'
      DB_PASSWORD: 'directus'

      CACHE_ENABLED: 'true'
      CACHE_STORE: 'redis'
      REDIS_HOST: 'redis'
      REDIS_PORT: '6379'

      ADMIN_EMAIL: 'admin@example.com'
      ADMIN_PASSWORD: 'd1r3ctu5'

      PUBLIC_URL: 'https://yourdomain.com'

    depends_on:
      - postgres
      - redis

  postgres:
    image: postgis/postgis:13-3.4-alpine
    environment:
      POSTGRES_DB: 'directus'
      POSTGRES_USER: 'directus'
      POSTGRES_PASSWORD: 'directus'
    volumes:
      - postgres_data:/var/lib/postgresql/data

  redis:
    image: redis:6-alpine
    volumes:
      - redis_data:/data

volumes:
  postgres_data:
  redis_data:
Security: Replace KEY, SECRET, and all passwords with strong, random values before deploying to production!
2

Generate Secure Keys

Generate secure random values for KEY and SECRET:
# Generate KEY (must be exactly 32 characters)
openssl rand -base64 32

# Generate SECRET (can be any length)
openssl rand -base64 64
Update your docker-compose.yml with these values.
3

Start the Services

docker compose up -d
This will:
  • Start PostgreSQL database
  • Start Redis cache
  • Start Directus
  • Bootstrap the database on first run
4

Verify Installation

Check that all services are running:
docker compose ps
Access Directus at http://localhost:8055

Dockerfile Reference

The official Directus Dockerfile uses a multi-stage build:
ARG NODE_VERSION=22

# Build stage
FROM node:${NODE_VERSION}-alpine AS builder

RUN npm install --global corepack@latest
RUN apk --no-cache add python3 py3-setuptools build-base

WORKDIR /directus

COPY package.json .
RUN corepack enable && corepack prepare

RUN chown node:node .
USER node

ENV NODE_OPTIONS=--max-old-space-size=8192

COPY pnpm-lock.yaml .
RUN pnpm fetch

COPY --chown=node:node . .
RUN pnpm install --recursive --offline --frozen-lockfile
RUN npm_config_workspace_concurrency=2 pnpm run build
RUN pnpm --filter directus deploy --legacy --prod dist

# Runtime stage
FROM node:${NODE_VERSION}-alpine AS runtime

RUN npm install --global pm2@5 corepack@latest

USER node
WORKDIR /directus

ENV DB_CLIENT="sqlite3" \
    DB_FILENAME="/directus/database/database.sqlite" \
    NODE_ENV="production" \
    NPM_CONFIG_UPDATE_NOTIFIER="false"

COPY --from=builder --chown=node:node /directus/ecosystem.config.cjs .
COPY --from=builder --chown=node:node /directus/dist .

EXPOSE 8055

CMD node cli.js bootstrap && pm2-runtime start ecosystem.config.cjs

npm/pnpm Installation

Install via npm

1

Install Directus Globally

npm install -g directus
2

Create a New Project

directus init my-project
cd my-project
3

Install Database Driver

Install the appropriate database driver:
npm install pg
4

Configure Environment

Edit the .env file created during init. See Environment Configuration below.
5

Bootstrap and Start

# Initialize the database
npx directus bootstrap

# Start the server
npx directus start

Install via pnpm

1

Install Directus Globally

pnpm install -g directus
2

Create and Setup Project

directus init my-project
cd my-project
3

Install Database Driver

# For PostgreSQL
pnpm install pg

# For MySQL/MariaDB
pnpm install mysql2
4

Bootstrap and Start

pnpm directus bootstrap
pnpm directus start

Install from Source

For development or if you want to customize Directus:
1

Clone the Repository

git clone https://github.com/directus/directus.git
cd directus
2

Install Dependencies

Directus uses pnpm for package management:
# Enable corepack (comes with Node.js 22)
corepack enable

# Install dependencies
pnpm install
3

Build All Packages

# Build all packages
pnpm build

# Or build specific package
pnpm --filter @directus/api build
4

Run Development Server

# API with hot reload on port 8055
cd api && pnpm dev

# App with Vite HMR on port 8080
cd app && pnpm dev

Environment Configuration

Directus is configured via environment variables. Here are the essential configurations:

Core Configuration

# Server Configuration
HOST="0.0.0.0"                    # Default: 0.0.0.0
PORT=8055                          # Default: 8055
PUBLIC_URL="https://yourdomain.com" # Your public-facing URL

# Security (REQUIRED)
KEY="your-secret-key-32-chars"     # Exactly 32 characters
SECRET="your-secret-phrase"        # Any length

# Limits
MAX_PAYLOAD_SIZE="1mb"             # Default: 1mb
MAX_RELATIONAL_DEPTH=10            # Default: 10
QUERY_LIMIT_DEFAULT=100            # Default: 100
MAX_BATCH_MUTATION="Infinity"      # Default: Infinity

Caching with Redis

CACHE_ENABLED="true"
CACHE_STORE="redis"
CACHE_TTL="30m"                   # Cache time-to-live
CACHE_NAMESPACE="directus-cache"

REDIS_HOST="localhost"
REDIS_PORT=6379
# REDIS_PASSWORD="redis-password"  # If password protected

Storage Configuration

STORAGE_LOCATIONS="local"
STORAGE_LOCAL_DRIVER="local"
STORAGE_LOCAL_ROOT="./uploads"

Rate Limiting

RATE_LIMITER_ENABLED="true"
RATE_LIMITER_POINTS=50             # Requests per duration
RATE_LIMITER_DURATION=1            # Duration in seconds
RATE_LIMITER_STORE="memory"        # Or "redis"

# Global rate limiter (all requests)
RATE_LIMITER_GLOBAL_ENABLED="true"
RATE_LIMITER_GLOBAL_POINTS=1000
RATE_LIMITER_GLOBAL_DURATION=1

Authentication & Security

ACCESS_TOKEN_TTL="15m"             # Default: 15 minutes
REFRESH_TOKEN_TTL="7d"             # Default: 7 days
REFRESH_TOKEN_COOKIE_SECURE="true" # Set true in production
REFRESH_TOKEN_COOKIE_SAME_SITE="lax"

SESSION_COOKIE_TTL="1d"
SESSION_COOKIE_SECURE="true"
SESSION_COOKIE_SAME_SITE="lax"

LOGIN_STALL_TIME=500               # Delay in ms (security)

Email Configuration

EMAIL_FROM="noreply@yourdomain.com"
EMAIL_TRANSPORT="smtp"
EMAIL_SMTP_HOST="smtp.gmail.com"
EMAIL_SMTP_PORT=587
EMAIL_SMTP_USER="your-email@gmail.com"
EMAIL_SMTP_PASSWORD="your-password"
EMAIL_SMTP_SECURE="false"          # Use TLS

Production Deployment

Using PM2 for Process Management

Directus includes PM2 configuration for production deployments:
# Install PM2 globally
npm install -g pm2

# Start Directus with PM2
pm2 start ecosystem.config.cjs

# View logs
pm2 logs directus

# Monitor
pm2 monit

# Restart
pm2 restart directus

# Stop
pm2 stop directus

# Save PM2 configuration
pm2 save

# Set PM2 to start on boot
pm2 startup

Nginx Reverse Proxy

Example Nginx configuration:
server {
    listen 80;
    server_name yourdomain.com;

    # Redirect HTTP to HTTPS
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    server_name yourdomain.com;

    ssl_certificate /path/to/certificate.crt;
    ssl_certificate_key /path/to/private.key;

    client_max_body_size 100M;

    location / {
        proxy_pass http://localhost:8055;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_cache_bypass $http_upgrade;
    }
}

Production Checklist

Before deploying to production:
  • Use PostgreSQL or MySQL (not SQLite)
  • Set up automated backups
  • Configure connection pooling
  • Enable SSL for database connections
  • Exclude system tables: DB_EXCLUDE_TABLES="spatial_ref_sys,sysdiagrams"
  • Generate strong KEY (32 characters) and SECRET
  • Set REFRESH_TOKEN_COOKIE_SECURE="true"
  • Set SESSION_COOKIE_SECURE="true"
  • Configure PUBLIC_URL to your domain
  • Enable and configure CORS appropriately
  • Set up rate limiting with Redis
  • Review and configure CORS_ORIGIN
  • Enable Redis caching: CACHE_ENABLED="true"
  • Configure rate limiting with Redis store
  • Set appropriate cache TTL values
  • Use CDN for assets
  • Configure MAX_PAYLOAD_SIZE based on needs
  • Configure cloud storage (S3, Azure, GCS)
  • Set up CDN for file delivery
  • Configure appropriate file upload limits
  • Enable server-side encryption if required
  • Configure email transport (SMTP, SES, etc.)
  • Set EMAIL_FROM to valid sender address
  • Test password reset emails
  • Configure email rate limiting
  • Enable logging: Configure Pino log levels
  • Set up health check endpoint: /server/ping
  • Monitor with PM2 or Docker health checks
  • Set up error tracking (Sentry, etc.)
  • Configure metrics export if needed
  • Configure SSL certificates
  • Use reverse proxy (Nginx, Caddy, etc.)
  • Force HTTPS redirects
  • Enable HSTS headers

Database Migration

When updating Directus versions, migrations may be required:
# Check migration status
directus database migrate:latest

# Run migrations one at a time
directus database migrate:up

# Rollback one migration
directus database migrate:down
Always backup your database before running migrations!

Troubleshooting

Symptoms: Error connecting to databaseSolutions:
  • Verify database is running
  • Check DB_HOST, DB_PORT, DB_DATABASE, DB_USER, DB_PASSWORD
  • Ensure database driver is installed (pg, mysql2, etc.)
  • Check network connectivity
  • For PostgreSQL, try: DB_SSL="false" if SSL is not configured
Symptoms: Error: listen EADDRINUSE: address already in use :::8055Solutions:
  • Change port: PORT=3000 in .env
  • Find and kill process using port 8055:
    lsof -ti:8055 | xargs kill -9
    
Symptoms: Error: KEY environment variable is requiredSolutions:
  • Generate keys:
    directus security key:generate
    directus security secret:generate
    
  • Add to .env file
Symptoms: Files fail to upload or saveSolutions:
  • Check STORAGE_LOCAL_ROOT directory exists and is writable
  • Increase MAX_PAYLOAD_SIZE if files are large
  • Verify disk space
  • Check file permissions on upload directory
Symptoms: Container exits immediatelySolutions:
  • Check logs: docker logs directus
  • Verify all required environment variables are set
  • Ensure database is ready before Directus starts (use depends_on)
  • Check volume mounts are correct

Next Steps

Configure Data Model

Set up your collections, fields, and relationships

Authentication Setup

Configure OAuth, LDAP, SAML, or other auth providers

API Documentation

Learn about REST and GraphQL endpoints

Extensions

Extend Directus with custom interfaces and endpoints

Webhooks & Flows

Automate workflows and integrate with external services

User Management

Set up roles, permissions, and user accounts

Additional Resources