feature - 6 - fix production compose issues
This commit is contained in:
parent
630a8cc73f
commit
71212ef9da
5 changed files with 123 additions and 54 deletions
47
Dockerfile
47
Dockerfile
|
|
@ -36,25 +36,24 @@ ENV APP_ENV=production \
|
||||||
MAIL_MAILER=smtp \
|
MAIL_MAILER=smtp \
|
||||||
MAIL_ENCRYPTION=tls
|
MAIL_ENCRYPTION=tls
|
||||||
|
|
||||||
# Copy composer files and install PHP dependencies
|
# Copy application code first
|
||||||
COPY composer.json composer.lock ./
|
COPY . .
|
||||||
|
|
||||||
|
# Install PHP dependencies (production only)
|
||||||
RUN composer install --no-dev --no-interaction --optimize-autoloader
|
RUN composer install --no-dev --no-interaction --optimize-autoloader
|
||||||
|
|
||||||
# Copy package files and install Node dependencies
|
# Install ALL Node dependencies (including dev for building)
|
||||||
COPY package*.json ./
|
RUN npm ci
|
||||||
RUN npm ci --omit=dev
|
|
||||||
|
|
||||||
# Copy application code
|
|
||||||
COPY . .
|
|
||||||
|
|
||||||
# Build frontend assets
|
# Build frontend assets
|
||||||
RUN npm run build
|
RUN npm run build
|
||||||
|
|
||||||
|
# Remove node_modules after build to save space
|
||||||
|
RUN rm -rf node_modules
|
||||||
|
|
||||||
# Laravel optimizations
|
# Laravel optimizations
|
||||||
RUN php artisan config:cache \
|
RUN php artisan config:cache \
|
||||||
&& php artisan route:cache \
|
&& php artisan route:cache \
|
||||||
&& php artisan view:cache \
|
|
||||||
&& php artisan livewire:discover \
|
|
||||||
&& composer dump-autoload --optimize
|
&& composer dump-autoload --optimize
|
||||||
|
|
||||||
# Set permissions
|
# Set permissions
|
||||||
|
|
@ -93,5 +92,31 @@ EXPOSE 8000
|
||||||
HEALTHCHECK --interval=30s --timeout=3s --start-period=5s --retries=3 \
|
HEALTHCHECK --interval=30s --timeout=3s --start-period=5s --retries=3 \
|
||||||
CMD curl -f http://localhost:8000/up || exit 1
|
CMD curl -f http://localhost:8000/up || exit 1
|
||||||
|
|
||||||
|
# Create startup script for production
|
||||||
|
RUN cat > /start-prod.sh <<'EOF'
|
||||||
|
#!/bin/sh
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# Wait for database to be ready
|
||||||
|
echo "Waiting for database..."
|
||||||
|
for i in $(seq 1 30); do
|
||||||
|
if php artisan db:monitor --database=mysql 2>/dev/null | grep -q "OK"; then
|
||||||
|
echo "Database is ready!"
|
||||||
|
break
|
||||||
|
fi
|
||||||
|
echo "Waiting for database... ($i/30)"
|
||||||
|
sleep 2
|
||||||
|
done
|
||||||
|
|
||||||
|
# Run migrations
|
||||||
|
echo "Running migrations..."
|
||||||
|
php artisan migrate --force || echo "Migrations failed or already up-to-date"
|
||||||
|
|
||||||
# Start FrankenPHP
|
# Start FrankenPHP
|
||||||
CMD ["frankenphp", "run", "--config", "/etc/caddy/Caddyfile"]
|
exec frankenphp run --config /etc/caddy/Caddyfile
|
||||||
|
EOF
|
||||||
|
|
||||||
|
RUN chmod +x /start-prod.sh
|
||||||
|
|
||||||
|
# Start with our script
|
||||||
|
CMD ["/start-prod.sh"]
|
||||||
|
|
|
||||||
20
Makefile
20
Makefile
|
|
@ -38,21 +38,17 @@ logs-db: ## Show database logs
|
||||||
docker compose logs -f db
|
docker compose logs -f db
|
||||||
|
|
||||||
# Production Commands
|
# Production Commands
|
||||||
.PHONY: prod
|
|
||||||
prod: ## Start production environment
|
|
||||||
docker compose -f docker-compose.prod.yml up -d
|
|
||||||
|
|
||||||
.PHONY: prod-build
|
.PHONY: prod-build
|
||||||
prod-build: ## Build production image
|
prod-build: ## Build production image for Codeberg
|
||||||
docker compose -f docker-compose.prod.yml build
|
./bin/build-push.sh
|
||||||
|
|
||||||
.PHONY: prod-stop
|
.PHONY: prod-build-tag
|
||||||
prod-stop: ## Stop production environment
|
prod-build-tag: ## Build with specific tag (usage: make prod-build-tag TAG=v1.0.0)
|
||||||
docker compose -f docker-compose.prod.yml down
|
./bin/build-push.sh $(TAG)
|
||||||
|
|
||||||
.PHONY: prod-logs
|
.PHONY: prod-login
|
||||||
prod-logs: ## Show production logs
|
prod-login: ## Login to Codeberg registry
|
||||||
docker compose -f docker-compose.prod.yml logs -f
|
podman login codeberg.org
|
||||||
|
|
||||||
# Laravel Commands
|
# Laravel Commands
|
||||||
.PHONY: artisan
|
.PHONY: artisan
|
||||||
|
|
|
||||||
29
bin/build-push.sh
Executable file
29
bin/build-push.sh
Executable file
|
|
@ -0,0 +1,29 @@
|
||||||
|
#!/bin/bash
|
||||||
|
# Build and push production image to Codeberg
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
# Configuration
|
||||||
|
REGISTRY="codeberg.org"
|
||||||
|
NAMESPACE="lvl0"
|
||||||
|
IMAGE_NAME="dish-planner"
|
||||||
|
TAG="${1:-latest}"
|
||||||
|
|
||||||
|
echo "🔨 Building production image..."
|
||||||
|
podman build -f Dockerfile -t ${REGISTRY}/${NAMESPACE}/${IMAGE_NAME}:${TAG} .
|
||||||
|
|
||||||
|
echo "📤 Pushing to Codeberg registry..."
|
||||||
|
echo "Please ensure you're logged in to Codeberg:"
|
||||||
|
echo " podman login codeberg.org"
|
||||||
|
|
||||||
|
podman push ${REGISTRY}/${NAMESPACE}/${IMAGE_NAME}:${TAG}
|
||||||
|
|
||||||
|
echo "✅ Done! Image pushed to ${REGISTRY}/${NAMESPACE}/${IMAGE_NAME}:${TAG}"
|
||||||
|
echo ""
|
||||||
|
echo "To deploy in production:"
|
||||||
|
echo "1. Copy docker-compose.prod.yml to your server"
|
||||||
|
echo "2. Set required environment variables:"
|
||||||
|
echo " - APP_KEY (generate with: openssl rand -base64 32)"
|
||||||
|
echo " - APP_URL"
|
||||||
|
echo " - DB_DATABASE, DB_USERNAME, DB_PASSWORD, DB_ROOT_PASSWORD"
|
||||||
|
echo "3. Run: docker-compose -f docker-compose.prod.yml up -d"
|
||||||
|
|
@ -1,12 +1,7 @@
|
||||||
# Production Docker Compose
|
# Production Docker Compose
|
||||||
version: '3.8'
|
|
||||||
|
|
||||||
services:
|
services:
|
||||||
app:
|
app:
|
||||||
build:
|
image: codeberg.org/lvl0/dish-planner:latest
|
||||||
context: .
|
|
||||||
dockerfile: Dockerfile
|
|
||||||
image: dishplanner:latest
|
|
||||||
container_name: dishplanner_app
|
container_name: dishplanner_app
|
||||||
restart: always
|
restart: always
|
||||||
ports:
|
ports:
|
||||||
|
|
@ -30,8 +25,7 @@ services:
|
||||||
- app_storage:/app/storage
|
- app_storage:/app/storage
|
||||||
- app_logs:/app/storage/logs
|
- app_logs:/app/storage/logs
|
||||||
depends_on:
|
depends_on:
|
||||||
db:
|
- db
|
||||||
condition: service_healthy
|
|
||||||
networks:
|
networks:
|
||||||
- dishplanner
|
- dishplanner
|
||||||
healthcheck:
|
healthcheck:
|
||||||
|
|
@ -50,22 +44,10 @@ services:
|
||||||
MYSQL_USER: "${DB_USERNAME}"
|
MYSQL_USER: "${DB_USERNAME}"
|
||||||
MYSQL_PASSWORD: "${DB_PASSWORD}"
|
MYSQL_PASSWORD: "${DB_PASSWORD}"
|
||||||
MYSQL_ROOT_PASSWORD: "${DB_ROOT_PASSWORD}"
|
MYSQL_ROOT_PASSWORD: "${DB_ROOT_PASSWORD}"
|
||||||
# MariaDB performance tuning
|
|
||||||
MYSQL_INITDB_SKIP_TZINFO: 1
|
|
||||||
MYSQL_CHARACTER_SET_SERVER: utf8mb4
|
|
||||||
MYSQL_COLLATION_SERVER: utf8mb4_unicode_ci
|
|
||||||
volumes:
|
volumes:
|
||||||
- db_data:/var/lib/mysql
|
- db_data:/var/lib/mysql
|
||||||
- ./database/backups:/backups # For backup scripts
|
|
||||||
networks:
|
networks:
|
||||||
- dishplanner
|
- dishplanner
|
||||||
healthcheck:
|
|
||||||
test: ["CMD", "healthcheck.sh", "--connect", "--innodb_initialized"]
|
|
||||||
interval: 30s
|
|
||||||
timeout: 10s
|
|
||||||
retries: 3
|
|
||||||
start_period: 60s
|
|
||||||
# No ports exposed - only accessible within network
|
|
||||||
|
|
||||||
# Optional: Redis for production caching/sessions
|
# Optional: Redis for production caching/sessions
|
||||||
# redis:
|
# redis:
|
||||||
|
|
@ -105,9 +87,6 @@ services:
|
||||||
networks:
|
networks:
|
||||||
dishplanner:
|
dishplanner:
|
||||||
driver: bridge
|
driver: bridge
|
||||||
ipam:
|
|
||||||
config:
|
|
||||||
- subnet: 172.20.0.0/16
|
|
||||||
|
|
||||||
volumes:
|
volumes:
|
||||||
db_data:
|
db_data:
|
||||||
|
|
|
||||||
50
shell.nix
50
shell.nix
|
|
@ -52,6 +52,45 @@ pkgs.mkShell {
|
||||||
podman-compose exec app php artisan "$@"
|
podman-compose exec app php artisan "$@"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
prod-build() {
|
||||||
|
local TAG="''${1:-latest}"
|
||||||
|
local REGISTRY="codeberg.org"
|
||||||
|
local NAMESPACE="lvl0"
|
||||||
|
local IMAGE_NAME="dish-planner"
|
||||||
|
|
||||||
|
echo "🔨 Building production image..."
|
||||||
|
podman build -f Dockerfile -t ''${REGISTRY}/''${NAMESPACE}/''${IMAGE_NAME}:''${TAG} .
|
||||||
|
|
||||||
|
echo "✅ Build complete: ''${REGISTRY}/''${NAMESPACE}/''${IMAGE_NAME}:''${TAG}"
|
||||||
|
echo "Run 'prod-push' to push to Codeberg"
|
||||||
|
}
|
||||||
|
|
||||||
|
prod-push() {
|
||||||
|
local TAG="''${1:-latest}"
|
||||||
|
local REGISTRY="codeberg.org"
|
||||||
|
local NAMESPACE="lvl0"
|
||||||
|
local IMAGE_NAME="dish-planner"
|
||||||
|
|
||||||
|
echo "📤 Pushing to Codeberg registry..."
|
||||||
|
if podman push ''${REGISTRY}/''${NAMESPACE}/''${IMAGE_NAME}:''${TAG}; then
|
||||||
|
echo "✅ Image pushed to ''${REGISTRY}/''${NAMESPACE}/''${IMAGE_NAME}:''${TAG}"
|
||||||
|
else
|
||||||
|
echo "❌ Failed to push image. Did you run 'prod-build' first?"
|
||||||
|
echo " Also make sure you're logged in with 'prod-login'"
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
prod-build-push() {
|
||||||
|
local TAG="''${1:-latest}"
|
||||||
|
prod-build "$TAG" && prod-push "$TAG"
|
||||||
|
}
|
||||||
|
|
||||||
|
prod-login() {
|
||||||
|
echo "📝 Logging into Codeberg registry..."
|
||||||
|
podman login codeberg.org
|
||||||
|
}
|
||||||
|
|
||||||
echo "🚀 Dish Planner Development Environment"
|
echo "🚀 Dish Planner Development Environment"
|
||||||
echo "======================================="
|
echo "======================================="
|
||||||
echo "PHP: $(php --version | head -n1)"
|
echo "PHP: $(php --version | head -n1)"
|
||||||
|
|
@ -59,17 +98,18 @@ pkgs.mkShell {
|
||||||
echo "Podman: $(podman --version)"
|
echo "Podman: $(podman --version)"
|
||||||
echo "Podman-compose: $(podman-compose --version 2>/dev/null || echo 'checking...')"
|
echo "Podman-compose: $(podman-compose --version 2>/dev/null || echo 'checking...')"
|
||||||
echo ""
|
echo ""
|
||||||
echo "Quick commands:"
|
echo "Development commands:"
|
||||||
echo " rebuild - Full rebuild (removes volumes)"
|
echo " rebuild - Full rebuild (removes volumes)"
|
||||||
echo " rebuild-quick - Quick rebuild (keeps volumes)"
|
echo " rebuild-quick - Quick rebuild (keeps volumes)"
|
||||||
echo " logs [service] - Follow logs (default: all)"
|
echo " logs [service] - Follow logs (default: all)"
|
||||||
echo " shell - Enter app container"
|
echo " shell - Enter app container"
|
||||||
echo " artisan [cmd] - Run artisan commands"
|
echo " artisan [cmd] - Run artisan commands"
|
||||||
echo ""
|
echo ""
|
||||||
echo "Standard commands:"
|
echo "Production commands:"
|
||||||
echo " podman-compose up -d - Start containers"
|
echo " prod-login - Login to Codeberg registry"
|
||||||
echo " podman-compose down - Stop containers"
|
echo " prod-build [tag] - Build production image (default: latest)"
|
||||||
echo " make dev - Start via Makefile"
|
echo " prod-push [tag] - Push image to Codeberg"
|
||||||
|
echo " prod-build-push - Build and push in one command"
|
||||||
echo ""
|
echo ""
|
||||||
|
|
||||||
# Auto-start prompt
|
# Auto-start prompt
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue