Major improvements: flexible install dir, configurable compose file name for git, enhanced webhook notifications, cross-platform lock, robust rollback, and updated docs.\n\n- Install dir is now user-confirmable and dynamic\n- Added COMPOSE_FILENAME for git stacks\n- Webhook payloads now include git context and rollback events\n- Lock file age check is cross-platform\n- Rollback notifications for success/failure\n- Updated TOML example and documentation\n- Many robustness and UX improvements
This commit is contained in:
parent
f0dba7cc0a
commit
70486907aa
18 changed files with 3788 additions and 1767 deletions
|
|
@ -1,263 +1,404 @@
|
|||
# Watchtower Integration
|
||||
|
||||
This guide covers how to use ComposeSync alongside Watchtower and how to configure them to work together effectively.
|
||||
This guide explains how ComposeSync works with Watchtower and provides recommendations for using both tools together.
|
||||
|
||||
## Understanding the Tools
|
||||
## Overview
|
||||
|
||||
### Watchtower
|
||||
- Monitors running Docker images and updates them when new versions are available in the registry
|
||||
- Focuses on updating container images, not compose file configurations
|
||||
- Works at the container level
|
||||
ComposeSync and Watchtower are complementary tools that serve different purposes:
|
||||
|
||||
### ComposeSync
|
||||
- Monitors remote sources for changes to `docker-compose.yml` files and applies those changes
|
||||
- Focuses on updating compose file configurations, not just images
|
||||
- Works at the compose file level
|
||||
- **ComposeSync**: Updates Docker Compose configuration files
|
||||
- **Watchtower**: Updates Docker container images
|
||||
|
||||
## Recommended Configuration
|
||||
## Key Differences
|
||||
|
||||
For stacks managed by ComposeSync, it's recommended to disable Watchtower to prevent conflicts and race conditions.
|
||||
| Feature | ComposeSync | Watchtower |
|
||||
|---------|-------------|------------|
|
||||
| **Purpose** | Updates compose files | Updates container images |
|
||||
| **Scope** | Configuration changes | Image updates |
|
||||
| **Method** | Downloads new compose files | Pulls new images |
|
||||
| **Safety** | Preserves overrides, rollback on failure | Automatic image updates |
|
||||
| **Control** | Version-controlled updates | Real-time updates |
|
||||
|
||||
### Disabling Watchtower for ComposeSync Stacks
|
||||
## When to Use Each Tool
|
||||
|
||||
Add the following to your `docker-compose.override.yml`:
|
||||
### Use ComposeSync When:
|
||||
- You want to update application configurations
|
||||
- You need to preserve custom overrides
|
||||
- You want version-controlled updates
|
||||
- You're managing complex multi-service stacks
|
||||
- You need rollback capabilities
|
||||
|
||||
```yaml
|
||||
services:
|
||||
your-service:
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false"
|
||||
### Use Watchtower When:
|
||||
- You want automatic image updates
|
||||
- You're running simple containers
|
||||
- You don't need configuration changes
|
||||
- You want real-time updates
|
||||
- You're using `latest` tags
|
||||
|
||||
## Integration Strategies
|
||||
|
||||
### Strategy 1: ComposeSync Only (Recommended)
|
||||
|
||||
Use ComposeSync for both configuration and image updates:
|
||||
|
||||
```toml
|
||||
# Global settings
|
||||
[global]
|
||||
UPDATE_INTERVAL_SECONDS = 3600
|
||||
KEEP_VERSIONS = 10
|
||||
DRY_RUN = false
|
||||
|
||||
# Stack with specific image versions
|
||||
[immich]
|
||||
URL = "https://github.com/immich-app/immich/releases/latest/download/docker-compose.yml"
|
||||
PATH = "/opt/composesync/stacks/immich"
|
||||
TOOL = "wget"
|
||||
```
|
||||
|
||||
### Example Configuration
|
||||
**Benefits:**
|
||||
- Full control over updates
|
||||
- Configuration and images updated together
|
||||
- Automatic rollback on failures
|
||||
- Preserves your customizations
|
||||
|
||||
### Strategy 2: Watchtower Only
|
||||
|
||||
Use Watchtower for automatic image updates:
|
||||
|
||||
```yaml
|
||||
# docker-compose.override.yml for a ComposeSync-managed stack
|
||||
# docker-compose.yml
|
||||
version: '3.8'
|
||||
services:
|
||||
immich-server:
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false"
|
||||
immich-microservices:
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false"
|
||||
immich-machine-learning:
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false"
|
||||
watchtower:
|
||||
image: containrrr/watchtower
|
||||
volumes:
|
||||
- /var/run/docker.sock:/var/run/docker.sock
|
||||
environment:
|
||||
- WATCHTOWER_POLL_INTERVAL=3600
|
||||
- WATCHTOWER_CLEANUP=true
|
||||
restart: unless-stopped
|
||||
```
|
||||
|
||||
**Benefits:**
|
||||
- Real-time image updates
|
||||
- Simple setup
|
||||
- Automatic cleanup
|
||||
|
||||
### Strategy 3: Hybrid Approach
|
||||
|
||||
Use both tools for different purposes:
|
||||
|
||||
```toml
|
||||
# ComposeSync for configuration updates
|
||||
[global]
|
||||
UPDATE_INTERVAL_SECONDS = 86400 # Daily config updates
|
||||
KEEP_VERSIONS = 10
|
||||
DRY_RUN = false
|
||||
|
||||
[immich]
|
||||
URL = "https://github.com/immich-app/immich/releases/latest/download/docker-compose.yml"
|
||||
PATH = "/opt/composesync/stacks/immich"
|
||||
TOOL = "wget"
|
||||
```
|
||||
|
||||
```yaml
|
||||
# Watchtower for image updates
|
||||
version: '3.8'
|
||||
services:
|
||||
watchtower:
|
||||
image: containrrr/watchtower
|
||||
volumes:
|
||||
- /var/run/docker.sock:/var/run/docker.sock
|
||||
environment:
|
||||
- WATCHTOWER_POLL_INTERVAL=3600 # Hourly image updates
|
||||
- WATCHTOWER_CLEANUP=true
|
||||
- WATCHTOWER_LABEL_ENABLE=true
|
||||
restart: unless-stopped
|
||||
```
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Use ComposeSync for:
|
||||
- Applications where the `docker-compose.yml` configuration evolves
|
||||
- Complex stacks with multiple services
|
||||
- Applications that require specific version management
|
||||
- Stacks with custom configurations and overrides
|
||||
### 1. Avoid Conflicts
|
||||
|
||||
### 2. Use Watchtower for:
|
||||
- Simple, self-contained applications
|
||||
- Stacks with static `docker-compose.yml` files
|
||||
- Applications where only image updates are needed
|
||||
- Stacks without complex configurations
|
||||
**Don't use both tools on the same services** - this can cause conflicts and unexpected behavior.
|
||||
|
||||
### 3. Notification Integration:
|
||||
- Configure both tools to send notifications to the same webhook
|
||||
- This provides a unified view of all Docker updates
|
||||
- Helps track what's being updated and when
|
||||
### 2. Use Specific Image Tags
|
||||
|
||||
## Configuration Examples
|
||||
|
||||
### ComposeSync-Managed Stack (Immich)
|
||||
When using ComposeSync, prefer specific image tags over `latest`:
|
||||
|
||||
```yaml
|
||||
# docker-compose.override.yml
|
||||
# Good: Specific version
|
||||
services:
|
||||
immich-server:
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false"
|
||||
environment:
|
||||
- IMMICH_SERVER_URL=http://immich-server:2283
|
||||
networks:
|
||||
- npm_network
|
||||
- immich-backend
|
||||
image: ghcr.io/immich-app/immich-server:v1.75.0
|
||||
|
||||
redis:
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false"
|
||||
networks:
|
||||
- immich-backend
|
||||
|
||||
database:
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false"
|
||||
networks:
|
||||
- immich-backend
|
||||
|
||||
networks:
|
||||
npm_network:
|
||||
external: true
|
||||
immich-backend:
|
||||
name: immich-backend
|
||||
# Avoid: Latest tag
|
||||
services:
|
||||
immich-server:
|
||||
image: ghcr.io/immich-app/immich-server:latest
|
||||
```
|
||||
|
||||
### Watchtower-Managed Stack (Simple App)
|
||||
### 3. Configure Update Intervals
|
||||
|
||||
Set appropriate intervals for each tool:
|
||||
|
||||
```toml
|
||||
# ComposeSync: Less frequent config updates
|
||||
[global]
|
||||
UPDATE_INTERVAL_SECONDS = 86400 # Daily
|
||||
|
||||
[immich]
|
||||
URL = "https://github.com/immich-app/immich/releases/latest/download/docker-compose.yml"
|
||||
PATH = "/opt/composesync/stacks/immich"
|
||||
TOOL = "wget"
|
||||
```
|
||||
|
||||
```yaml
|
||||
# Watchtower: More frequent image updates
|
||||
services:
|
||||
watchtower:
|
||||
environment:
|
||||
- WATCHTOWER_POLL_INTERVAL=3600 # Hourly
|
||||
```
|
||||
|
||||
### 4. Use Labels for Control
|
||||
|
||||
When using Watchtower, use labels to control which containers are updated:
|
||||
|
||||
```yaml
|
||||
# docker-compose.yml
|
||||
version: '3.8'
|
||||
services:
|
||||
simple-app:
|
||||
image: nginx:latest
|
||||
ports:
|
||||
- "8080:80"
|
||||
immich-server:
|
||||
image: ghcr.io/immich-app/immich-server:v1.75.0
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=true"
|
||||
restart: unless-stopped
|
||||
|
||||
database:
|
||||
image: postgres:15
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false" # Don't auto-update
|
||||
restart: unless-stopped
|
||||
```
|
||||
|
||||
## Potential Conflicts
|
||||
|
||||
### Race Conditions
|
||||
- Both tools might try to update the same stack simultaneously
|
||||
- Can lead to inconsistent states
|
||||
- May cause service interruptions
|
||||
|
||||
### Configuration Conflicts
|
||||
- Watchtower might update images while ComposeSync is updating compose files
|
||||
- Can result in version mismatches
|
||||
- May break service dependencies
|
||||
|
||||
### Resource Contention
|
||||
- Both tools competing for Docker resources
|
||||
- Can slow down update processes
|
||||
- May cause timeouts or failures
|
||||
|
||||
## Monitoring Both Tools
|
||||
|
||||
### Unified Logging
|
||||
Monitor both services together:
|
||||
```bash
|
||||
# Watch ComposeSync logs
|
||||
sudo journalctl -u composesync -f
|
||||
|
||||
# Watch Watchtower logs (if running as container)
|
||||
docker logs -f watchtower
|
||||
|
||||
# Or if running as systemd service
|
||||
sudo journalctl -u watchtower -f
|
||||
```
|
||||
|
||||
### Webhook Integration
|
||||
Configure both tools to use the same webhook:
|
||||
```env
|
||||
# ComposeSync webhook
|
||||
NOTIFICATION_WEBHOOK_URL=https://your-webhook-url.com/endpoint
|
||||
|
||||
# Watchtower webhook (in docker-compose.yml)
|
||||
environment:
|
||||
- WATCHTOWER_NOTIFICATIONS=webhook
|
||||
- WATCHTOWER_NOTIFICATION_WEBHOOK_URL=https://your-webhook-url.com/endpoint
|
||||
```
|
||||
|
||||
## Migration Strategy
|
||||
## Migration Scenarios
|
||||
|
||||
### From Watchtower to ComposeSync
|
||||
|
||||
1. **Identify stacks to migrate**
|
||||
- Choose stacks with evolving configurations
|
||||
- Select stacks that need custom overrides
|
||||
If you're currently using Watchtower and want to switch to ComposeSync:
|
||||
|
||||
2. **Configure ComposeSync**
|
||||
- Add stack configuration to `.env`
|
||||
- Set up override files
|
||||
- Test with dry-run mode
|
||||
1. **Stop Watchtower:**
|
||||
```bash
|
||||
docker compose down watchtower
|
||||
```
|
||||
|
||||
3. **Disable Watchtower**
|
||||
- Add labels to disable Watchtower for migrated stacks
|
||||
- Keep Watchtower for simple stacks
|
||||
2. **Configure ComposeSync:**
|
||||
```toml
|
||||
[global]
|
||||
UPDATE_INTERVAL_SECONDS = 3600
|
||||
KEEP_VERSIONS = 10
|
||||
DRY_RUN = false
|
||||
|
||||
4. **Monitor and verify**
|
||||
- Check that updates work correctly
|
||||
- Verify no conflicts occur
|
||||
[your-stack]
|
||||
URL = "https://your-source.com/docker-compose.yml"
|
||||
PATH = "/opt/composesync/stacks/your-stack"
|
||||
TOOL = "wget"
|
||||
```
|
||||
|
||||
3. **Create override file:**
|
||||
```bash
|
||||
sudo nano /opt/composesync/stacks/your-stack/docker-compose.override.yml
|
||||
```
|
||||
|
||||
4. **Start ComposeSync:**
|
||||
```bash
|
||||
sudo systemctl start composesync
|
||||
```
|
||||
|
||||
### From ComposeSync to Watchtower
|
||||
|
||||
1. **Identify simple stacks**
|
||||
- Choose stacks with static configurations
|
||||
- Select stacks that only need image updates
|
||||
If you want to switch from ComposeSync to Watchtower:
|
||||
|
||||
2. **Remove from ComposeSync**
|
||||
- Remove stack configuration from `.env`
|
||||
- Clean up stack directories
|
||||
1. **Stop ComposeSync:**
|
||||
```bash
|
||||
sudo systemctl stop composesync
|
||||
sudo systemctl disable composesync
|
||||
```
|
||||
|
||||
3. **Enable Watchtower**
|
||||
- Remove Watchtower disable labels
|
||||
- Configure Watchtower for the stack
|
||||
2. **Deploy Watchtower:**
|
||||
```yaml
|
||||
version: '3.8'
|
||||
services:
|
||||
watchtower:
|
||||
image: containrrr/watchtower
|
||||
volumes:
|
||||
- /var/run/docker.sock:/var/run/docker.sock
|
||||
environment:
|
||||
- WATCHTOWER_POLL_INTERVAL=3600
|
||||
- WATCHTOWER_CLEANUP=true
|
||||
restart: unless-stopped
|
||||
```
|
||||
|
||||
3. **Update your compose files to use `latest` tags:**
|
||||
```yaml
|
||||
services:
|
||||
your-app:
|
||||
image: your-app:latest
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Update Conflicts
|
||||
### Conflicts Between Tools
|
||||
|
||||
If you see conflicts between the tools:
|
||||
1. Check which tool is managing each stack
|
||||
2. Ensure proper labels are set
|
||||
3. Monitor logs for race conditions
|
||||
4. Consider separating responsibilities more clearly
|
||||
If you experience conflicts:
|
||||
|
||||
### Service Failures
|
||||
```bash
|
||||
# Check which tool is managing your containers
|
||||
docker ps --format "table {{.Names}}\t{{.Image}}\t{{.Status}}"
|
||||
|
||||
If services fail after updates:
|
||||
1. Check which tool performed the update
|
||||
2. Verify the update was applied correctly
|
||||
3. Check for configuration conflicts
|
||||
4. Review logs for error messages
|
||||
# Check ComposeSync logs
|
||||
sudo journalctl -u composesync -f
|
||||
|
||||
# Check Watchtower logs
|
||||
docker logs watchtower
|
||||
```
|
||||
|
||||
### Unexpected Updates
|
||||
|
||||
If containers are updating unexpectedly:
|
||||
|
||||
```bash
|
||||
# Check ComposeSync configuration
|
||||
cat /opt/composesync/config.toml
|
||||
|
||||
# Check Watchtower configuration
|
||||
docker inspect watchtower | grep -A 10 "Env"
|
||||
|
||||
# Check container labels
|
||||
docker inspect your-container | grep -A 5 "Labels"
|
||||
```
|
||||
|
||||
### Performance Issues
|
||||
|
||||
If updates are slow or failing:
|
||||
1. Check resource usage during updates
|
||||
2. Verify network connectivity
|
||||
3. Consider staggering update intervals
|
||||
4. Monitor for resource contention
|
||||
If you experience performance issues:
|
||||
|
||||
## Advanced Configuration
|
||||
```bash
|
||||
# Check update frequency
|
||||
grep "UPDATE_INTERVAL_SECONDS" /opt/composesync/config.toml
|
||||
|
||||
### Selective Updates
|
||||
# Check Watchtower interval
|
||||
docker inspect watchtower | grep "WATCHTOWER_POLL_INTERVAL"
|
||||
|
||||
You can configure both tools to update different aspects:
|
||||
# Monitor resource usage
|
||||
docker stats
|
||||
```
|
||||
|
||||
## Recommendations
|
||||
|
||||
### For Production Environments
|
||||
|
||||
**Use ComposeSync** for production environments because:
|
||||
- Better control over updates
|
||||
- Automatic rollback on failures
|
||||
- Preserves your customizations
|
||||
- Version-controlled updates
|
||||
- Better monitoring and logging
|
||||
|
||||
### For Development Environments
|
||||
|
||||
**Use Watchtower** for development environments because:
|
||||
- Faster iteration
|
||||
- Real-time updates
|
||||
- Simpler setup
|
||||
- Less configuration overhead
|
||||
|
||||
### For Mixed Environments
|
||||
|
||||
**Use the hybrid approach** with:
|
||||
- ComposeSync for critical production stacks
|
||||
- Watchtower for development and testing stacks
|
||||
- Clear separation of responsibilities
|
||||
|
||||
## Example Configurations
|
||||
|
||||
### Production Setup (ComposeSync Only)
|
||||
|
||||
```toml
|
||||
# /opt/composesync/config.toml
|
||||
[global]
|
||||
UPDATE_INTERVAL_SECONDS = 86400 # Daily updates
|
||||
KEEP_VERSIONS = 15
|
||||
DRY_RUN = false
|
||||
NOTIFICATION_WEBHOOK_URL = "https://your-webhook.com/endpoint"
|
||||
|
||||
[immich]
|
||||
URL = "https://github.com/immich-app/immich/releases/latest/download/docker-compose.yml"
|
||||
PATH = "/opt/composesync/stacks/immich"
|
||||
TOOL = "wget"
|
||||
|
||||
[portainer]
|
||||
URL = "https://github.com/portainer/portainer-compose.git"
|
||||
PATH = "/opt/composesync/stacks/portainer"
|
||||
TOOL = "git"
|
||||
GIT_SUBPATH = "compose/docker-compose.yml"
|
||||
GIT_REF = "main"
|
||||
```
|
||||
|
||||
### Development Setup (Watchtower Only)
|
||||
|
||||
```yaml
|
||||
# ComposeSync handles compose file updates
|
||||
# Watchtower handles image updates for specific services
|
||||
# docker-compose.yml
|
||||
version: '3.8'
|
||||
services:
|
||||
app:
|
||||
watchtower:
|
||||
image: containrrr/watchtower
|
||||
volumes:
|
||||
- /var/run/docker.sock:/var/run/docker.sock
|
||||
environment:
|
||||
- WATCHTOWER_POLL_INTERVAL=1800 # 30 minutes
|
||||
- WATCHTOWER_CLEANUP=true
|
||||
- WATCHTOWER_LABEL_ENABLE=true
|
||||
restart: unless-stopped
|
||||
|
||||
dev-app:
|
||||
image: your-dev-app:latest
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=true"
|
||||
- "com.centurylinklabs.watchtower.scope=app"
|
||||
|
||||
database:
|
||||
restart: unless-stopped
|
||||
```
|
||||
|
||||
### Hybrid Setup
|
||||
|
||||
```toml
|
||||
# ComposeSync for production stacks
|
||||
[global]
|
||||
UPDATE_INTERVAL_SECONDS = 86400
|
||||
KEEP_VERSIONS = 10
|
||||
|
||||
[production-app]
|
||||
URL = "https://github.com/user/production-app.git"
|
||||
PATH = "/opt/composesync/stacks/production"
|
||||
TOOL = "git"
|
||||
GIT_REF = "main"
|
||||
```
|
||||
|
||||
```yaml
|
||||
# Watchtower for development stacks
|
||||
services:
|
||||
watchtower:
|
||||
image: containrrr/watchtower
|
||||
volumes:
|
||||
- /var/run/docker.sock:/var/run/docker.sock
|
||||
environment:
|
||||
- WATCHTOWER_POLL_INTERVAL=3600
|
||||
- WATCHTOWER_CLEANUP=true
|
||||
- WATCHTOWER_LABEL_ENABLE=true
|
||||
restart: unless-stopped
|
||||
|
||||
dev-app:
|
||||
image: your-dev-app:latest
|
||||
labels:
|
||||
- "com.centurylinklabs.watchtower.enable=false"
|
||||
```
|
||||
|
||||
### Update Scheduling
|
||||
|
||||
Coordinate update schedules to avoid conflicts:
|
||||
|
||||
```env
|
||||
# ComposeSync: Check every 6 hours
|
||||
UPDATE_INTERVAL_SECONDS=21600
|
||||
|
||||
# Watchtower: Check every 12 hours (different schedule)
|
||||
# Configure in Watchtower settings
|
||||
```
|
||||
|
||||
### Notification Filtering
|
||||
|
||||
Use different webhook endpoints for different tools:
|
||||
```env
|
||||
# ComposeSync notifications
|
||||
NOTIFICATION_WEBHOOK_URL=https://webhook.com/composesync
|
||||
|
||||
# Watchtower notifications (separate endpoint)
|
||||
# Configure in Watchtower settings
|
||||
```
|
||||
|
||||
This allows you to handle notifications differently based on the source.
|
||||
- "com.centurylinklabs.watchtower.enable=true"
|
||||
restart: unless-stopped
|
||||
```
|
||||
Loading…
Add table
Add a link
Reference in a new issue