Skip to content

feat: ship official Docker image and docker compose (closes #278) - #296

Open
Madhumasa84 wants to merge 1 commit into
PrismorSec:mainfrom
Madhumasa84:feat/278-docker-image-and-compose
Open

Madhumasa84 wants to merge 1 commit into
PrismorSec:mainfrom
Madhumasa84:feat/278-docker-image-and-compose

Conversation

@Madhumasa84

@Madhumasa84 Madhumasa84 commented Aug 16, 2026

Copy link
Copy Markdown
Contributor

Problem

There was a docs/docker.md guide but no official Dockerfile or docker-compose.yml in the repository, making
bare-metal Python installs the only supported deployment method. Users and teams running automated agent pipelines
lacked an official, pre-hardened, unprivileged container image and compose setup for the web dashboard, evaluation
server, and periodic audit jobs.

Closes #278

Prior art - what already exists

  • I extended an existing pattern. Which one, and what I followed:
    Followed the standard multi-stage Python container pattern (building standard wheels in stage 1 with
    hatchling and installing into a minimal python:3.12-slim runner in stage 2). Leveraged existing CLI entry points
    (prismor dashboard, prismor eval-server, prismor status) for service commands and Docker healthchecks, applying
    container security best practices (USER 10001:10001, --read-only rootfs, cap_drop: [ALL], no-new-privileges).

Tangential updates:

  • prismor/__init__.py: Extended package __path__ via pkgutil.extend_path so adapter subpackages resolve
    correctly across editable dev installs and test suites.
  • prismor/runtime/scanner.py: Added fallback to tomli for environments running on Python < 3.11.

Solution - high level

  • Added a multi-stage, hardened Dockerfile based on python:3.12-slim running as non-root user UID 10001 (prismor), supporting --read-only rootfs, exposing ports 7070/7071, and using prismor status for HEALTHCHECK.
  • Added docker-compose.yml defining dashboard (default), eval-server (profile), and periodic cron (profile)
    services with persistent SQLite storage (prismor_data volume) and dropped capabilities.
  • Added .dockerignore and integrated multi-arch (linux/amd64, linux/arm64) container builds and GHCR publishing
    into .github/workflows/release.yml.
  • Added automated config tests in tests/test_docker.py and updated docs/docker.md with complete deployment,
    compose, and security hardening documentation.

Deep dive - how it works

  • Multi-Stage Build: Stage 1 (builder) installs build dependencies and packages the wheel; Stage 2 (runner)
    copies and installs the standalone wheel and cleans up temporary files, keeping the final runtime image lean (~200MB).
  • Hardening & Isolation: Runtime runs as deterministic non-root UID 10001:10001. The container root filesystem
    is compatible with --read-only because all state writes are isolated to /home/prismor/.prismor (mounted as a volume
    or tmpfs). The host workspace is mounted read-only at /workspace.
  • Compose Profiles: docker compose up starts the dashboard on port 7070 by default. Running docker compose - -profile eval-server up enables the HTTP evaluation server (port 7071), and --profile cron runs periodic workspace
    security audits.
  • CI Multi-Arch Release: .github/workflows/release.yml builds and pushes multi-platform images (linux/amd64
    and linux/arm64) to ghcr.io/prismorsec/prismor tagged with semver versions and latest on release tags.

Files changed

File Why it changed
Dockerfile Multi-stage build, unprivileged user (10001), healthcheck, exposed ports 7070/7071
docker-compose.yml Multi-service orchestration (dashboard, eval-server, cron), volume mounts, dropped
caps
.dockerignore Exclude git, caches, test artifacts, and temp files from build context
.github/workflows/release.yml Added docker job for multi-arch build and GHCR push on release tags
docs/docker.md Comprehensive deployment guide, Docker Compose usage, hardening rules, and env var reference
tests/test_docker.py Automated tests verifying Dockerfile directives, non-root user, exposed ports, and compose
validity
prismor/__init__.py Extended __path__ via pkgutil.extend_path for adapter package discovery
prismor/runtime/scanner.py Fallback import from tomllib to tomli for Python < 3.11 compatibility

Testing

# Automated Docker and compose configuration tests
pytest tests/test_docker.py -q

# Full test suite
pytest -q

# OSS safety scan
python3 scripts/check_oss_safe.py

# Policy schema validation
prismor policy validate prismor/runtime/default_policy.yaml

# Local container verification
docker build -t prismor:test .
docker run --rm prismor:test check "rm -rf /"
docker run --rm prismor:test check "echo hello"
docker compose config

…rismorSec#278)

- Add multi-stage Dockerfile (python:3.12-slim, UID 10001, read-only
  rootfs, ports 7070/7071, healthcheck via prismor status)
- Add docker-compose.yml with dashboard, eval-server (profile), cron
  (profile) services; prismor_data volume; --cap-drop ALL, no-new-privs
- Add .dockerignore
- Add tests/test_docker.py (3 tests: Dockerfile, .dockerignore, compose)
- Update .github/workflows/release.yml: docker job builds multi-arch
  linux/amd64+arm64 and pushes to ghcr.io on release tags
- Update docs/docker.md with deployment and hardening guide
- Fix prismor/__init__.py: extend __path__ via pkgutil so adapter
  subpackage imports resolve during pip install -e . dev runs
- Fix prismor/runtime/scanner.py: tomllib fallback to tomli for Python < 3.11

All 1956 tests pass; OSS guard clean; policy schema valid.
Copilot AI lite review requested due to automatic review settings August 16, 2026 18:01

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Ship official Docker image and docker-compose

2 participants