Spaces:
Sleeping
Sleeping
Commit ·
4f15b05
1
Parent(s): 31fa536
Rebuild image on python:3.11-slim with isolated venvs
Browse filesThe searxng/searxng base image no longer ships a searx-pyenv virtualenv
(2026.7.1 runs granian and installs searx elsewhere), which broke the build.
Switch to a controllable python:3.11-slim base and install SearXNG from
source into /opt/searxng-venv and the Gradio app into /opt/appenv, so the
two dependency sets stay isolated. start.sh now drives each venv explicitly.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Dockerfile +42 -37
- start.sh +11 -9
Dockerfile
CHANGED
|
@@ -1,48 +1,53 @@
|
|
| 1 |
# Blog Post Generator — HF Docker Space
|
| 2 |
-
#
|
| 3 |
-
|
| 4 |
-
|
| 5 |
-
|
| 6 |
-
|
| 7 |
-
|
| 8 |
-
|
| 9 |
-
|
| 10 |
-
|
| 11 |
-
|
| 12 |
-
|
| 13 |
-
|
| 14 |
-
|
| 15 |
-
|
| 16 |
-
|
| 17 |
-
|
| 18 |
-
|
| 19 |
-
|
| 20 |
-
|
| 21 |
-
|
| 22 |
-
|
| 23 |
-
|
| 24 |
-
#
|
| 25 |
-
|
| 26 |
-
|
| 27 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 28 |
WORKDIR /app
|
| 29 |
-
|
| 30 |
-
COPY
|
| 31 |
-
RUN "$VENV/bin/pip" install --no-cache-dir -r requirements.txt
|
| 32 |
-
|
| 33 |
-
# App source
|
| 34 |
-
COPY app.py start.sh ./
|
| 35 |
-
COPY pipeline ./pipeline
|
| 36 |
COPY searxng/settings.yml /etc/searxng/settings.yml
|
| 37 |
|
| 38 |
# HF Spaces run the container as UID 1000 — make everything that gets written writable.
|
| 39 |
RUN chmod +x /app/start.sh \
|
| 40 |
-
&& mkdir -p /data /app/.cache \
|
| 41 |
-
&&
|
| 42 |
-
&&
|
|
|
|
| 43 |
|
| 44 |
EXPOSE 7860
|
| 45 |
-
|
| 46 |
USER 1000
|
| 47 |
|
| 48 |
ENTRYPOINT ["/app/start.sh"]
|
|
|
|
| 1 |
# Blog Post Generator — HF Docker Space
|
| 2 |
+
# One container, two isolated virtualenvs:
|
| 3 |
+
# /opt/searxng-venv → SearXNG (internal metasearch on 127.0.0.1:8080)
|
| 4 |
+
# /opt/appenv → the Gradio app (public on 7860)
|
| 5 |
+
# Keeping them separate avoids dependency conflicts between SearXNG and Gradio.
|
| 6 |
+
FROM python:3.11-slim
|
| 7 |
+
|
| 8 |
+
ENV PIP_NO_CACHE_DIR=1 \
|
| 9 |
+
PIP_DISABLE_PIP_VERSION_CHECK=1 \
|
| 10 |
+
PYTHONUNBUFFERED=1 \
|
| 11 |
+
SEARXNG_SETTINGS_PATH=/etc/searxng/settings.yml \
|
| 12 |
+
SEARXNG_URL=http://127.0.0.1:8080 \
|
| 13 |
+
DATA_DIR=/data \
|
| 14 |
+
HOME=/app
|
| 15 |
+
|
| 16 |
+
# --- system deps: build tools + libs for lxml/trafilatura/Pillow, git for SearXNG source ---
|
| 17 |
+
RUN apt-get update && apt-get install -y --no-install-recommends \
|
| 18 |
+
bash git build-essential \
|
| 19 |
+
libxml2-dev libxslt1-dev zlib1g-dev libffi-dev libssl-dev \
|
| 20 |
+
libjpeg62-turbo-dev \
|
| 21 |
+
ca-certificates curl \
|
| 22 |
+
&& rm -rf /var/lib/apt/lists/*
|
| 23 |
+
|
| 24 |
+
# --- SearXNG (from source) into its own venv ---
|
| 25 |
+
ARG SEARXNG_REF=master
|
| 26 |
+
RUN git clone --depth 1 --branch "$SEARXNG_REF" https://github.com/searxng/searxng.git /usr/local/searxng
|
| 27 |
+
RUN python -m venv /opt/searxng-venv \
|
| 28 |
+
&& /opt/searxng-venv/bin/pip install -U pip setuptools wheel pyyaml msgspec typing-extensions pybind11 \
|
| 29 |
+
&& /opt/searxng-venv/bin/pip install --use-pep517 -e /usr/local/searxng
|
| 30 |
+
|
| 31 |
+
# --- Gradio app into its own venv ---
|
| 32 |
+
RUN python -m venv /opt/appenv
|
| 33 |
+
COPY requirements.txt /app/requirements.txt
|
| 34 |
+
RUN /opt/appenv/bin/pip install -U pip \
|
| 35 |
+
&& /opt/appenv/bin/pip install -r /app/requirements.txt
|
| 36 |
+
|
| 37 |
+
# --- app source + SearXNG config ---
|
| 38 |
WORKDIR /app
|
| 39 |
+
COPY app.py start.sh /app/
|
| 40 |
+
COPY pipeline /app/pipeline
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 41 |
COPY searxng/settings.yml /etc/searxng/settings.yml
|
| 42 |
|
| 43 |
# HF Spaces run the container as UID 1000 — make everything that gets written writable.
|
| 44 |
RUN chmod +x /app/start.sh \
|
| 45 |
+
&& mkdir -p /data /app/.cache /var/cache/searxng \
|
| 46 |
+
&& useradd -m -u 1000 user || true \
|
| 47 |
+
&& chown -R 1000:1000 /app /etc/searxng /data /var/cache/searxng /usr/local/searxng \
|
| 48 |
+
&& chmod -R u+rwX /app /etc/searxng /data /var/cache/searxng
|
| 49 |
|
| 50 |
EXPOSE 7860
|
|
|
|
| 51 |
USER 1000
|
| 52 |
|
| 53 |
ENTRYPOINT ["/app/start.sh"]
|
start.sh
CHANGED
|
@@ -1,8 +1,11 @@
|
|
| 1 |
#!/usr/bin/env bash
|
| 2 |
# Launch SearXNG (internal) then the Gradio app (public). SearXNG runs in the
|
| 3 |
# background bound to 127.0.0.1:8080; the app talks to it over localhost.
|
|
|
|
| 4 |
set -euo pipefail
|
| 5 |
|
|
|
|
|
|
|
| 6 |
SEARXNG_HOST="127.0.0.1"
|
| 7 |
SEARXNG_PORT="8080"
|
| 8 |
|
|
@@ -10,18 +13,17 @@ SEARXNG_PORT="8080"
|
|
| 10 |
# placeholder, generate one at runtime (settings dir is made writable in the image).
|
| 11 |
SETTINGS="${SEARXNG_SETTINGS_PATH:-/etc/searxng/settings.yml}"
|
| 12 |
if grep -q 'ultrasecretkey_change_me' "$SETTINGS" 2>/dev/null; then
|
| 13 |
-
KEY="$(
|
| 14 |
-
# portable in-place edit (BusyBox sed supports -i)
|
| 15 |
sed -i "s/ultrasecretkey_change_me/${KEY}/" "$SETTINGS" || true
|
| 16 |
fi
|
| 17 |
|
| 18 |
echo "[start] launching SearXNG on ${SEARXNG_HOST}:${SEARXNG_PORT} ..."
|
| 19 |
-
|
| 20 |
SEARXNG_PID=$!
|
| 21 |
|
| 22 |
-
# Wait for SearXNG to
|
| 23 |
-
for i in $(seq 1
|
| 24 |
-
if
|
| 25 |
import socket, sys
|
| 26 |
s = socket.socket()
|
| 27 |
s.settimeout(1)
|
|
@@ -37,12 +39,12 @@ PY
|
|
| 37 |
break
|
| 38 |
fi
|
| 39 |
if ! kill -0 "$SEARXNG_PID" 2>/dev/null; then
|
| 40 |
-
echo "[start] SearXNG process exited early;
|
| 41 |
break
|
| 42 |
fi
|
| 43 |
-
echo "[start] waiting for SearXNG ($i/
|
| 44 |
sleep 1
|
| 45 |
done
|
| 46 |
|
| 47 |
echo "[start] launching Gradio app on 0.0.0.0:7860 ..."
|
| 48 |
-
exec
|
|
|
|
| 1 |
#!/usr/bin/env bash
|
| 2 |
# Launch SearXNG (internal) then the Gradio app (public). SearXNG runs in the
|
| 3 |
# background bound to 127.0.0.1:8080; the app talks to it over localhost.
|
| 4 |
+
# Each process uses its own isolated virtualenv.
|
| 5 |
set -euo pipefail
|
| 6 |
|
| 7 |
+
SEARXNG_PY=/opt/searxng-venv/bin/python
|
| 8 |
+
APP_PY=/opt/appenv/bin/python
|
| 9 |
SEARXNG_HOST="127.0.0.1"
|
| 10 |
SEARXNG_PORT="8080"
|
| 11 |
|
|
|
|
| 13 |
# placeholder, generate one at runtime (settings dir is made writable in the image).
|
| 14 |
SETTINGS="${SEARXNG_SETTINGS_PATH:-/etc/searxng/settings.yml}"
|
| 15 |
if grep -q 'ultrasecretkey_change_me' "$SETTINGS" 2>/dev/null; then
|
| 16 |
+
KEY="$("$APP_PY" -c 'import secrets; print(secrets.token_hex(32))')"
|
|
|
|
| 17 |
sed -i "s/ultrasecretkey_change_me/${KEY}/" "$SETTINGS" || true
|
| 18 |
fi
|
| 19 |
|
| 20 |
echo "[start] launching SearXNG on ${SEARXNG_HOST}:${SEARXNG_PORT} ..."
|
| 21 |
+
"$SEARXNG_PY" -m searx.webapp &
|
| 22 |
SEARXNG_PID=$!
|
| 23 |
|
| 24 |
+
# Wait for SearXNG to accept connections before starting the app (max ~40s).
|
| 25 |
+
for i in $(seq 1 40); do
|
| 26 |
+
if "$APP_PY" - <<'PY' 2>/dev/null; then
|
| 27 |
import socket, sys
|
| 28 |
s = socket.socket()
|
| 29 |
s.settimeout(1)
|
|
|
|
| 39 |
break
|
| 40 |
fi
|
| 41 |
if ! kill -0 "$SEARXNG_PID" 2>/dev/null; then
|
| 42 |
+
echo "[start] WARNING: SearXNG process exited early; search will be degraded."
|
| 43 |
break
|
| 44 |
fi
|
| 45 |
+
echo "[start] waiting for SearXNG ($i/40) ..."
|
| 46 |
sleep 1
|
| 47 |
done
|
| 48 |
|
| 49 |
echo "[start] launching Gradio app on 0.0.0.0:7860 ..."
|
| 50 |
+
exec "$APP_PY" /app/app.py
|