# Development # docker build -t wally . # docker run --rm -v $(pwd)/api:/wally/api -v $(pwd)/web:/wally/web -e DEMO=true -p 80:80 wally # ============================== # Stage 1: Build Python dependencies # ============================== FROM python:3.15-alpine AS builder # Install build dependencies RUN apk add --no-cache --virtual .build-deps build-base libffi-dev musl-dev python3-dev WORKDIR /wally # Copy requirements COPY api/requirements.txt . # Install Python dependencies to a separate location RUN pip install --no-cache-dir --prefer-binary --upgrade pip setuptools wheel \ && pip install --no-cache-dir --prefix=/install -r requirements.txt # Optional: remove tests and unnecessary files from site-packages RUN find /install/lib/python*/site-packages -name "tests" -type d -exec rm -rf {} + \ && find /install/lib/python*/site-packages -name "*.pyc" -delete \ && find /install/lib/python*/site-packages -name "*.pyo" -delete \ && find /install/lib/python*/site-packages -name "*.so" -exec strip --strip-unneeded {} + # ============================== # Stage 2: Runtime image # ============================== FROM python:3.15-alpine # Install Nginx runtime. apk upgrade picks up Alpine security fixes that the # base image doesn't have yet, and Dependabot can't see. RUN apk upgrade --no-cache && apk add --no-cache nginx WORKDIR /wally # Copy Python dependencies from builder COPY --from=builder /install /usr/local # Copy app code COPY api /wally/api COPY --chown=nginx:nginx web /wally/web RUN mkdir /wally/data # Copy Nginx config COPY nginx.conf /etc/nginx/http.d/default.conf # Expose ports EXPOSE 80 # Start FastAPI + Nginx CMD ["sh", "-c", "python3 -m uvicorn api.main:app --host 127.0.0.1 --port 8000 --root-path /api --proxy-headers & nginx -g 'daemon off;'"]