diff --git a/Dockerfile b/Dockerfile index 640164e1d..f24ba6423 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,9 +1,10 @@ -FROM python:3.12-slim +# Build stage - for compiling dependencies +FROM python:3.12-slim as builder ENV PYTHONDONTWRITEBYTECODE=1 \ PYTHONUNBUFFERED=1 -# Install system dependencies +# Install build dependencies RUN apt-get update \ && apt-get install -y --no-install-recommends \ build-essential \ @@ -17,33 +18,68 @@ RUN apt-get update \ libxslt1-dev \ libffi-dev \ pkg-config \ + gcc \ + g++ \ + && rm -rf /var/lib/apt/lists/* + +# Create virtual environment +RUN python -m venv /opt/venv +ENV PATH="/opt/venv/bin:$PATH" + +# Install Python dependencies +COPY requirements.txt . +RUN pip install --upgrade pip \ + && pip install --no-cache-dir -r requirements.txt gunicorn psycopg2-binary + +# Production stage - minimal runtime image +FROM python:3.12-slim as production + +ENV PYTHONDONTWRITEBYTECODE=1 \ + PYTHONUNBUFFERED=1 \ + PATH="/opt/venv/bin:$PATH" + +# Install only runtime dependencies +RUN apt-get update \ + && apt-get install -y --no-install-recommends \ + libpq5 \ + libjpeg62-turbo \ + zlib1g \ + libcairo2 \ + libpango-1.0-0 \ + libgdk-pixbuf-xlib-2.0-0 \ + libxml2 \ + libxslt1.1 \ + libffi8 \ curl \ netcat-openbsd \ - && rm -rf /var/lib/apt/lists/* + && rm -rf /var/lib/apt/lists/* \ + && apt-get clean # Create non-root user RUN useradd --create-home --uid 1000 appuser +# Copy virtual environment from builder stage +COPY --from=builder /opt/venv /opt/venv + WORKDIR /app -# Install Python dependencies -COPY requirements.txt . -RUN pip install --no-cache-dir -r requirements.txt gunicorn psycopg2-binary +# Copy application code +COPY --chown=appuser:appuser . . -# Copy application -COPY . . +# Copy entrypoint script +COPY --chown=appuser:appuser docker/entrypoint.sh /entrypoint.sh +RUN chmod +x /entrypoint.sh -# Set permissions +# Create necessary directories and set permissions RUN mkdir -p staticfiles media \ && chown -R appuser:appuser /app -# Copy entrypoint -COPY docker/entrypoint.sh /entrypoint.sh -RUN chmod +x /entrypoint.sh - USER appuser EXPOSE 8000 +HEALTHCHECK --interval=30s --timeout=30s --start-period=5s --retries=3 \ + CMD curl -f http://localhost:8000/health/ || exit 1 + ENTRYPOINT ["/entrypoint.sh"] CMD ["gunicorn", "horilla.wsgi:application", "--config", "docker/gunicorn.conf.py"]