Deploying Directus
Introduction
Directus is a powerful open-source data platform and headless CMS that wraps your database with an intuitive admin interface and RESTful API. It provides a flexible content management solution that works with your existing SQL database, making it perfect for modern applications that need dynamic content management with complete control over your data structure.
This comprehensive guide shows you how to deploy Directus on Klutch.sh using Docker, configure persistent storage for uploads and database files, set up environment variables for production, and follow best practices for a secure, scalable deployment. Whether you’re building a content-driven website, mobile app backend, or data management platform, this guide will help you get Directus running reliably on Klutch.sh.
Prerequisites
- A Klutch.sh account
- A GitHub repository for your Directus deployment
- Basic familiarity with Docker, databases, and environment variables
- (Recommended for production) A PostgreSQL or MySQL database instance
Getting Started: Understanding Directus
Directus is designed to work with your existing SQL database and provides:
- Intuitive Admin Interface: A modern UI for managing content and data
- RESTful & GraphQL APIs: Automatic API generation from your database schema
- File Management: Built-in asset storage with transformations
- Role-Based Access Control: Granular permissions for users and teams
- Extensibility: Custom endpoints, hooks, and interfaces
Quick Installation Overview
Directus runs as a Node.js application that connects to your database. For Klutch.sh deployment, you’ll:
- Create a Dockerfile with Directus
- Configure database connection and storage
- Set up persistent volumes for uploads
- Deploy through the Klutch.sh dashboard
Sample Dockerfile
Klutch.sh automatically detects a Dockerfile in your repository root. Here’s a production-ready Dockerfile for Directus:
FROM directus/directus:11
# Set working directoryWORKDIR /directus
# Environment defaults (override these in Klutch.sh)ENV PORT=8055ENV PUBLIC_URL="https://example-app.klutch.sh"
# Expose the Directus portEXPOSE 8055
# Health check to ensure Directus is runningHEALTHCHECK --interval=30s --timeout=10s --start-period=60s --retries=3 \ CMD wget --no-verbose --tries=1 --spider http://localhost:8055/server/health || exit 1
# Start DirectusCMD ["node", "cli.js", "start"]Alternative: Custom Build Dockerfile
If you need to install extensions or customize the build:
FROM node:20-alpine
# Install dependenciesRUN apk add --no-cache \ bash \ git \ curl
# Set working directoryWORKDIR /directus
# Install DirectusRUN npm install -g directus@11
# Create directories for uploads and extensionsRUN mkdir -p /directus/uploads /directus/extensions
# Expose portEXPOSE 8055
# Start commandCMD ["directus", "start"]Deploying Directus on Klutch.sh
- Click “Create New App”
- Select your GitHub repository
- Choose the main branch
- Klutch.sh will automatically detect your Dockerfile
- Traffic Type: Select HTTP (Directus serves web traffic)
- Internal Port: Set to 8055 (Directus default port)
- Navigate to the “Volumes” section
- Click “Add Volume”
- Mount Path:
/directus/uploads - Size: Choose based on your storage needs (start with 10GB)
- Add another volume
- Mount Path:
/directus/database - Size: 5GB
- Review your configuration
- Click “Create” to deploy
- Klutch.sh will build your Docker image and start the container
- Your Directus instance will be available at
https://your-app.klutch.sh - Navigate to your app URL
- Log in with the admin credentials you configured (or create an admin user if not set)
- Configure your data model and collections
- Set up user roles and permissions
1. Prepare Your Repository
Create a new GitHub repository for your Directus deployment:
mkdir directus-klutchcd directus-klutchgit initAdd the Dockerfile (from above) to your repository root:
# Create Dockerfilecat > Dockerfile << 'EOF'FROM directus/directus:11
WORKDIR /directus
ENV PORT=8055ENV PUBLIC_URL="https://example-app.klutch.sh"
EXPOSE 8055
HEALTHCHECK --interval=30s --timeout=10s --start-period=60s --retries=3 \ CMD node -e "require('http').get('http://localhost:8055/server/health', (r) => {process.exit(r.statusCode === 200 ? 0 : 1)})"
CMD ["node", "cli.js", "start"]EOF
# Initialize and push to GitHubgit add Dockerfilegit commit -m "Add Directus Dockerfile"git branch -M maingit remote add origin https://github.com/yourusername/directus-klutch.gitgit push -u origin main2. Create a New App on Klutch.sh
Navigate to the Klutch.sh dashboard:
3. Configure Network Settings
In the app configuration:
4. Set Up Persistent Storage
Directus needs persistent storage for uploaded files. In the Klutch.sh dashboard:
For database persistence (if using SQLite for testing):
5. Configure Environment Variables
In the Klutch.sh dashboard, add these environment variables:
Required Variables:
KEY=your-random-secret-key-min-32-charsSECRET=your-random-secret-min-32-charsPUBLIC_URL=https://your-app.klutch.shGenerate secure keys with:
openssl rand -base64 32Database Configuration (PostgreSQL - Recommended):
DB_CLIENT=pgDB_HOST=your-postgres-hostDB_PORT=5432DB_DATABASE=directusDB_USER=directus_userDB_PASSWORD=your-secure-passwordDatabase Configuration (MySQL):
DB_CLIENT=mysqlDB_HOST=your-mysql-hostDB_PORT=3306DB_DATABASE=directusDB_USER=directus_userDB_PASSWORD=your-secure-passwordDatabase Configuration (SQLite - For Testing Only):
DB_CLIENT=sqlite3DB_FILENAME=/directus/database/data.dbOptional but Recommended:
# Admin user (created on first startup)ADMIN_EMAIL=admin@example.comADMIN_PASSWORD=your-secure-admin-password
# File storage configurationSTORAGE_LOCATIONS=localSTORAGE_LOCAL_ROOT=/directus/uploads
# Email configuration (for password resets, etc.)EMAIL_FROM=noreply@example.comEMAIL_TRANSPORT=smtpEMAIL_SMTP_HOST=smtp.example.comEMAIL_SMTP_PORT=587EMAIL_SMTP_USER=your-smtp-userEMAIL_SMTP_PASSWORD=your-smtp-password
# Cache configuration (optional)CACHE_ENABLED=trueCACHE_TTL=30m
# Rate limitingRATE_LIMITER_ENABLED=trueRATE_LIMITER_POINTS=50RATE_LIMITER_DURATION=1
# CORS settingsCORS_ENABLED=trueCORS_ORIGIN=true6. Deploy Your Application
7. Initial Setup
Once deployed:
Database Setup and Configuration
PostgreSQL (Recommended for Production)
PostgreSQL is the recommended database for production Directus deployments. It offers excellent performance, reliability, and feature support.
Setup Steps:
- Provision a PostgreSQL database (either on Klutch.sh or an external provider)
- Create a dedicated database and user:
CREATE DATABASE directus;CREATE USER directus_user WITH ENCRYPTED PASSWORD 'your-secure-password';GRANT ALL PRIVILEGES ON DATABASE directus TO directus_user;- Configure the environment variables as shown in the deployment section
- Directus will automatically create the necessary tables on first startup
MySQL/MariaDB
MySQL and MariaDB are also well-supported:
CREATE DATABASE directus;CREATE USER 'directus_user'@'%' IDENTIFIED BY 'your-secure-password';GRANT ALL PRIVILEGES ON directus.* TO 'directus_user'@'%';FLUSH PRIVILEGES;SQLite (Development Only)
SQLite is suitable for testing and development but not recommended for production:
- No separate database server needed
- File-based storage
- Limited concurrent write performance
- Requires persistent volume for the database file
Persistent Storage Configuration
File Uploads Storage
Directus stores uploaded files in the /directus/uploads directory by default. This must be mounted to a persistent volume:
In Klutch.sh Dashboard:
- Mount Path:
/directus/uploads - Recommended Size: 20GB+ (depending on expected usage)
Database Storage (SQLite Only)
If using SQLite for development:
- Mount Path:
/directus/database - Recommended Size: 5GB
Extensions and Custom Code
For custom extensions:
- Mount Path:
/directus/extensions - Size: 1GB
Environment Variables Reference
Core Settings
| Variable | Description | Required | Default |
|---|---|---|---|
KEY | Security key for encryption | Yes | - |
SECRET | Secret for JWT tokens | Yes | - |
PUBLIC_URL | Public URL of your instance | Yes | - |
PORT | Port Directus listens on | No | 8055 |
Database Settings
| Variable | Description | Required | Example |
|---|---|---|---|
DB_CLIENT | Database type | Yes | pg, mysql, sqlite3 |
DB_HOST | Database host | Yes* | postgres.example.com |
DB_PORT | Database port | Yes* | 5432 |
DB_DATABASE | Database name | Yes | directus |
DB_USER | Database user | Yes* | directus_user |
DB_PASSWORD | Database password | Yes* | - |
*Not required for SQLite
Storage Settings
| Variable | Description | Default |
|---|---|---|
STORAGE_LOCATIONS | Storage driver to use | local |
STORAGE_LOCAL_ROOT | Local storage path | ./uploads |
Security Settings
| Variable | Description | Default |
|---|---|---|
ACCESS_TOKEN_TTL | Access token lifetime | 15m |
REFRESH_TOKEN_TTL | Refresh token lifetime | 7d |
RATE_LIMITER_ENABLED | Enable rate limiting | false |
RATE_LIMITER_POINTS | Requests per duration | 50 |
RATE_LIMITER_DURATION | Duration in seconds | 1 |
Sample Code: Environment Configuration
Create a .env.example file in your repository as a template:
# Core ConfigurationKEY=generate-with-openssl-rand-base64-32SECRET=generate-with-openssl-rand-base64-32PUBLIC_URL=https://your-app.klutch.sh
# Database Configuration (PostgreSQL)DB_CLIENT=pgDB_HOST=your-postgres-host.klutch.shDB_PORT=5432DB_DATABASE=directusDB_USER=directus_userDB_PASSWORD=your-secure-password
# Admin User (Created on First Startup)ADMIN_EMAIL=admin@example.comADMIN_PASSWORD=your-secure-admin-password
# File StorageSTORAGE_LOCATIONS=localSTORAGE_LOCAL_ROOT=/directus/uploads
# Email ConfigurationEMAIL_FROM=noreply@example.comEMAIL_TRANSPORT=smtpEMAIL_SMTP_HOST=smtp.sendgrid.netEMAIL_SMTP_PORT=587EMAIL_SMTP_USER=apikeyEMAIL_SMTP_PASSWORD=your-sendgrid-api-keyEMAIL_SMTP_SECURE=false
# PerformanceCACHE_ENABLED=trueCACHE_TTL=30m
# SecurityRATE_LIMITER_ENABLED=trueRATE_LIMITER_POINTS=50RATE_LIMITER_DURATION=1
# CORSCORS_ENABLED=trueCORS_ORIGIN=trueCORS_METHODS=GET,POST,PATCH,DELETECORS_ALLOWED_HEADERS=Content-Type,Authorization
# LoggingLOG_LEVEL=infoLOG_STYLE=prettyProduction Best Practices
Security
- Use Strong Keys: Generate random keys with
openssl rand -base64 32 - Enable HTTPS: Klutch.sh provides automatic TLS for all deployments
- Configure CORS: Restrict API access to trusted domains
- Enable Rate Limiting: Protect against brute force attacks
- Regular Backups: Back up both database and uploaded files
- Keep Updated: Regularly update to the latest Directus version
Performance
- Use PostgreSQL: Best performance for production workloads
- Enable Caching: Reduces database load and improves response times
- Optimize Images: Use Directus image transformations instead of storing multiple sizes
- Monitor Resources: Use Klutch.sh monitoring to track CPU and memory usage
- Scale Horizontally: Run multiple instances behind a load balancer for high traffic
Monitoring and Maintenance
Monitor your Directus deployment:
# Health check endpointcurl https://your-app.klutch.sh/server/health
# Server infocurl https://your-app.klutch.sh/server/infoSet up alerts in Klutch.sh for:
- High CPU usage (>80%)
- High memory usage (>85%)
- Disk space usage (>80%)
- Application downtime
Backup Strategy
Database Backups:
For PostgreSQL:
pg_dump -h your-postgres-host -U directus_user directus > directus-backup-$(date +%Y%m%d).sqlFor MySQL:
mysqldump -h your-mysql-host -u directus_user -p directus > directus-backup-$(date +%Y%m%d).sqlFile Storage Backups:
Regularly backup the /directus/uploads volume to external storage like S3:
# Example backup scriptaws s3 sync /directus/uploads s3://your-backup-bucket/directus-uploads/Using Nixpacks Customizations
Klutch.sh uses Nixpacks for building applications. If you need to customize the build or start commands without using a Dockerfile, you can use environment variables:
Build-time Variables:
# Custom install commandNIXPACKS_INSTALL_CMD=npm install --production
# Custom build commandNIXPACKS_BUILD_CMD=npm run buildRuntime Variables:
# Custom start commandSTART_COMMAND=node cli.js start
# Node versionNODE_VERSION=20However, for Directus, using a Dockerfile is recommended for better control and reproducibility.
Troubleshooting
Common Issues and Solutions
Connection Refused / 502 Error:
- Verify the internal port is set to 8055
- Check that Directus is binding to
0.0.0.0notlocalhost - Review application logs in Klutch.sh dashboard
Database Connection Failed:
- Verify database credentials are correct
- Ensure database host is accessible from Klutch.sh
- Check database user has proper permissions
- Confirm the database server is running and accepting connections
File Upload Errors:
- Verify persistent volume is mounted to
/directus/uploads - Check volume has sufficient space
- Ensure directory permissions are correct
Admin User Not Created:
- Verify
ADMIN_EMAILandADMIN_PASSWORDare set - Check application logs for errors
- Try creating admin user manually through API
Memory Issues:
- Increase instance size in Klutch.sh dashboard
- Enable caching to reduce memory usage
- Optimize database queries
Debug Mode
Enable debug logging for troubleshooting:
LOG_LEVEL=debugLOG_STYLE=prettyAccess logs through the Klutch.sh dashboard to diagnose issues.
Scaling Your Directus Deployment
Vertical Scaling
Increase resources for a single instance:
- Upgrade to larger compute size in Klutch.sh dashboard
- Monitor CPU and memory usage to determine needs
- Recommended for most small to medium deployments
Horizontal Scaling
Run multiple instances for high availability:
- Deploy multiple instances behind a load balancer
- Use shared database (PostgreSQL or MySQL, not SQLite)
- Use external storage (S3) for uploads
- Configure session storage in Redis or database
For external storage with S3:
STORAGE_LOCATIONS=s3STORAGE_S3_DRIVER=s3STORAGE_S3_KEY=your-access-keySTORAGE_S3_SECRET=your-secret-keySTORAGE_S3_BUCKET=your-bucket-nameSTORAGE_S3_REGION=us-east-1Advanced Configuration
Custom Extensions
Add custom extensions by mounting a volume:
- Create extensions locally
- Mount
/directus/extensionsvolume in Klutch.sh - Upload extensions to the volume
- Restart the application
Webhooks and Automation
Configure webhooks for automation:
WEBHOOKS_ENABLED=trueSet up webhooks in the Directus admin interface to trigger actions on content changes.
Custom Email Templates
Mount custom email templates:
- Create templates directory structure
- Mount volume to
/directus/templates - Configure template path:
EMAIL_TEMPLATES_PATH=/directus/templatesMulti-Tenancy
Deploy separate Directus instances for each tenant:
- Create separate apps in Klutch.sh
- Use separate databases per tenant
- Configure unique public URLs
- Isolate data and access control
Migration from Existing Directus
Migrating Data
Export from existing instance:
- Export database using pg_dump or mysqldump
- Download uploaded files
- Export schema and configuration
Import to Klutch.sh deployment:
- Deploy new Directus instance on Klutch.sh
- Import database:
psql -h new-host -U directus_user directus < backup.sql- Upload files to persistent volume
- Verify data integrity
- Update DNS to point to new instance
Resources
- Directus Official Documentation
- Directus GitHub Repository
- Klutch.sh Quick Start Guide
- Klutch.sh Volumes Documentation
- Klutch.sh Deployments Guide
- Klutch.sh Networking Documentation
Deploying Directus on Klutch.sh provides you with a powerful, scalable content management platform backed by reliable infrastructure. With proper configuration of persistent storage, database connections, and security settings, you can build production-ready applications that leverage Directus’s flexible data management capabilities. The automatic Dockerfile detection and seamless deployment process make it easy to get started, while advanced features like horizontal scaling and external storage support your growth as your application evolves.