|
| 1 | +# Docker Setup Guide - Production-Ready Worklenz |
| 2 | + |
| 3 | +This repository now includes a **production-ready Docker setup** with enterprise-grade features including nginx reverse proxy, SSL/TLS support, Redis caching, automated backups, and comprehensive management scripts. |
| 4 | + |
| 5 | +## 🚀 Quick Start |
| 6 | + |
| 7 | +### Option 1: Automated Setup (Recommended) |
| 8 | +```bash |
| 9 | +./quick-setup.sh |
| 10 | +``` |
| 11 | +This script will: |
| 12 | +- Create `.env` file from `.env.example` |
| 13 | +- Auto-generate all security secrets |
| 14 | +- Configure URLs based on your domain |
| 15 | +- Set up SSL certificates (self-signed for localhost, Let's Encrypt for production) |
| 16 | +- Install and start Worklenz |
| 17 | + |
| 18 | +### Option 2: Manual Setup |
| 19 | +```bash |
| 20 | +# 1. Copy environment file |
| 21 | +cp .env.example .env |
| 22 | + |
| 23 | +# 2. Edit .env and set required values: |
| 24 | +# - DB_PASSWORD |
| 25 | +# - SESSION_SECRET (generate with: openssl rand -hex 32) |
| 26 | +# - COOKIE_SECRET (generate with: openssl rand -hex 32) |
| 27 | +# - JWT_SECRET (generate with: openssl rand -hex 32) |
| 28 | +# - AWS_SECRET_ACCESS_KEY (MinIO password) |
| 29 | +# - REDIS_PASSWORD |
| 30 | + |
| 31 | +# 3. Start services (Express mode - includes PostgreSQL, Redis, MinIO) |
| 32 | +docker compose --profile express up -d |
| 33 | + |
| 34 | +# 4. For production with SSL |
| 35 | +docker compose --profile express --profile ssl up -d |
| 36 | +``` |
| 37 | + |
| 38 | +## 📋 What's New |
| 39 | + |
| 40 | +### 1. **Production-Ready Docker Compose** |
| 41 | +- **Nginx reverse proxy** with SSL/TLS termination |
| 42 | +- **Redis cache** for session management |
| 43 | +- **Automated database backups** with retention policies |
| 44 | +- **Health checks** for all services |
| 45 | +- **Network isolation** (separate backend/frontend networks) |
| 46 | +- **Security hardening** (non-root users, no-new-privileges) |
| 47 | +- **Profile-based deployment** (express/advanced modes) |
| 48 | + |
| 49 | +### 2. **Enhanced Dockerfiles** |
| 50 | + |
| 51 | +#### Backend Dockerfile |
| 52 | +- Multi-stage build for smaller images |
| 53 | +- Non-root user (`worklenz`) for security |
| 54 | +- `tini` init system for proper signal handling |
| 55 | +- Health check endpoint |
| 56 | +- `libvips42` for image processing |
| 57 | +- Proper log directory with permissions |
| 58 | + |
| 59 | +#### Frontend Dockerfile |
| 60 | +- Multi-stage build with Alpine Linux |
| 61 | +- Non-root user for security |
| 62 | +- Runtime environment injection (supports reCAPTCHA, Google Login, etc.) |
| 63 | +- `tini` init system |
| 64 | +- Health check endpoint |
| 65 | +- Optimized `serve` configuration |
| 66 | + |
| 67 | +### 3. **Nginx Configuration** |
| 68 | +- **SSL/TLS support** (Let's Encrypt + self-signed) |
| 69 | +- **Rate limiting** (API and login endpoints) |
| 70 | +- **WebSocket support** for Socket.IO |
| 71 | +- **Security headers** (HSTS, CSP, X-Frame-Options, etc.) |
| 72 | +- **Gzip compression** |
| 73 | +- **Static asset caching** |
| 74 | +- **Upstream load balancing** |
| 75 | + |
| 76 | +### 4. **Database Initialization** |
| 77 | +- **Backup restoration** on startup |
| 78 | +- **Migration tracking** system |
| 79 | +- **Proper error handling** |
| 80 | +- **Initialization marker** to prevent re-runs |
| 81 | + |
| 82 | +### 5. **Management Scripts** |
| 83 | + |
| 84 | +#### `manage.sh` - Comprehensive Management |
| 85 | +```bash |
| 86 | +./manage.sh [command] |
| 87 | + |
| 88 | +Commands: |
| 89 | + install Install Worklenz (auto-generates secrets) |
| 90 | + start Start all services |
| 91 | + stop Stop all services |
| 92 | + restart Restart all services |
| 93 | + status Show service status |
| 94 | + logs View service logs |
| 95 | + backup Create database backup |
| 96 | + restore Restore from backup |
| 97 | + upgrade Upgrade to latest version |
| 98 | + configure Interactive configuration |
| 99 | + auto-configure Auto-configure from .env DOMAIN |
| 100 | + ssl Manage SSL certificates |
| 101 | + build Build Docker images locally |
| 102 | + push Push images to Docker Hub |
| 103 | + build-push Build and push in one step |
| 104 | +``` |
| 105 | + |
| 106 | +#### `quick-setup.sh` - Automated Installation |
| 107 | +One-command setup with auto-generated secrets and SSL configuration. |
| 108 | + |
| 109 | +## 🏗️ Architecture |
| 110 | + |
| 111 | +``` |
| 112 | +┌─────────────────────────────────────────────────────────┐ |
| 113 | +│ Nginx (Port 80/443) │ |
| 114 | +│ SSL/TLS, Rate Limiting, Caching │ |
| 115 | +└────────────────────┬────────────────────────────────────┘ |
| 116 | + │ |
| 117 | + ┌────────────┴────────────┐ |
| 118 | + │ │ |
| 119 | +┌───────▼────────┐ ┌───────▼────────┐ |
| 120 | +│ Frontend │ │ Backend │ |
| 121 | +│ (Node:22) │ │ (Node:20) │ |
| 122 | +│ Port: 5000 │ │ Port: 3000 │ |
| 123 | +└────────────────┘ └───────┬────────┘ |
| 124 | + │ |
| 125 | + ┌────────────┼────────────┐ |
| 126 | + │ │ │ |
| 127 | + ┌───────▼──┐ ┌────▼────┐ ┌───▼────┐ |
| 128 | + │PostgreSQL│ │ Redis │ │ MinIO │ |
| 129 | + │ Port: │ │ Port: │ │ Port: │ |
| 130 | + │ 5432 │ │ 6379 │ │ 9000 │ |
| 131 | + └──────────┘ └─────────┘ └────────┘ |
| 132 | +``` |
| 133 | + |
| 134 | +## 🔧 Configuration |
| 135 | + |
| 136 | +### Deployment Modes |
| 137 | + |
| 138 | +#### Express Mode (Default) |
| 139 | +All services bundled together - PostgreSQL, Redis, MinIO included. |
| 140 | +```bash |
| 141 | +docker compose --profile express up -d |
| 142 | +``` |
| 143 | + |
| 144 | +#### Advanced Mode |
| 145 | +Use external services (AWS S3, Azure Blob, external PostgreSQL). |
| 146 | +```bash |
| 147 | +# Set in .env: |
| 148 | +DEPLOYMENT_MODE=advanced |
| 149 | +STORAGE_PROVIDER=s3 # or azure |
| 150 | + |
| 151 | +docker compose up -d |
| 152 | +``` |
| 153 | + |
| 154 | +### Environment Variables |
| 155 | + |
| 156 | +Key variables in `.env`: |
| 157 | +- `DOMAIN` - Your domain (localhost for local testing) |
| 158 | +- `DEPLOYMENT_MODE` - express or advanced |
| 159 | +- `STORAGE_PROVIDER` - s3 or azure |
| 160 | +- `ENABLE_SSL` - true/false |
| 161 | +- `BACKUP_RETENTION_DAYS` - Days to keep backups (default: 30) |
| 162 | + |
| 163 | +See `.env.example` for complete documentation. |
| 164 | + |
| 165 | +## 🔐 Security Features |
| 166 | + |
| 167 | +1. **Non-root containers** - All services run as non-root users |
| 168 | +2. **Security options** - `no-new-privileges` enabled |
| 169 | +3. **Network isolation** - Backend network is internal-only |
| 170 | +4. **SSL/TLS** - Let's Encrypt for production, self-signed for localhost |
| 171 | +5. **Rate limiting** - API and login endpoints protected |
| 172 | +6. **Security headers** - HSTS, CSP, X-Frame-Options, etc. |
| 173 | +7. **Secret management** - Auto-generated secure secrets |
| 174 | + |
| 175 | +## 💾 Backup & Restore |
| 176 | + |
| 177 | +### Automated Backups |
| 178 | +Database backups run automatically every 24 hours with configurable retention: |
| 179 | +```bash |
| 180 | +# Enable backup service |
| 181 | +docker compose --profile backup up -d |
| 182 | +``` |
| 183 | + |
| 184 | +### Manual Backup |
| 185 | +```bash |
| 186 | +./manage.sh backup |
| 187 | +``` |
| 188 | + |
| 189 | +### Restore from Backup |
| 190 | +```bash |
| 191 | +./manage.sh restore |
| 192 | +``` |
| 193 | + |
| 194 | +Backups are stored in `./backups/` directory and compressed with gzip. |
| 195 | + |
| 196 | +## 🌐 SSL/TLS Setup |
| 197 | + |
| 198 | +### Localhost (Self-Signed) |
| 199 | +Automatically configured for localhost testing. |
| 200 | + |
| 201 | +### Production Domain (Let's Encrypt) |
| 202 | +```bash |
| 203 | +# 1. Set domain in .env |
| 204 | +DOMAIN=your-domain.com |
| 205 | +ENABLE_SSL=true |
| 206 | +LETSENCRYPT_EMAIL=your-email@domain.com |
| 207 | + |
| 208 | +# 2. Point DNS A record to your server IP |
| 209 | + |
| 210 | +# 3. Start with SSL profile |
| 211 | +docker compose --profile express --profile ssl up -d |
| 212 | +``` |
| 213 | + |
| 214 | +Or use the management script: |
| 215 | +```bash |
| 216 | +./manage.sh ssl |
| 217 | +``` |
| 218 | + |
| 219 | +## 📊 Monitoring |
| 220 | + |
| 221 | +### View Service Status |
| 222 | +```bash |
| 223 | +./manage.sh status |
| 224 | +# or |
| 225 | +docker compose ps |
| 226 | +``` |
| 227 | + |
| 228 | +### View Logs |
| 229 | +```bash |
| 230 | +./manage.sh logs |
| 231 | +# or |
| 232 | +docker compose logs -f [service-name] |
| 233 | +``` |
| 234 | + |
| 235 | +### Health Checks |
| 236 | +All services include health checks: |
| 237 | +- Backend: `http://localhost:3000/public/health` |
| 238 | +- Frontend: `http://localhost:5000` |
| 239 | +- PostgreSQL: `pg_isready` |
| 240 | +- Redis: `redis-cli ping` |
| 241 | +- MinIO: `/minio/health/live` |
| 242 | + |
| 243 | +## 🔄 Upgrading |
| 244 | + |
| 245 | +```bash |
| 246 | +./manage.sh upgrade |
| 247 | +``` |
| 248 | + |
| 249 | +This will: |
| 250 | +1. Create a backup |
| 251 | +2. Pull latest images |
| 252 | +3. Rebuild containers |
| 253 | +4. Restart services |
| 254 | + |
| 255 | +## 🐳 Building Custom Images |
| 256 | + |
| 257 | +### Build Locally |
| 258 | +```bash |
| 259 | +./manage.sh build |
| 260 | +``` |
| 261 | + |
| 262 | +### Push to Docker Hub |
| 263 | +```bash |
| 264 | +./manage.sh push |
| 265 | +``` |
| 266 | + |
| 267 | +### Build and Push |
| 268 | +```bash |
| 269 | +./manage.sh build-push |
| 270 | +``` |
| 271 | + |
| 272 | +## 📁 Directory Structure |
| 273 | + |
| 274 | +``` |
| 275 | +worklenz/ |
| 276 | +├── docker-compose.yaml # Main compose file |
| 277 | +├── .env.example # Environment template |
| 278 | +├── manage.sh # Management script |
| 279 | +├── quick-setup.sh # Quick setup script |
| 280 | +├── nginx/ # Nginx configuration |
| 281 | +│ ├── nginx.conf |
| 282 | +│ ├── conf.d/ |
| 283 | +│ │ └── worklenz.conf |
| 284 | +│ └── ssl/ # SSL certificates |
| 285 | +├── scripts/ # Database scripts |
| 286 | +│ └── db-init-wrapper.sh |
| 287 | +├── backups/ # Database backups |
| 288 | +├── worklenz-backend/ |
| 289 | +│ └── Dockerfile # Backend Dockerfile |
| 290 | +└── worklenz-frontend/ |
| 291 | + └── Dockerfile # Frontend Dockerfile |
| 292 | +``` |
| 293 | + |
| 294 | +## ❓ FAQ |
| 295 | + |
| 296 | +### What if Docker is not installed? |
| 297 | +You must install Docker and Docker Desktop (for Windows/Mac) or Docker Engine (for Linux). Follow the official [Docker installation guide](https://docs.docker.com/get-docker/). |
| 298 | + |
| 299 | +### How do I install Docker Compose? |
| 300 | +Modern Docker installations (Docker Desktop and latest Docker Engine) include Docker Compose by default. You can check by running `docker compose version`. If you need to install it separately, see the [Compose installation guide](https://docs.docker.com/compose/install/). |
| 301 | + |
| 302 | +### Why do I get "permission denied" errors on Linux? |
| 303 | +On Linux, you may need to run Docker commands with `sudo` or add your user to the `docker` group: |
| 304 | +```bash |
| 305 | +sudo usermod -aG docker $USER |
| 306 | +``` |
| 307 | +*Note: You may need to log out and back in for this change to take effect.* |
| 308 | + |
| 309 | +### I'm on Windows, why isn't it working? |
| 310 | +For the best experience on Windows, we recommend using **WSL2** (Windows Subsystem for Linux). |
| 311 | +1. Install [WSL2](https://learn.microsoft.com/en-us/windows/wsl/install). |
| 312 | +2. Install [Docker Desktop for Windows](https://docs.docker.com/desktop/install/windows-install/). |
| 313 | +3. Enable WSL2 integration in Docker Desktop Settings -> Resources -> WSL Integration. |
| 314 | + |
| 315 | +### How do I check if my hardware supports virtualization? |
| 316 | +- **Windows**: Check Performance tab in Task Manager. Look for "Virtualization: Enabled". |
| 317 | +- **Linux**: Run `lscpu | grep Virtualization`. |
| 318 | + |
| 319 | +## 🆘 Troubleshooting |
| 320 | + |
| 321 | +### Services won't start |
| 322 | +```bash |
| 323 | +# Check logs |
| 324 | +docker compose logs |
| 325 | + |
| 326 | +# Check service status |
| 327 | +docker compose ps |
| 328 | + |
| 329 | +# Restart services |
| 330 | +./manage.sh restart |
| 331 | +``` |
| 332 | + |
| 333 | +### Database initialization fails |
| 334 | +```bash |
| 335 | +# Check database logs |
| 336 | +docker compose logs postgres |
| 337 | + |
| 338 | +# Verify database scripts exist |
| 339 | +ls -la worklenz-backend/database/sql/ |
| 340 | +``` |
| 341 | + |
| 342 | +### SSL certificate issues |
| 343 | +```bash |
| 344 | +# For Let's Encrypt |
| 345 | +./manage.sh ssl |
| 346 | + |
| 347 | +# Check certificate info |
| 348 | +openssl x509 -in nginx/ssl/cert.pem -text -noout |
| 349 | +``` |
| 350 | + |
| 351 | +### Port conflicts |
| 352 | +```bash |
| 353 | +# Change ports in .env |
| 354 | +HTTP_PORT=8080 |
| 355 | +HTTPS_PORT=8443 |
| 356 | +``` |
| 357 | + |
| 358 | +## 📝 Migration from Old Setup |
| 359 | + |
| 360 | +If you're migrating from the old `docker-compose.yml`: |
| 361 | + |
| 362 | +1. **Backup your data**: |
| 363 | + ```bash |
| 364 | + docker compose exec db pg_dump -U postgres worklenz_db > backup.sql |
| 365 | + ``` |
| 366 | + |
| 367 | +2. **Stop old containers**: |
| 368 | + ```bash |
| 369 | + docker compose -f docker-compose.yml down |
| 370 | + ``` |
| 371 | + |
| 372 | +3. **Copy your `.env` files** to the new structure |
| 373 | + |
| 374 | +4. **Start new setup**: |
| 375 | + ```bash |
| 376 | + docker compose --profile express up -d |
| 377 | + ``` |
| 378 | + |
| 379 | +5. **Restore data if needed**: |
| 380 | + ```bash |
| 381 | + ./manage.sh restore |
| 382 | + ``` |
| 383 | + |
| 384 | +## 🤝 Contributing |
| 385 | + |
| 386 | +When making changes to Docker configuration: |
| 387 | +1. Test with both express and advanced modes |
| 388 | +2. Verify health checks work |
| 389 | +3. Test SSL setup for both localhost and production |
| 390 | +4. Update this documentation |
0 commit comments