Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 7 additions & 9 deletions docker/docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -162,19 +162,17 @@ services:
# gateway bridges that to plain HTTP on the compose network so odek can use
# its existing HTTP-based piguard client without sharing a socket volume.
#
# Apple Silicon note: the upstream daemon Dockerfile pins its base images by
# amd64 digest, which yields x86-64 binaries that crash under Rosetta on
# macOS. If `docker compose up` fails with "rosetta error", build the daemon
# locally from the guard repo with the digest pins removed and tag it
# piguard:local (compose reuses the existing image).
# The daemon image is vendored (./piguard-daemon) for arch-safe builds: the
# upstream Dockerfile pins amd64-only base digests, which crash under Rosetta
# on Apple Silicon. The vendored Dockerfile builds the pinned upstream v1.0.0
# source with native (unpinned) base images instead.
piguard:
profiles: ["restricted", "godmode", "telegram-restricted", "telegram-godmode"]
# GHCR packages for this repo are private, so we build the daemon image locally
# from the public source. The first build clones the repo and compiles the
# binary; subsequent starts reuse the cached image.
# from the public source. The first build clones the upstream repo and compiles
# the binary; subsequent starts reuse the cached image.
build:
context: https://github.com/BackendStack21/go-prompt-injection-guard.git#v1.0.0
dockerfile: Dockerfile
context: ./piguard-daemon
image: piguard:local
command:
- "--socket=/run/piguard/piguard.sock"
Expand Down
55 changes: 55 additions & 0 deletions docker/piguard-daemon/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
# syntax=docker/dockerfile:1
#
# Vendored, architecture-safe build of the PIGuard prompt-injection daemon.
#
# Why vendored: the upstream Dockerfile
# (https://github.com/BackendStack21/go-prompt-injection-guard/blob/v1.0.0/Dockerfile)
# pins its base images by amd64-only sha256 digests, so on Apple Silicon Macs
# the build produces x86-64 binaries (piguard-server, libonnxruntime.so) inside
# an arm64-labeled image, and the container crash-loops with:
# rosetta error: failed to open elf at /lib64/ld-linux-x86-64.so.2
# This Dockerfile builds the same pinned upstream source (v1.0.0) but uses
# unpinned base image tags, which resolve to the host architecture. The upstream
# Makefile is arch-aware (it selects the aarch64 ONNX Runtime when
# GOARCH=arm64), so the resulting image contains native binaries. Note: the
# upstream Makefile has no checksum entries for linux-arm64, so it prints
# WARNINGs during the build — that is expected and harmless.

# ---- build stage ----
# cgo is required: the tokenizer bindings link a static library and ONNX Runtime
# is loaded at runtime. A glibc base is required (the prebuilt libtokenizers.a is
# a GNU build), so this uses debian-based images rather than Alpine.
FROM golang:1.26-bookworm AS builder

# Fetch the pinned upstream release.
RUN git clone --depth 1 --branch v1.0.0 \
https://github.com/BackendStack21/go-prompt-injection-guard.git /src
WORKDIR /src

# Fetch native libs (tokenizers static + ONNX Runtime shared) and build both
# binaries.
RUN make libtokenizers libonnxruntime build

# ---- runtime stage ----
FROM debian:bookworm-slim AS runtime
RUN apt-get update \
&& apt-get install -y --no-install-recommends ca-certificates libstdc++6 \
&& rm -rf /var/lib/apt/lists/*

COPY --from=builder /src/bin/piguard /usr/local/bin/piguard
COPY --from=builder /src/bin/piguard-server /usr/local/bin/piguard-server
COPY --from=builder /src/lib/libonnxruntime.so /usr/local/lib/libonnxruntime.so

# The tokenizer code is linked statically; only ONNX Runtime is loaded at
# runtime, located via ORT_DYLIB_PATH.
ENV ORT_DYLIB_PATH=/usr/local/lib/libonnxruntime.so

# Run as a non-root user. /run/piguard holds the Unix socket (share it with
# clients via a volume); /models holds the exported model (mount it read-only).
RUN useradd --system --uid 10001 piguard \
&& mkdir -p /run/piguard /models \
&& chown -R piguard /run/piguard
USER piguard

ENTRYPOINT ["piguard-server"]
CMD ["--socket", "/run/piguard/piguard.sock", "--model-dir", "/models"]
Loading