Guia completa para migrar el backend Python de DataFlow AI a uv: entornos reproducibles, CI/CD optimizado y Docker sin dolor.
# 1. Instalar uv (macOS/Linux — sin necesitar Python) curl -LsSf https://astral.sh/uv/install.sh | sh # 2. Verificar instalacion uv --version # uv 0.4.x # 3. En el repo dataflow-ai — inicializar proyecto uv # (mantiene requirements.txt existente temporalmente) cd dataflow-ai/ uv init --no-package . # 4. Pinear Python 3.12 para todo el equipo uv python pin 3.12 # Crea .python-version con "3.12" # 5. uv descarga automaticamente Python 3.12 si no esta instalado uv python install 3.12
[project] name = "dataflow-ai" version = "0.3.1" description = "SaaS B2B de analisis de datos con IA para pymes" requires-python = ">=3.12" dependencies = [ "fastapi>=0.110.0,<1.0", "uvicorn[standard]>=0.29.0", "pandas>=2.2.0", "anthropic>=0.28.0", "pydantic>=2.7.0", "sqlalchemy>=2.0.0", "psycopg2-binary>=2.9.9", ] [project.optional-dependencies] dev = [ "pytest>=8.0.0", "pytest-cov>=5.0.0", "black>=24.0.0", "ruff>=0.4.0", "mypy>=1.10.0", "httpx>=0.27.0", # TestClient de FastAPI ] [build-system] requires = ["hatchling"] build-backend = "hatchling.build"
# Sincronizar todas las dependencias (crea .venv + uv.lock) uv sync --all-extras # Resuelto en ~1.8s vs ~45s con pip # Commit del lockfile (obligatorio para reproducibilidad) git add pyproject.toml uv.lock .python-version git commit -m "chore: migrar a uv package manager" # Verificar arbol de dependencias uv tree
name: CI on: [push, pull_request] jobs: test: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Instalar uv (con cache) uses: astral-sh/setup-uv@v2 with: enable-cache: true cache-dependency-glob: "uv.lock" - name: Instalar Python 3.12 run: uv python install - name: Instalar dependencias (frozen) run: uv sync --frozen --all-extras # --frozen: usa uv.lock exacto, sin resolver - name: Linting con ruff run: uv run ruff check . - name: Formato con black run: uv run black --check . - name: Tests con cobertura run: uv run pytest --cov=src --cov-report=xml -v - name: Type check con mypy run: uv run mypy src/
# ====== BUILD STAGE ====== FROM python:3.12-slim AS builder # Copiar binario uv (no requiere Rust ni cargo) COPY --from=ghcr.io/astral-sh/uv:0.6 /uv /usr/local/bin/uv WORKDIR /app # Instalar dependencias (cacheado si pyproject.toml/uv.lock no cambian) COPY pyproject.toml uv.lock ./ RUN uv sync --frozen --no-dev --no-editable # Solo produccion, sin dev tools # ====== RUNTIME STAGE ====== FROM python:3.12-slim WORKDIR /app # Copiar SOLO el venv del builder (sin uv, sin pip, limpio) COPY --from=builder /app/.venv .venv COPY src/ ./src/ # Activar venv via PATH ENV PATH="/app/.venv/bin:$PATH" ENV PYTHONDONTWRITEBYTECODE=1 ENV PYTHONUNBUFFERED=1 EXPOSE 8000 CMD ["uvicorn", "src.main:app", "--host", "0.0.0.0", "--port", "8000"]
| Metrica | pip + requirements.txt | uv + uv.lock | Mejora |
|---|---|---|---|
| Tiempo install CI (cold) | 4 min 52 seg | 1 min 05 seg | 4.5x mas rapido |
| Tiempo install CI (cache) | 4 min 12 seg | 18 seg | 14x mas rapido |
| Reproducibilidad | No garantizada | 100% via uv.lock | Determinista |
| Tamano imagen Docker | 1.2 GB | ~480 MB | 60% menos |
| Conflictos de version | Frecuentes | Ninguno | Eliminados |
| Gestion Python version | Manual / pyenv | uv python pin | Integrado |
| Compatibilidad pip | Nativa | Compatible (uv pip) | Sin rotura |