Changed health check to try without password first, then with Docker Secret.
This handles both scenarios where password might not be immediately available
or where the Secret read might fail in health check context.
Changes:
- Use CMD-SHELL instead of CMD for shell expansion support
- Try 'redis-cli ping' first (no auth)
- Fallback to authenticated ping if first attempt fails
- Properly quote password from Docker Secret
This is the eleventh cumulative fix for production deployment pipeline.
Related: commit 477fe67 (initial Redis health check fix)
Previous health check used incorrect command: redis-cli --raw incr ping
This increments a counter instead of checking Redis health.
Changed to proper health check:
- Use standard redis-cli ping command
- Authenticate with password from Docker Secret
- Verify PONG response with grep
This is the ninth cumulative fix for production deployment pipeline.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
Docker named volumes cannot create mount points inside read-only directories.
Previous configuration attempted to mount storage and var-data volumes at subdirectories
inside a read-only base mount (/var/www/html:ro), causing deployment failures.
Changes:
- php service: Changed /var/www/html mount from :ro to :rw, removed storage volume
- queue-worker service: Changed mount to :rw, removed storage and var-data volumes
- scheduler service: Changed mount to :rw, removed storage and var-data volumes
Security maintained through:
- Container runs as non-root user (appuser via gosu)
- Security hardening (no-new-privileges, dropped capabilities)
- Rsync deployment from trusted source
This is the eighth cumulative fix for production deployment pipeline.
Remove separate .env file mounts from php, queue-worker, and scheduler
services to fix read-only filesystem mount conflict.
The .env file is already included in the rsync deployment at
/home/deploy/michaelschiemer/current/.env and is accessible through
the main application code mount. Separate file mounts are redundant
and cause Docker mount conflicts because they attempt to create mount
points inside read-only parent directories.
Error fixed:
- error mounting '/var/www/html/.env': read-only file system
Services fixed:
- php: removed .env mount (line 154)
- queue-worker: removed .env mount (line 254)
- scheduler: removed .env mount (line 327)
Added 'build: null' to web, php, and queue-worker services in docker-compose.production.yml
to explicitly remove build sections inherited from base config.
This fixes 'lstat /home/deploy/deployment/stacks/application/docker/php: no such file or directory'
error during deployment, as production servers only have docker-compose files, not build context.
Registry-based deployment should pull pre-built images, not attempt to build on production server.
Production deployment was failing because docker-compose.production.yml
had build: sections but no image: references. This caused Docker Compose
to attempt building on the server, which failed because the docker/
directory doesn't exist in the deployment location.
Changes:
- Add image: git.michaelschiemer.de:5000/framework:latest to web, php, and queue-worker services
- Removed build: section from php service (no longer needed)
- Remove test comment from ShowHome.php
The deployment script's sed command (line 1259-1260 in build-image.yml)
now successfully finds and updates the image: tags with the correct
version from the registry.
Related to: Production deployment error "docker/php: no such file or directory"
- Mount /home/deploy/michaelschiemer/current:/var/www/html:ro in php and queue-worker services
- This allows deployment via rsync without requiring Docker image rebuild
- Storage volume still mounted as writable overlay for runtime data
- Change default DB_DRIVER to 'pgsql' for PostgreSQL
Deployment Architecture:
- rsync deploys code to /home/deploy/michaelschiemer/releases/{timestamp}
- Atomic symlink switch to /home/deploy/michaelschiemer/current
- PHP containers mount current/ for immediate code updates
- No rebuild needed - code changes are live after symlink switch
Benefits:
- Faster deployments (no Docker rebuild)
- Code changes reflected immediately
- Zero-downtime releases
- Easy rollback via symlink change
- Create AnsibleDeployStage using framework's Process module for secure command execution
- Integrate AnsibleDeployStage into DeploymentPipelineCommands for production deployments
- Add force_deploy flag support in Ansible playbook to override stale locks
- Use PHP deployment module as orchestrator (php console.php deploy:production)
- Fix ErrorAggregationInitializer to use Environment class instead of $_ENV superglobal
Architecture:
- BuildStage → AnsibleDeployStage → HealthCheckStage for production
- Process module provides timeout, error handling, and output capture
- Ansible playbook supports rollback via rollback-git-based.yml
- Zero-downtime deployments with health checks