mirror of
https://github.com/yogeshojha/rengine.git
synced 2026-10-20 23:31:31 +02:00
Four compose services declared their own build against worker/Dockerfile, so buildkit shared the solve and then exported and unpacked the same image once per tag. Compose does not dedupe identical targets, measured on a three-service probe. Under the containerd snapshotter the unpack is a second full pass over every byte, as expensive as the export. The go module and build caches were baked into layers: `go install nuclei` made a 2.66GB layer for a 190MB binary, and /root/go/pkg/mod (3.4GB) plus /root/.cache/go-build (3.3GB) were half the 13.1GB image. - the tools build in a throwaway stage with --mount=type=cache on GOCACHE and GOMODCACHE; the runtime stage copies /out/bin alone - worker-default builds rengine-worker:latest; worker-beat, ct-stream and flower reference it. Building one of those alone now needs worker-default built first - the runtime stage drops the go toolchain, build-essential and libpcap-dev; uv sync needs no compiler. libpcap0.8t64 stays, naabu dlopens it for SYN so ldd shows nothing and the loss would only surface at scan time - -ldflags=-s trims the binaries 650MB -> 495MB - only shared/ and tools/ are copied, being file:// path deps; stages/, reports/, interest/, toolbox/, mcp/, connectors/ and binaries/ are mounted - the frontend fetches tech icons above COPY frontend/. ., so a source edit no longer re-runs the tarball download - .dockerignore excludes .git (271MB) and node_modules (320MB); COPY frontend/. . had been copying the host's node_modules over the npm ci result worker image 13.1GB -> 2.41GB, frontend 1.38GB -> 969MB worker export+unpack 453s across three tags -> 55s across one editing stages/ or reports/ now rebuilds nothing (1s), frontend/src 4s, shared/ 19s; cold build 475s -> 414s, still dominated by go compilation Tool versions diff identical against the old image, naabu SYN proven against a live listener, 8/8 services up, 853 tests green, ruff clean. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_015fWjAbvFBdmsmVeMcwaaR9
270 lines
7.4 KiB
YAML
270 lines
7.4 KiB
YAML
services:
|
|
db:
|
|
image: postgres:16-alpine
|
|
shm_size: ${POSTGRES_SHM_SIZE:-1gb}
|
|
env_file:
|
|
- .env
|
|
volumes:
|
|
- postgres_data:/var/lib/postgresql/data
|
|
ports:
|
|
- "${BIND_ADDR:-127.0.0.1}:5432:5432"
|
|
command: >
|
|
postgres
|
|
-c shared_buffers=${POSTGRES_SHARED_BUFFERS:-2GB}
|
|
-c effective_cache_size=${POSTGRES_EFFECTIVE_CACHE_SIZE:-6GB}
|
|
-c work_mem=${POSTGRES_WORK_MEM:-32MB}
|
|
-c maintenance_work_mem=${POSTGRES_MAINTENANCE_WORK_MEM:-512MB}
|
|
-c random_page_cost=1.1
|
|
-c effective_io_concurrency=200
|
|
-c max_parallel_workers_per_gather=4
|
|
-c jit=off
|
|
-c max_connections=${POSTGRES_MAX_CONNECTIONS:-150}
|
|
-c shared_preload_libraries=pg_stat_statements
|
|
-c pg_stat_statements.max=5000
|
|
-c pg_stat_statements.track=top
|
|
-c track_io_timing=on
|
|
-c log_min_duration_statement=${POSTGRES_LOG_MIN_DURATION:-2000}
|
|
healthcheck:
|
|
test: ["CMD-SHELL", "pg_isready -U $${POSTGRES_USER:-rengine}"]
|
|
interval: 5s
|
|
timeout: 5s
|
|
retries: 5
|
|
|
|
redis:
|
|
image: redis:8-alpine
|
|
ports:
|
|
- "${BIND_ADDR:-127.0.0.1}:6379:6379"
|
|
volumes:
|
|
- redis_data:/data
|
|
environment:
|
|
REDIS_PASSWORD: ${REDIS_PASSWORD:-}
|
|
healthcheck:
|
|
test:
|
|
[
|
|
"CMD-SHELL",
|
|
"redis-cli $${REDIS_PASSWORD:+-a \"$$REDIS_PASSWORD\"} --no-auth-warning ping | grep -q PONG",
|
|
]
|
|
interval: 5s
|
|
timeout: 5s
|
|
retries: 5
|
|
command: >
|
|
redis-server
|
|
--appendonly yes
|
|
--maxmemory ${REDIS_MAXMEMORY:-1gb}
|
|
--maxmemory-policy noeviction
|
|
${REDIS_PASSWORD:+--requirepass} ${REDIS_PASSWORD:-}
|
|
|
|
api:
|
|
build:
|
|
context: .
|
|
dockerfile: api/Dockerfile
|
|
target: development
|
|
volumes:
|
|
- ./api/app:/app/app
|
|
- ./shared:/app/shared
|
|
- ./tools:/app/tools
|
|
- ./stages:/app/stages
|
|
- ./reports:/app/reports
|
|
- ./interest:/app/interest
|
|
- ./mcp:/app/mcp
|
|
- ./connectors:/app/connectors
|
|
- ./toolbox:/app/toolbox
|
|
- ./binaries:/app/binaries:ro
|
|
- ./alembic:/app/alembic
|
|
- ./alembic.ini:/app/alembic.ini
|
|
- ./tests:/app/tests
|
|
- ./pyproject.toml:/app/pyproject.toml
|
|
# read-only, so the tests can check a frontend mirror has not drifted
|
|
- ./frontend/src/lib/config:/app/frontend-config:ro
|
|
- ./scan_media:/app/scan_media
|
|
- vuln_templates:/app/vuln-templates
|
|
- wordlists:/app/wordlists
|
|
- reports_out:/app/reports-out
|
|
- exports_out:/app/exports-out
|
|
- report_fonts:/app/report-fonts
|
|
- /app/shared/build
|
|
- /app/shared/rengine_shared.egg-info
|
|
- /app/tools/build
|
|
- /app/tools/rengine_tools.egg-info
|
|
ports:
|
|
- "${APP_BIND_ADDR:-0.0.0.0}:8000:8000"
|
|
env_file:
|
|
- .env
|
|
environment:
|
|
- WATCHFILES_FORCE_POLLING=true
|
|
depends_on:
|
|
db:
|
|
condition: service_healthy
|
|
redis:
|
|
condition: service_healthy
|
|
|
|
# default workers for handling regular tasks like imports, whois etc
|
|
worker-default:
|
|
init: true
|
|
image: rengine-worker:latest
|
|
build:
|
|
context: .
|
|
dockerfile: worker/Dockerfile
|
|
target: development
|
|
volumes:
|
|
- ./worker/app:/app/app
|
|
- ./shared:/app/shared
|
|
- ./tools:/app/tools
|
|
- ./stages:/app/stages
|
|
- ./reports:/app/reports
|
|
- ./interest:/app/interest
|
|
- ./toolbox:/app/toolbox
|
|
- ./scan_media:/app/scan_media
|
|
- vuln_templates:/app/vuln-templates
|
|
- wordlists:/app/wordlists
|
|
- reports_out:/app/reports-out
|
|
- exports_out:/app/exports-out
|
|
- report_fonts:/app/report-fonts
|
|
- /app/shared/build
|
|
- /app/shared/rengine_shared.egg-info
|
|
- /app/tools/build
|
|
- /app/tools/rengine_tools.egg-info
|
|
env_file:
|
|
- .env
|
|
# the widest level holds 5 stages
|
|
command: >
|
|
uv run celery -A app.celery worker
|
|
--loglevel=DEBUG
|
|
--concurrency=${CELERY_SCAN_CONCURRENCY:-12}
|
|
--queues=critical,default,scans
|
|
--hostname=worker-default@%h
|
|
--max-tasks-per-child=100
|
|
depends_on:
|
|
db:
|
|
condition: service_healthy
|
|
redis:
|
|
condition: service_healthy
|
|
healthcheck:
|
|
test: ["CMD-SHELL", "/app/.venv/bin/celery -A app.celery inspect ping -d worker-default@$$HOSTNAME || exit 1"]
|
|
interval: 30s
|
|
timeout: 10s
|
|
retries: 3
|
|
start_period: 30s
|
|
|
|
# beat scheduler: emits the schedule tick that fires due scan schedules
|
|
worker-beat:
|
|
init: true
|
|
# built by worker-default
|
|
image: rengine-worker:latest
|
|
volumes:
|
|
- ./worker/app:/app/app
|
|
- ./shared:/app/shared
|
|
- ./tools:/app/tools
|
|
- ./stages:/app/stages
|
|
- ./reports:/app/reports
|
|
- ./interest:/app/interest
|
|
- ./toolbox:/app/toolbox
|
|
- ./scan_media:/app/scan_media
|
|
- vuln_templates:/app/vuln-templates
|
|
- wordlists:/app/wordlists
|
|
- reports_out:/app/reports-out
|
|
- exports_out:/app/exports-out
|
|
- report_fonts:/app/report-fonts
|
|
- /app/shared/build
|
|
- /app/shared/rengine_shared.egg-info
|
|
- /app/tools/build
|
|
- /app/tools/rengine_tools.egg-info
|
|
env_file:
|
|
- .env
|
|
command: >
|
|
uv run celery -A app.celery beat
|
|
--loglevel=INFO
|
|
--schedule=/tmp/celerybeat-schedule
|
|
depends_on:
|
|
db:
|
|
condition: service_healthy
|
|
redis:
|
|
condition: service_healthy
|
|
|
|
# certificate transparency stream for watched programs
|
|
ct-stream:
|
|
init: true
|
|
# built by worker-default
|
|
image: rengine-worker:latest
|
|
volumes:
|
|
- ./worker/app:/app/app
|
|
- ./shared:/app/shared
|
|
- ./tools:/app/tools
|
|
- ./stages:/app/stages
|
|
- ./reports:/app/reports
|
|
- ./interest:/app/interest
|
|
- ./toolbox:/app/toolbox
|
|
- ct_state:/app/ct-state
|
|
- /app/shared/build
|
|
- /app/shared/rengine_shared.egg-info
|
|
- /app/tools/build
|
|
- /app/tools/rengine_tools.egg-info
|
|
env_file:
|
|
- .env
|
|
command: uv run python -m app.ct_stream
|
|
restart: unless-stopped
|
|
depends_on:
|
|
db:
|
|
condition: service_healthy
|
|
redis:
|
|
condition: service_healthy
|
|
|
|
flower:
|
|
# built by worker-default
|
|
image: rengine-worker:latest
|
|
volumes:
|
|
- ./worker/app:/app/app
|
|
- ./shared:/app/shared
|
|
- ./tools:/app/tools
|
|
- ./stages:/app/stages
|
|
- ./reports:/app/reports
|
|
- ./interest:/app/interest
|
|
- ./toolbox:/app/toolbox
|
|
- ./scan_media:/app/scan_media
|
|
- vuln_templates:/app/vuln-templates
|
|
- wordlists:/app/wordlists
|
|
- reports_out:/app/reports-out
|
|
- exports_out:/app/exports-out
|
|
- report_fonts:/app/report-fonts
|
|
- /app/shared/build
|
|
- /app/shared/rengine_shared.egg-info
|
|
- /app/tools/build
|
|
- /app/tools/rengine_tools.egg-info
|
|
profiles: ["debug"]
|
|
ports:
|
|
- "${BIND_ADDR:-127.0.0.1}:5555:5555"
|
|
env_file:
|
|
- .env
|
|
command: >
|
|
uv run celery -A app.celery flower
|
|
--port=5555
|
|
--basic-auth=${FLOWER_USER:-admin}:${FLOWER_PASSWORD:-admin}
|
|
depends_on:
|
|
redis:
|
|
condition: service_healthy
|
|
|
|
frontend:
|
|
build:
|
|
context: .
|
|
dockerfile: frontend/Dockerfile.dev
|
|
volumes:
|
|
- ./frontend/src:/app/src
|
|
- ./frontend/vite.config.ts:/app/vite.config.ts
|
|
ports:
|
|
- "${APP_BIND_ADDR:-0.0.0.0}:5173:5173"
|
|
environment:
|
|
- NODE_ENV=development
|
|
depends_on:
|
|
- api
|
|
|
|
volumes:
|
|
ct_state:
|
|
postgres_data:
|
|
redis_data:
|
|
celery_beat_data:
|
|
vuln_templates:
|
|
wordlists:
|
|
exports_out:
|
|
reports_out:
|
|
report_fonts:
|