# TimeSafari Docker Setup

## Overview

This directory contains Docker configuration files for building and deploying TimeSafari across different environments with full configurability.

## Files

- `Dockerfile` - Multi-stage Docker build for TimeSafari
- `nginx.conf` - Main nginx configuration with security headers
- `default.conf` - Production server configuration
- `staging.conf` - Staging server configuration with relaxed caching
- `docker-compose.yml` - Multi-environment Docker Compose setup
- `.dockerignore` - Optimizes build context
- `run.sh` - Convenient script to run different configurations

## Quick Start

### Using the Run Script (Recommended)

```bash
# Development mode with hot reloading
./docker/run.sh dev

# Staging mode for testing
./docker/run.sh staging

# Production mode
./docker/run.sh production

# Custom mode with environment variables
BUILD_MODE=staging ./docker/run.sh custom

# Show build arguments for a mode
./docker/run.sh dev --build-args

# Custom port and environment file
./docker/run.sh staging --port 9000 --env .env.test
```

### Using Docker Compose

```bash
# Development environment with hot reloading
docker-compose up dev

# Staging environment
docker-compose up staging

# Production environment
docker-compose up production

# Custom environment with variables
BUILD_MODE=staging docker-compose up custom
```

## Build Commands

### Manual Docker Build

```bash
# Build production image (default)
docker build -t timesafari:latest .

# Build staging image
docker build --build-arg BUILD_MODE=staging -t timesafari:staging .

# Build development image
docker build --build-arg BUILD_MODE=development -t timesafari:dev .

# Build with custom arguments
docker build \
  --build-arg BUILD_MODE=staging \
  --build-arg NODE_ENV=staging \
  
  -t timesafari:custom .
```

### Run Container

```bash
# Run production container
docker run -d -p 80:80 timesafari:latest

# Run with environment file
docker run -d -p 80:80 --env-file .env.production timesafari:latest

# Run with custom environment variables
docker run -d -p 80:80 \
  -e VITE_APP_SERVER=https://myapp.com \
  -e VITE_DEFAULT_ENDORSER_API_SERVER=https://api.myapp.com \
  timesafari:latest
```

## Configuration Options

### Build Arguments

The Dockerfile supports these build arguments:

| Argument | Default | Description |
|----------|---------|-------------|
| `BUILD_MODE` | `production` | Build mode: development, staging, or production |
| `NODE_ENV` | `production` | Node.js environment |
| `VITE_PLATFORM` | `web` | Vite platform type |
| PWA | `enabled` | Automatically enabled for web platforms |

### Environment Variables

Docker Compose supports these environment variables:

| Variable | Default | Description |
|----------|---------|-------------|
| `BUILD_MODE` | `production` | Build mode |
| `NODE_ENV` | `production` | Node environment |
| `VITE_PLATFORM` | `web` | Vite platform |
| PWA | `enabled` | Automatically enabled for web platforms |
| `DEV_PORT` | `5173` | Development port |
| `STAGING_PORT` | `8080` | Staging port |
| `PROD_PORT` | `80` | Production port |
| `DEV_ENV_FILE` | `.env.development` | Development env file |
| `TEST_ENV_FILE` | `.env.test` | Test env file |
| `PROD_ENV_FILE` | `.env.production` | Production env file |

### Environment Files

Create environment files for different deployments:

```bash
# .env.development
VITE_APP_SERVER=https://dev.timesafari.app
VITE_DEFAULT_ENDORSER_API_SERVER=https://dev-api.endorser.ch
VITE_DEFAULT_IMAGE_API_SERVER=https://dev-image-api.timesafari.app
VITE_DEFAULT_PARTNER_API_SERVER=https://dev-partner-api.endorser.ch
VITE_DEFAULT_PUSH_SERVER=https://dev.timesafari.app
VITE_PASSKEYS_ENABLED=true

# .env.test
VITE_APP_SERVER=https://staging.timesafari.app
VITE_DEFAULT_ENDORSER_API_SERVER=https://staging-api.endorser.ch
VITE_DEFAULT_IMAGE_API_SERVER=https://staging-image-api.timesafari.app
VITE_DEFAULT_PARTNER_API_SERVER=https://staging-partner-api.endorser.ch
VITE_DEFAULT_PUSH_SERVER=https://staging.timesafari.app
VITE_PASSKEYS_ENABLED=true

# .env.production
VITE_APP_SERVER=https://timesafari.app
VITE_DEFAULT_ENDORSER_API_SERVER=https://api.endorser.ch
VITE_DEFAULT_IMAGE_API_SERVER=https://image-api.timesafari.app
VITE_DEFAULT_PARTNER_API_SERVER=https://partner-api.endorser.ch
VITE_DEFAULT_PUSH_SERVER=https://timesafari.app
VITE_PASSKEYS_ENABLED=true
```

## Build Modes

### Development Mode
- **Target**: `development`
- **Features**: Hot reloading, development server
- **Port**: 5173
- **Caching**: Disabled
- **Use Case**: Local development

```bash
./docker/run.sh dev
# or
docker build --target development -t timesafari:dev .
```

### Staging Mode
- **Target**: `staging`
- **Features**: Production build with relaxed caching
- **Port**: 8080 (mapped from 80)
- **Caching**: Short-term (1 hour)
- **Use Case**: Testing and QA

```bash
./docker/run.sh staging
# or
docker build --build-arg BUILD_MODE=staging -t timesafari:staging .
```

### Production Mode
- **Target**: `production`
- **Features**: Optimized production build
- **Port**: 80
- **Caching**: Long-term (1 year for assets)
- **Use Case**: Live deployment

```bash
./docker/run.sh production
# or
docker build -t timesafari:latest .
```

### Custom Mode
- **Target**: Configurable via `BUILD_TARGET`
- **Features**: Fully configurable
- **Port**: Configurable via `CUSTOM_PORT`
- **Use Case**: Special deployments

```bash
BUILD_MODE=staging NODE_ENV=staging ./docker/run.sh custom
```

## Advanced Usage

### Custom Build Configuration

```bash
# Build with specific environment
docker build \
  --build-arg BUILD_MODE=staging \
  --build-arg NODE_ENV=staging \
  
  -t timesafari:staging-no-pwa .

# Run with custom configuration
docker run -d -p 9000:80 \
  -e VITE_APP_SERVER=https://test.example.com \
  timesafari:staging-no-pwa
```

### Docker Compose with Custom Variables

```bash
# Set environment variables
export BUILD_MODE=staging
export NODE_ENV=staging
export STAGING_PORT=9000
export STAGING_ENV_FILE=.env.test

# Run staging with custom config
docker-compose up staging
```

### Multi-Environment Deployment

```bash
# Development
./docker/run.sh dev

# Staging in another terminal
./docker/run.sh staging --port 8081

# Production in another terminal
./docker/run.sh production --port 8082
```

## Security Features

### Built-in Security
- **Non-root user execution**: All containers run as non-root users
- **Security headers**: XSS protection, content type options, frame options
- **Rate limiting**: API request rate limiting
- **File access restrictions**: Hidden files and backup files blocked
- **Minimal attack surface**: Alpine Linux base images

### Security Headers
- `X-Frame-Options: SAMEORIGIN`
- `X-Content-Type-Options: nosniff`
- `X-XSS-Protection: 1; mode=block`
- `Referrer-Policy: strict-origin-when-cross-origin`
- `Content-Security-Policy`: Comprehensive CSP policy

## Performance Optimizations

### Caching Strategy
- **Static assets**: 1 year cache with immutable flag (production)
- **HTML files**: 1 hour cache (production) / no cache (staging)
- **Service worker**: No cache
- **Manifest**: 1 day cache (production) / 1 hour cache (staging)

### Compression
- **Gzip compression**: Enabled for text-based files
- **Compression level**: 6 (balanced)
- **Minimum size**: 1024 bytes

### Nginx Optimizations
- **Sendfile**: Enabled for efficient file serving
- **TCP optimizations**: nopush and nodelay enabled
- **Keepalive**: 65 second timeout
- **Worker processes**: Auto-detected based on CPU cores

## Health Checks

### Built-in Health Checks
All services include health checks that:
- Check every 30 seconds
- Timeout after 10 seconds
- Retry 3 times before marking unhealthy
- Start checking after 40 seconds

### Health Check Endpoints
- **Production/Staging**: `http://localhost/health`
- **Development**: `http://localhost:5173`

## SSL/HTTPS Setup

### SSL Certificates
For SSL deployment, create an `ssl` directory with certificates:

```bash
mkdir ssl
# Copy your certificates to ssl/ directory
cp your-cert.pem ssl/
cp your-key.pem ssl/
```

### SSL Configuration
Use the `production-ssl` service in docker-compose:

```bash
docker-compose up production-ssl
```

## Monitoring and Logging

### Log Locations
- **Access logs**: `/var/log/nginx/access.log`
- **Error logs**: `/var/log/nginx/error.log`

### Log Format
```
$remote_addr - $remote_user [$time_local] "$request" 
$status $body_bytes_sent "$http_referer" 
"$http_user_agent" "$http_x_forwarded_for"
```

### Log Levels
- **Production**: `warn` level
- **Staging**: `debug` level
- **Development**: Full logging

## Troubleshooting

### Common Issues

#### Build Failures
```bash
# Check build logs
docker build -t timesafari:latest . 2>&1 | tee build.log

# Verify dependencies
docker run --rm timesafari:latest npm list --depth=0

# Check build arguments
./docker/run.sh dev --build-args
```

#### Container Won't Start
```bash
# Check container logs
docker logs <container_id>

# Check health status
docker inspect <container_id> | grep -A 10 "Health"

# Verify port availability
netstat -tulpn | grep :80
```

#### Environment Variables Not Set
```bash
# Check environment in container
docker exec <container_id> env | grep VITE_

# Verify .env file
cat .env.production

# Check build arguments
./docker/run.sh production --build-args
```

#### Performance Issues
```bash
# Check container resources
docker stats <container_id>

# Check nginx configuration
docker exec <container_id> nginx -t

# Monitor access logs
docker exec <container_id> tail -f /var/log/nginx/access.log
```

### Debug Commands

#### Container Debugging
```bash
# Enter running container
docker exec -it <container_id> /bin/sh

# Check nginx status
docker exec <container_id> nginx -t

# Check file permissions
docker exec <container_id> ls -la /usr/share/nginx/html
```

#### Network Debugging
```bash
# Check container network
docker network inspect bridge

# Test connectivity
docker exec <container_id> curl -I http://localhost

# Check DNS resolution
docker exec <container_id> nslookup google.com
```

## Production Deployment

### Recommended Production Setup
1. **Use specific version tags**: `timesafari:1.0.0`
2. **Implement health checks**: Already included
3. **Configure proper logging**: Use external log aggregation
4. **Set up reverse proxy**: Use nginx-lb service
5. **Use Docker secrets**: For sensitive data

### Production Commands
```bash
# Build with specific version
docker build -t timesafari:1.0.0 .

# Run with production settings
docker run -d \
  --name timesafari \
  -p 80:80 \
  --restart unless-stopped \
  --env-file .env.production \
  timesafari:1.0.0

# Update production deployment
docker stop timesafari
docker rm timesafari
docker build -t timesafari:1.0.1 .
docker run -d --name timesafari -p 80:80 --restart unless-stopped --env-file .env.production timesafari:1.0.1
```

## Development Workflow

### Local Development
```bash
# Start development environment
./docker/run.sh dev

# Make changes to code (hot reloading enabled)
# Access at http://localhost:5173

# Stop development environment
docker-compose down dev
```

### Testing Changes
```bash
# Build and test staging
./docker/run.sh staging

# Test production build locally
./docker/run.sh production
```

### Continuous Integration
```bash
# Build and test in CI
docker build -t timesafari:test .
docker run -d --name timesafari-test -p 8080:80 timesafari:test

# Run tests against container
curl -f http://localhost:8080/health

# Cleanup
docker stop timesafari-test
docker rm timesafari-test
```

## Best Practices

### Security
- Always use non-root users
- Keep base images updated
- Scan images for vulnerabilities
- Use secrets for sensitive data
- Implement proper access controls

### Performance
- Use multi-stage builds
- Optimize layer caching
- Minimize image size
- Use appropriate base images
- Implement proper caching

### Monitoring
- Use health checks
- Monitor resource usage
- Set up log aggregation
- Implement metrics collection
- Use proper error handling

### Maintenance
- Regular security updates
- Monitor for vulnerabilities
- Keep dependencies updated
- Document configuration changes
- Test deployment procedures 