docker -v
docker-compose -v
If not installed, run:
# Install Docker
sudo yum install -y yum-utils
sudo yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
sudo yum install -y docker-ce docker-ce-cli containerd.io
sudo systemctl start docker
sudo systemctl enable docker
# Install Docker Compose
sudo curl -L "https://github.com/docker/compose/releases/latest/download/docker-compose-$(uname -
s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose
docker-compose.yml
production-ready stack with Nextcloud, OnlyOffice, MariaDB, Redis, Nginx, and Certbot.
version: '3.7'
services:
db:
image: mariadb
container_name: nextcloud-db
restart: always
volumes:
- db_data:/var/lib/mysql
environment:
MYSQL_ROOT_PASSWORD: rootpass
MYSQL_DATABASE: nextcloud
MYSQL_USER: nextcloud
MYSQL_PASSWORD: ncpass
redis:
image: redis:alpine
container_name: nextcloud-redis
restart: always
app:
image: nextcloud
container_name: nextcloud-app
depends_on:
- db
- redis
restart: always
volumes:
- nextcloud_data:/var/www/html
environment:
REDIS_HOST: redis
networks:
- internal
onlyoffice:
image: onlyoffice/documentserver
container_name: onlyoffice
restart: always
networks:
- internal
nginx:
image: nginx:alpine
container_name: nextcloud-nginx
restart: always
ports:
- "80:80"
- "443:443"
volumes:
- ./nginx/nginx.conf:/etc/nginx/conf.d/default.conf
- certbot-etc:/etc/letsencrypt
- certbot-var:/var/lib/letsencrypt
- nextcloud_data:/var/www/html:ro
depends_on:
- app
- onlyoffice
certbot:
image: certbot/certbot
container_name: certbot
volumes:
- certbot-etc:/etc/letsencrypt
- certbot-var:/var/lib/letsencrypt
- ./nginx:/var/www/certbot
entrypoint: "/bin/sh -c 'trap exit TERM; while :; do sleep 12h & wait $${!}; certbot renew;
done'"
volumes:
db_data:
nextcloud_data:
certbot-etc:
certbot-var:
networks:
internal:
driver: bridge
Nginx SSL + Reverse Proxy
nginx/nginx.conf (Example for HTTPS with Let's Encrypt):
server {
listen 80;
server_name yourdomain.com;
location /.well-known/acme-challenge/ {
root /var/www/certbot;
}
location / {
return 301 https://$host$request_uri;
}
}
server {
listen 443 ssl;
server_name yourdomain.com;
ssl_certificate /etc/letsencrypt/live/yourdomain.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/yourdomain.com/privkey.pem;
location / {
proxy_pass http://app:80;
include /etc/nginx/proxy_params;
}
location /onlyoffice/ {
proxy_pass http://onlyoffice/;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
}
}
Generate HTTPS Certificate
Run the Certbot container once manually:
sudo docker run --rm -v certbot-etc:/etc/letsencrypt \
-v ./nginx:/var/www/certbot \
certbot/certbot certonly --webroot --webroot-path=/var/www/certbot \
--email you@example.com --agree-tos --no-eff-email -d yourdomain.com
Setup Backup Script (backup/backup.sh)
#!/bin/bash
BACKUP_DIR=/backup/nextcloud-$(date +%F)
mkdir -p $BACKUP_DIR
# Backup volumes
docker run --rm -v nextcloud-docker_nextcloud_data:/data -v $BACKUP_DIR:/backup alpine \
tar czf /backup/nextcloud_data.tar.gz -C /data .
docker run --rm -v nextcloud-docker_db_data:/data -v $BACKUP_DIR:/backup alpine \
tar czf /backup/db_data.tar.gz -C /data .
echo "Backup done at $BACKUP_DIR"
Make it executable:
chmod +x backup/backup.sh
Optional: Monitoring Stack (Bonus)
Add services in docker-compose.yml:
portainer:
image: portainer/portainer-ce
container_name: portainer
restart: always
ports:
- "9000:9000"
volumes:
- /var/run/docker.sock:/var/run/docker.sock
- portainer_data:/data
Deployment
1. Set your domain DNS to your CentOS server.
2. Run:
docker-compose up -d
3. Access https://yourdomain.com and configure Nextcloud.
4. Install OnlyOffice App inside Nextcloud.
Settings → OnlyOffice → URL: https://yourdomain.com/onlyoffice/
Security Tips
Use firewalld to limit ports:
firewall-cmd --permanent --add-service=http
firewall-cmd --permanent --add-service=https
firewall-cmd --reload
Run Fail2Ban or other hardening tools.