Docker Tutorial #9: Praxis – Shopware 6 Entwicklungsumgebung mit Docker
Vollständige Shopware 6 Docker-Umgebung
Eine produktionsreife Docker-Setup für Shopware 6 Development mit allen benötigten Services.
Projektstruktur
shopware-docker/
├── docker-compose.yml
├── docker/
│ ├── Dockerfile
│ ├── nginx/
│ │ └── default.conf
│ └── php/
│ ├── php.ini
│ └── php-fpm.conf
├── shopware/
│ └── (Shopware 6 Code)
└── .env
Dockerfile für Shopware 6
docker/Dockerfile:
FROM php:8.2-fpm-alpine
# Installiere Abhängigkeiten
RUN apk add --no-cache \
bash \
git \
curl \
zip \
unzip \
libzip-dev \
libpng-dev \
libwebp-dev \
libjpeg-turbo-dev \
freetype-dev \
icu-dev \
oniguruma-dev \
libxml2-dev \
nodejs \
npm
# PHP Extensions
RUN docker-php-ext-configure gd --with-freetype --with-jpeg --with-webp && \
docker-php-ext-install -j$(nproc) \
pdo pdo_mysql \
mysqli \
zip \
gd \
intl \
opcache \
bcmath \
soap \
mbstring
# Composer installieren
COPY --from=composer:latest /usr/bin/composer /usr/bin/composer
# Shopware CLI (optional)
RUN curl -1sLf 'https://dl.cloudsmith.io/public/friendsofshopware/stable/setup.alpine.sh' | bash && \
apk add shopware-cli
# PHP Konfiguration
COPY docker/php/php.ini /usr/local/etc/php/conf.d/shopware.ini
# Working Directory
WORKDIR /var/www/html
# User für bessere Sicherheit
RUN adduser -D -u 1000 shopware && \
chown -R shopware:shopware /var/www
USER shopware
EXPOSE 9000
docker-compose.yml
version: '3.8'
services:
# PHP-FPM für Shopware
app:
build:
context: .
dockerfile: docker/Dockerfile
volumes:
- ./shopware:/var/www/html
- /var/www/html/vendor
- /var/www/html/var
environment:
DATABASE_URL: mysql://shopware:shopware@mysql:3306/shopware
APP_URL: http://localhost:8000
APP_ENV: dev
MAILER_URL: smtp://mailhog:1025
OPENSEARCH_URL: http://opensearch:9200
REDIS_URL: redis://redis:6379
depends_on:
mysql:
condition: service_healthy
redis:
condition: service_started
networks:
- shopware-network
# Nginx Webserver
nginx:
image: nginx:alpine
ports:
- "8000:80"
volumes:
- ./shopware:/var/www/html:ro
- ./docker/nginx/default.conf:/etc/nginx/conf.d/default.conf:ro
depends_on:
- app
networks:
- shopware-network
# MySQL Datenbank
mysql:
image: mysql:8.0
ports:
- "3306:3306"
environment:
MYSQL_ROOT_PASSWORD: root
MYSQL_DATABASE: shopware
MYSQL_USER: shopware
MYSQL_PASSWORD: shopware
command: >
--character-set-server=utf8mb4
--collation-server=utf8mb4_unicode_ci
--sql-mode="STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_ENGINE_SUBSTITUTION"
--innodb-buffer-pool-size=512M
--max-allowed-packet=64M
volumes:
- mysql_data:/var/lib/mysql
healthcheck:
test: ["CMD", "mysqladmin", "ping", "-h", "localhost", "-u", "shopware", "-pshopware"]
interval: 5s
timeout: 3s
retries: 10
networks:
- shopware-network
# Redis für Caching
redis:
image: redis:alpine
ports:
- "6379:6379"
volumes:
- redis_data:/data
networks:
- shopware-network
# OpenSearch für Produktsuche
opensearch:
image: opensearchproject/opensearch:2
environment:
discovery.type: single-node
plugins.security.disabled: "true"
OPENSEARCH_JAVA_OPTS: "-Xms512m -Xmx512m"
ports:
- "9200:9200"
volumes:
- opensearch_data:/usr/share/opensearch/data
networks:
- shopware-network
# Mailhog für E-Mail-Testing
mailhog:
image: mailhog/mailhog
ports:
- "1025:1025"
- "8025:8025"
networks:
- shopware-network
# Adminer für Datenbank-Management
adminer:
image: adminer
ports:
- "8080:8080"
environment:
ADMINER_DEFAULT_SERVER: mysql
depends_on:
- mysql
networks:
- shopware-network
# Node.js für Asset Building (optional)
node:
image: node:18-alpine
working_dir: /var/www/html
volumes:
- ./shopware:/var/www/html
command: sh -c "npm install && npm run watch"
networks:
- shopware-network
profiles:
- dev
volumes:
mysql_data:
redis_data:
opensearch_data:
networks:
shopware-network:
driver: bridge
Nginx Konfiguration
docker/nginx/default.conf:
upstream php-upstream {
server app:9000;
}
server {
listen 80;
server_name localhost;
root /var/www/html/public;
index index.php;
# Logging
access_log /var/log/nginx/shopware-access.log;
error_log /var/log/nginx/shopware-error.log;
location / {
try_files $uri /index.php$is_args$args;
}
# PHP-FPM
location ~ ^/(index|shopware-installer\.phar)\.php(/|$) {
fastcgi_pass php-upstream;
fastcgi_split_path_info ^(.+\.php)(/.*)$;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
fastcgi_param DOCUMENT_ROOT $realpath_root;
fastcgi_buffer_size 128k;
fastcgi_buffers 4 256k;
fastcgi_busy_buffers_size 256k;
internal;
}
# Deny alle anderen PHP-Dateien
location ~ \.php$ {
return 404;
}
# Assets mit Caching
location ~* \.(jpg|jpeg|png|gif|svg|ico|css|js|woff|woff2|ttf|eot)$ {
expires 1y;
add_header Cache-Control "public, immutable";
access_log off;
}
client_max_body_size 128M;
}
PHP Konfiguration
docker/php/php.ini:
[PHP]
memory_limit = 512M
max_execution_time = 300
upload_max_filesize = 128M
post_max_size = 128M
max_input_vars = 10000
date.timezone = Europe/Berlin
[opcache]
opcache.enable = 1 opcache.enable_cli = 1 opcache.memory_consumption = 256 opcache.interned_strings_buffer = 20 opcache.max_accelerated_files = 100000 opcache.validate_timestamps = 0 opcache.revalidate_freq = 0 opcache.save_comments = 1
Installation
1. Docker-Umgebung starten
docker compose up -d
2. Shopware 6 installieren
# In den App-Container
docker compose exec app bash
# Shopware per Composer installieren
composer create-project shopware/production:6.5.* .
# Oder Clone von Git
git clone https://github.com/shopware/platform shopware6
cd shopware6
composer install
# Shopware Setup
bin/console system:install --basic-setup --create-database
bin/console system:generate-jwt-secret
bin/console plugin:refresh
bin/console theme:refresh
bin/console assets:install
# Admin-User erstellen
bin/console user:create admin admin@example.com --admin
3. Frontend Build
# Storefront bauen
./bin/build-storefront.sh
# Oder mit Node-Container
docker compose --profile dev up node
4. Zugriff
- Storefront: http://localhost:8000
- Admin: http://localhost:8000/admin
- Mailhog: http://localhost:8025
- Adminer: http://localhost:8080
Entwickler-Workflow
Plugin-Entwicklung
# In den Container
docker compose exec app bash
# Plugin erstellen
bin/console plugin:create SwagExamplePlugin
# Plugin installieren
bin/console plugin:refresh
bin/console plugin:install SwagExamplePlugin --activate
# Cache leeren
bin/console cache:clear
Theme-Entwicklung
# Theme erstellen
bin/console theme:create MyTheme
# Theme zuweisen
bin/console theme:change MyTheme
# Theme kompilieren
bin/console theme:compile
# Watch Mode mit Node
docker compose --profile dev up node
Database Management
# SQL Import
docker compose exec -T mysql mysql -u shopware -pshopware shopware < backup.sql
# SQL Export
docker compose exec mysql mysqldump -u shopware -pshopware shopware > backup.sql
# Direkt in Container
docker compose exec mysql mysql -u shopware -pshopware shopware
Debugging
Xdebug aktivieren
docker/php/php.ini erweitern:
[xdebug]
zend_extension=xdebug.so
xdebug.mode=debug,develop
xdebug.client_host=host.docker.internal
xdebug.client_port=9003
xdebug.start_with_request=yes
xdebug.idekey=PHPSTORM
Dockerfile ergänzen:
RUN apk add --no-cache $PHPIZE_DEPS && \
pecl install xdebug && \
docker-php-ext-enable xdebug
PHPStorm Konfiguration
- Einstellungen → PHP → Servers
- Name:
docker - Host:
localhost - Port:
8000 - Debugger:
Xdebug - Path Mappings:
/var/www/html→./shopware
Production Deployment
docker-compose.prod.yml
version: '3.8'
services:
app:
environment:
APP_ENV: prod
deploy:
resources:
limits:
cpus: '2.0'
memory: 2G
nginx:
deploy:
resources:
limits:
cpus: '1.0'
memory: 512M
mysql:
command: >
--character-set-server=utf8mb4
--collation-server=utf8mb4_unicode_ci
--innodb-buffer-pool-size=2G
Starten:
docker compose -f docker-compose.yml -f docker-compose.prod.yml up -d
Backup & Restore
Vollständiges Backup
#!/bin/bash
# backup.sh
DATE=$(date +%Y%m%d_%H%M%S)
BACKUP_DIR="./backups/$DATE"
mkdir -p $BACKUP_DIR
# Datenbank
docker compose exec -T mysql mysqldump -u shopware -pshopware shopware > $BACKUP_DIR/database.sql
# Files
docker compose exec app tar czf - /var/www/html/files /var/www/html/media > $BACKUP_DIR/files.tar.gz
echo "Backup erstellt: $BACKUP_DIR"
Restore
#!/bin/bash
# restore.sh
BACKUP_DIR=$1
# Datenbank
docker compose exec -T mysql mysql -u shopware -pshopware shopware < $BACKUP_DIR/database.sql
# Files
cat $BACKUP_DIR/files.tar.gz | docker compose exec -T app tar xzf - -C /
Performance-Optimierung
1. OpCache aktivieren
Bereits in php.ini konfiguriert.
2. Redis für Sessions
config/packages/framework.yaml:
framework:
session:
handler_id: 'redis://redis:6379/0'
3. HTTP Cache aktivieren
bin/console system:config:set core.httpCache.enabled true
bin/console system:config:set core.httpCache.warmUpEnabled true
4. Asset Building optimieren
# Production Build
./bin/build-storefront.sh
# Mit Optimierung
NODE_ENV=production npm run build
Troubleshooting
Cache-Probleme
docker compose exec app bin/console cache:clear
docker compose exec app bin/console cache:warmup
Permissions-Fehler
docker compose exec -u root app chown -R shopware:shopware /var/www/html
MySQL Connection Error
# Health Check
docker compose ps mysql
# Logs prüfen
docker compose logs mysql
# Verbindung testen
docker compose exec app nc -zv mysql 3306
Best Practices
- Volumes für Performance:
vendorundvarals Volumes - Health Checks: Für MySQL und OpenSearch
- Separate Netzwerke: Frontend/Backend trennen
- Environment Variables: Niemals Secrets committen
- Multi-Stage Builds: Für kleinere Images
- Logging: Strukturiertes Logging aktivieren
- Monitoring: Mit Prometheus/Grafana
Zusammenfassung
Sie haben gelernt:
- Vollständige Shopware 6 Docker-Umgebung
- Development und Production Setup
- Plugin- und Theme-Entwicklung
- Debugging mit Xdebug
- Backup und Restore
- Performance-Optimierung

Author: Andreas Lang
Andreas Lang konzentriert sich seit zwei Jahrzehnten auf die Webentwicklung und Webdesign mit dem Schwerpunkt PHP, Laravel und Javascript und betreut seine Kunden mit Herz und Seele in allen Bereichen von Entwicklung, Design, Suchmaschinenoptimierung, IT-Recht, IT-Sicherheit etc.

