# 📄 PDF Toolkit — Manipulação, Otimização e Conversão de PDFs @~/AGENTS.md ## 🧠 Contexto do Projeto & Memória no Obsidian - **Cofre Principal:** `$OBSIDIAN_VAULT_PATH/` - **Ficha do Projeto:** `$OBSIDIAN_VAULT_PATH/03_Dev_Projetos/PDF_Toolkit/00_Index.md` - **Padrões de Arquitetura:** `$OBSIDIAN_VAULT_PATH/03_Dev_Projetos/PDF_Toolkit/padroes-arquitetura.md` - **Registro de Gotchas & Lições:** `$OBSIDIAN_VAULT_PATH/03_Dev_Projetos/PDF_Toolkit/gotchas-e-bugs.md` - **Especificação de Escopo:** [docs/escopo.md](docs/escopo.md) - **Roadmap & Fases:** [docs/fases.md](docs/fases.md) - **Documentação de Arquitetura Local:** [docs/ARCHITECTURE.md](docs/ARCHITECTURE.md) - **Documentação de Endpoints da API:** [docs/API.md](docs/API.md) - **Repositório Gitea:** `https://gitea.cmconsultor.com.br/cmconsultor/pdf-toolkit` --- ## 🛠️ Stack Tecnológica & Comandos - **Linguagem & Runtime:** Python 3.12+ - **Bibliotecas Core:** `pypdf` (manipulação de estrutura/streams), `Pillow` (reamostragem de imagens JPEG/PNG) - **Camada Web / GUI:** Streamlit (porta `8550`) - **Camada API REST:** FastAPI + Uvicorn (porta `8555`) - **Containerização:** Docker e Docker Compose (`Dockerfile.api`, `Dockerfile.web`, `docker-compose.yml`) - **Testes Unitários:** Pytest ### Comandos de Execução Local: ```bash # Instalação de dependências pip install -r requirements.txt # Executar Interface Web (Streamlit) streamlit run app.py --server.port 8550 # Executar API REST (FastAPI com recarregamento dinâmico) uvicorn api:app --host 0.0.0.0 --port 8555 --reload # Executar suíte de testes unitários pytest tests/ -v ``` ### Comandos Docker: ```bash # Subir ambos os serviços (GUI + API) docker compose up -d # Visualizar logs docker compose logs -f # Parar serviços docker compose down ``` --- ## 📐 Diretrizes de Engenharia Locais 1. **Processamento In-Memory:** Todas as operações do `core/` devem operar recebendo `bytes` e devolvendo `bytes` via `io.BytesIO`. Não grave arquivos temporários em disco sem necessidade expressa. 2. **Proteção contra Inflação:** No pipeline de compressão, sempre compare o tamanho final gerado com o original. Caso o resultado seja maior, descarte a re-escrita e preserve os bytes originais (`reduced: False`). 3. **Desacoplamento Core / Interfaces:** Nenhuma lógica de negócio ou manipulação de PDF deve residir diretamente em `api.py` ou `app.py`. Ambas as interfaces devem chamar exclusivamente a fachada `PDFEngine` de `core/engine.py`. 4. **Validação Rigorosa:** Sempre validar o cabeçalho do arquivo (`validate_pdf`) antes de processar operações para evitar exceções não tratadas em arquivos corrompidos.