Deploy em Produção¶
Deploy do LASERLAB-Sis no servidor laser-estoque usando Docker Compose com Nginx + Gunicorn + PostgreSQL 16.
Pré-requisitos¶
- Servidor Ubuntu 24.04 com Docker e Docker Compose instalados
- Acesso via Tailscale (Tailnet)
- Deploy key configurada no GitHub para clone via SSH
Arquitetura¶
| Container | Imagem | Rede | Porta |
|---|---|---|---|
laserlab_nginx |
nginx:alpine | host | 80 |
laserlab_web |
Dockerfile.prod (Python 3.12) | host | 8000 |
laserlab_db |
postgres:16-alpine | bridge | 127.0.0.1:5432 |
Por que
network_mode: host? O containerwebprecisa acessar a impressora Zebra na rede local (10.42.0.216:9100). Com rede bridge, o container não alcança a LAN. Veja network-printer.md para detalhes.
Primeiro Deploy (Setup Inicial)¶
1. Clonar o repositório¶
ssh laser@100.88.89.90
# Criar diretório de deploy
sudo mkdir -p /opt/laserlab
sudo chown laser:laser /opt/laserlab
# Clonar via deploy key
git clone git@github.com:felipeosmar/LASERLAB-Sis.git /opt/laserlab
cd /opt/laserlab
2. Criar o .env¶
cp .env.production .env
Editar .env e substituir os valores placeholder:
DEBUG=False
SECRET_KEY=<gerar com: python3 -c "import secrets; print(secrets.token_urlsafe(50))">
ALLOWED_HOSTS=laser-estoque.tailb42313.ts.net,100.88.89.90,localhost
POSTGRES_DB=laserlab
POSTGRES_USER=laserlab
POSTGRES_PASSWORD=<gerar com: python3 -c "import secrets; print(secrets.token_urlsafe(24))">
DATABASE_URL=postgres://laserlab:<MESMA_SENHA>@127.0.0.1:5432/laserlab
Alternativa: O script
deploy.shgera as chaves automaticamente se.envnão existir.
3. Executar o deploy¶
# Opção A: Script automatizado (recomendado para primeiro deploy)
bash deploy.sh
# Opção B: Manual
docker compose -f docker-compose.prod.yml build
docker compose -f docker-compose.prod.yml up -d db
sleep 5
docker compose -f docker-compose.prod.yml run --rm web python manage.py migrate --noinput
docker compose -f docker-compose.prod.yml run --rm web python manage.py collectstatic --noinput
docker compose -f docker-compose.prod.yml up -d
4. Criar superusuário¶
docker compose -f docker-compose.prod.yml run --rm web python manage.py createsuperuser
⚠️ O
deploy.shcria um superuser padrão (admin/admin123). Troque a senha imediatamente em produção.
Deploys Subsequentes¶
Deploys subsequentes são automatizados via GitHub Actions (veja ci-cd.md). Para deploy manual:
cd /opt/laserlab
git fetch origin main
git reset --hard origin/main
docker compose -f docker-compose.prod.yml build
docker compose -f docker-compose.prod.yml run --rm web python manage.py migrate --noinput
docker compose -f docker-compose.prod.yml run --rm web python manage.py collectstatic --noinput
docker compose -f docker-compose.prod.yml up -d
Arquivos de Configuração¶
| Arquivo | Descrição |
|---|---|
docker-compose.prod.yml |
Orquestração dos 3 containers |
Dockerfile.prod |
Build da imagem Django (Python 3.12-slim + Gunicorn) |
nginx/default.conf |
Proxy reverso + arquivos estáticos |
.env.production |
Template de variáveis de ambiente |
.env |
Variáveis reais (não versionado, apenas no servidor) |
deploy.sh |
Script de primeiro deploy (gera chaves, migra, inicia) |
Gunicorn¶
Configuração no Dockerfile.prod:
Workers: 3
Worker class: gthread
Threads: 2
Timeout: 120s
Comandos Úteis¶
# Ver status dos containers
docker compose -f docker-compose.prod.yml ps
# Ver logs
docker compose -f docker-compose.prod.yml logs -f web
docker compose -f docker-compose.prod.yml logs -f nginx
# Reiniciar serviço específico
docker compose -f docker-compose.prod.yml restart web
# Abrir shell Django
docker compose -f docker-compose.prod.yml run --rm web python manage.py shell
# Parar tudo
docker compose -f docker-compose.prod.yml down
# Parar tudo E apagar dados (⚠️ CUIDADO)
docker compose -f docker-compose.prod.yml down -v
Troubleshooting¶
Container web não inicia¶
docker compose -f docker-compose.prod.yml logs web
.env existe? DATABASE_URL aponta para 127.0.0.1:5432?
Nginx retorna 502¶
O Gunicorn ainda está iniciando ou caiu. Verificar logs do web.
Static files 404¶
docker compose -f docker-compose.prod.yml run --rm web python manage.py collectstatic --noinput
docker compose -f docker-compose.prod.yml restart nginx