# 🔄 Configuration Migration Guide **From Complex Caddy Config to Simple Quantum Config** This guide helps you migrate from complex Caddy v2 configurations to Quantum's simple format, and when to use each format. ## 📋 Quick Decision Matrix | Use Case | Simple Config | Full Config | |----------|---------------|-------------| | Basic reverse proxy | ✅ Perfect | ❌ Overkill | | Static file serving | ✅ Perfect | ❌ Overkill | | File upload/download | ✅ Perfect | ❌ Overkill | | Multiple services on different ports | ✅ Perfect | ❌ Overkill | | Host-based routing | ❌ Use full | ✅ Required | | Path-based routing | ❌ Use full | ✅ Required | | Advanced load balancing | ❌ Use full | ✅ Required | | Health checks | ❌ Use full | ✅ Required | | Custom middleware | ❌ Use full | ✅ Required | ## 🚀 Migration Examples ### 1. Basic Reverse Proxy **Before (Full Config):** ```json { "admin": {"listen": ":2019"}, "apps": { "http": { "servers": { "proxy_server": { "listen": [":8080"], "routes": [ { "handle": [ { "handler": "reverse_proxy", "upstreams": [ {"dial": "localhost:3000"} ] } ] } ] } } } } } ``` **After (Simple Config):** ```json { "proxy": { "localhost:3000": ":8080" } } ``` **Result:** 90% less configuration, same functionality. --- ### 2. Static File Server **Before (Full Config):** ```json { "admin": {"listen": ":2019"}, "apps": { "http": { "servers": { "file_server": { "listen": [":8080"], "routes": [ { "handle": [ { "handler": "file_server", "root": "./public", "browse": true } ] } ] } } } } } ``` **After (Simple Config):** ```json { "static_files": { "./public": ":8080" } } ``` **Result:** 85% less configuration, automatic browse enabled. --- ### 3. Multi-Service Setup **Before (Full Config):** ```json { "admin": {"listen": ":2019"}, "apps": { "http": { "servers": { "api_server": { "listen": [":8080"], "routes": [ { "handle": [ { "handler": "reverse_proxy", "upstreams": [{"dial": "localhost:3000"}] } ] } ] }, "static_server": { "listen": [":8081"], "routes": [ { "handle": [ { "handler": "file_server", "root": "./public" } ] } ] }, "upload_server": { "listen": [":8082"], "routes": [ { "handle": [ { "handler": "file_sync", "root": "./uploads", "enable_upload": true } ] } ] } } } } } ``` **After (Simple Config):** ```json { "proxy": {"localhost:3000": ":8080"}, "static_files": {"./public": ":8081"}, "file_sync": {"./uploads": ":8082"} } ``` **Result:** 95% less configuration, much clearer intent. --- ## ❌ When Simple Config Can't Help ### Host-Based Routing **Full Config Required:** ```json { "apps": { "http": { "servers": { "gateway": { "listen": [":80"], "routes": [ { "match": [ {"matcher": "host", "hosts": ["api.example.com"]} ], "handle": [ { "handler": "reverse_proxy", "upstreams": [{"dial": "api-backend:8080"}] } ] }, { "match": [ {"matcher": "host", "hosts": ["files.example.com"]} ], "handle": [ { "handler": "file_server", "root": "./public" } ] } ] } } } } } ``` **Why Simple Config Can't Help:** - Requires host-based routing logic - Multiple services on same port with different domains - Complex matching rules --- ### Path-Based Routing **Full Config Required:** ```json { "routes": [ { "match": [ {"matcher": "path", "paths": ["/api/*"]} ], "handle": [ { "handler": "reverse_proxy", "upstreams": [{"dial": "api-backend:8080"}] } ] }, { "match": [ {"matcher": "path", "paths": ["/admin/*"]} ], "handle": [ { "handler": "reverse_proxy", "upstreams": [{"dial": "admin-backend:8080"}] } ] }, { "handle": [ { "handler": "file_server", "root": "./public" } ] } ] } ``` **Why Simple Config Can't Help:** - Path-based routing to different backends - Fallback behavior (serve static files for unmatched paths) - Order-dependent route processing --- ## 🔄 Hybrid Approach You can use **both formats** in different situations: ### Development: Simple Config ```json { "proxy": {"localhost:3000": ":8080"} } ``` ### Staging: Simple Config ```json { "proxy": {"localhost:3000": ":8080"}, "static_files": {"./public": ":8081"}, "tls": "auto" } ``` ### Production: Full Config (Complex Routing) ```json { "apps": { "http": { "servers": { "production": { "listen": [":443"], "routes": [ { "match": [ {"matcher": "host", "hosts": ["api.example.com"]}, {"matcher": "path", "paths": ["/v1/*"]} ], "handle": [ { "handler": "reverse_proxy", "upstreams": [ {"dial": "backend1:8080"}, {"dial": "backend2:8080"} ], "load_balancing": { "selection_policy": {"policy": "least_conn"} }, "health_checks": { "active": { "path": "/health", "interval": "30s" } } } ] } ], "tls": { "automation": { "policies": [ { "subjects": ["api.example.com"], "issuer": { "module": "acme", "email": "admin@example.com", "agreed": true } } ] } } } } } } } ``` --- ## 🛠️ Migration Process ### Step 1: Identify Your Use Case Ask yourself: - **Single service per port?** → Use simple config - **Multiple services on same port?** → Use full config - **Need custom routing?** → Use full config - **Need advanced features?** → Use full config ### Step 2: Convert Gradually Start with simple config for basic services: 1. **Extract basic proxy mappings** 2. **Extract static file servers** 3. **Extract file sync handlers** 4. **Keep complex routing in full config** ### Step 3: Test Configuration ```bash # Test simple config quantum --config simple.json # Test full config quantum --config full.json # Quantum auto-detects the format ``` ### Step 4: Validate Quantum provides helpful validation: ```bash ✅ Detected simple configuration format ✅ Detected full Caddy configuration format ❌ Proxy upstream 'localhost' must include port (e.g., 'localhost:3000') ``` --- ## 📊 Migration Checklist ### Before Migration - [ ] Understand current configuration complexity - [ ] Identify which services can use simple config - [ ] Backup current configuration - [ ] Plan migration strategy ### During Migration - [ ] Convert simple services first - [ ] Test each service independently - [ ] Validate configuration with Quantum - [ ] Keep complex routing in full format ### After Migration - [ ] Verify all services work correctly - [ ] Update documentation - [ ] Train team on new configuration format - [ ] Monitor for any issues --- ## 🎯 Best Practices ### Do's ✅ **Start simple** - Use simple config for new services ✅ **Migrate gradually** - Convert one service at a time ✅ **Test thoroughly** - Validate each migration step ✅ **Keep it mixed** - Use both formats as needed ✅ **Document changes** - Update team documentation ### Don'ts ❌ **Don't migrate everything at once** - Too risky ❌ **Don't force simple config** - Use full config when needed ❌ **Don't ignore validation** - Pay attention to error messages ❌ **Don't skip testing** - Always verify functionality ❌ **Don't overcomplicate** - Simple is often better --- ## 🔍 Common Migration Patterns ### Pattern 1: Development → Production ```bash # Development (simple) {"proxy": {"localhost:3000": ":8080"}} # Production (full with health checks) {"apps": {"http": {"servers": {...complex routing...}}}} ``` ### Pattern 2: Microservice Split ```bash # Before (monolith proxy) {"proxy": {"localhost:3000": ":8080"}} # After (multiple services) { "proxy": { "localhost:3001": ":8080", "localhost:3002": ":8081", "localhost:3003": ":8082" } } ``` ### Pattern 3: Add Static Assets ```bash # Before (just proxy) {"proxy": {"localhost:3000": ":8080"}} # After (proxy + static) { "proxy": {"localhost:3000": ":8080"}, "static_files": {"./public": ":8081"} } ``` --- ## 🚀 Next Steps After migration: 1. **Monitor performance** - Ensure no regressions 2. **Update automation** - CI/CD scripts, deployment tools 3. **Train team** - Share new configuration approaches 4. **Iterate** - Continue simplifying where possible 5. **Contribute** - Share experiences with the community --- **Remember: The goal is simplicity where possible, complexity only when necessary.** For more information: - **[SIMPLE-CONFIG.md](SIMPLE-CONFIG.md)** - Complete simple configuration guide - **[QUICKSTART.md](QUICKSTART.md)** - Common usage scenarios - **[docs/api.md](docs/api.md)** - Full API reference