mirror of
https://github.com/garrytan/gstack.git
synced 2026-09-22 12:50:50 +02:00
v1.87.0.0 feat: add verified CSO audits and replayable repair bundles (#2852)
* feat(cso): add verified audits and replayable repair bundles * fix(cso): harden qualification and setup boundaries * fix(cso): assemble security canaries at runtime * fix(cso): bound release proof and maintenance work Co-Authored-By: OpenAI Codex <noreply@openai.com> * fix(cso): require complete evaluation reports Co-Authored-By: OpenAI Codex <noreply@openai.com> * fix(cso): replay expired snapshots from supplied source Co-Authored-By: OpenAI Codex <noreply@openai.com> * test(cso): synchronize DNS cancellation assertion Co-Authored-By: OpenAI Codex <noreply@openai.com> * chore(ship): exempt repository owner from liveness proof Co-Authored-By: OpenAI Codex <noreply@openai.com> * test(cso): make recheck retention overlap deterministic Co-Authored-By: OpenAI Codex <noreply@openai.com> * chore: bump version and changelog (v1.85.0.0) Co-Authored-By: OpenAI Codex <noreply@openai.com> * fix(cso): pass native release gates Co-Authored-By: OpenAI Codex <noreply@openai.com> * chore: move release to v1.86.0.0 Co-Authored-By: OpenAI Codex <noreply@openai.com> * fix(cso): resolve rechecks by finding Co-Authored-By: OpenAI Codex <noreply@openai.com> * chore: move release to v1.87.0.0 Co-Authored-By: OpenAI Codex <noreply@openai.com> * fix(cso): pass macOS and Windows release gates Normalize BSD wc output, compare Windows paths by filesystem identity, preserve portable snapshot race coverage, and narrow POSIX-only Windows fixtures. Co-Authored-By: OpenAI Codex <noreply@openai.com> * fix(cso): harden native verification gates * fix(cso): refine Windows native diagnostics * test(cso): isolate Windows Git startup failure * test(cso): stabilize Windows native diagnostics * fix(cso): support hardened Git on Windows * fix(cso): close final verification gaps * test(cso): bound cold Docker fixture setup * fix(cso): restore cross-platform free-suite gates --------- Co-authored-by: OpenAI Codex <noreply@openai.com>
This commit is contained in:
co-authored by
OpenAI Codex
parent
9f81911136
commit
4a3c6a8a3c
@@ -0,0 +1,109 @@
|
||||
# CSO runtime build and qualification
|
||||
|
||||
These recipes are trusted runtime inputs, not application Dockerfiles. The base
|
||||
and tool inputs are reviewed and pinned per native platform; the resulting
|
||||
gstack images are not yet published or qualified. `runtime-catalog.json`
|
||||
records all ten build-reviewed profiles and deliberately contains no executable
|
||||
image until the release gates have passed.
|
||||
|
||||
Trusted CI re-resolves each recorded source tag to its reviewed index digest,
|
||||
proves that the native manifest is a member of that index, inspects its native
|
||||
image configuration, and executes exact version probes without network access.
|
||||
It validates `BASE_IMAGE` (and Python's `UV_IMAGE`) as reviewed
|
||||
`repository@sha256:<64 lowercase hex>` references before building. Build each
|
||||
profile on Linux amd64 and arm64, record exact runtime and package-manager
|
||||
versions, generate an SBOM and provenance attestations, and verify those
|
||||
attestations before proposing a catalog change. The catalog records their
|
||||
digests, the source commit, and the qualification run. A tag, a successful image
|
||||
build, or an agent-provided `qualified` assertion is insufficient.
|
||||
|
||||
The Rails base additionally needs a compiler, SQLite and PostgreSQL development
|
||||
headers, and the exact Bundler version from its supported fixture matrix.
|
||||
Unsupported native libraries are prerequisites. The Python base includes pip;
|
||||
the separate uv image supplies the exact qualified uv executable.
|
||||
|
||||
The PostgreSQL sidecar is a separate qualified image. It runs as fixed uid/gid
|
||||
10001, creates every validated synthetic Rails database from a read-only policy,
|
||||
and exposes PostgreSQL only on the reproduction group's loopback namespace.
|
||||
Qualification must prove readiness for every declared database before Rails is
|
||||
started and must rebuild a fresh sidecar for each before/after phase.
|
||||
|
||||
All recipes use the fixed `/opt/cso/entrypoint`, uid/gid 10001, and no application
|
||||
source. The runner must still impose network namespaces, seccomp, dropped
|
||||
capabilities, no-new-privileges, a read-only root, bounded tmpfs mounts, resource
|
||||
admission, disabled daemon logging, and a detached watchdog. The image's USER and
|
||||
ENTRYPOINT alone provide none of those guarantees.
|
||||
|
||||
Each application image also contains the compiled `/opt/cso/preparation`
|
||||
helper. Its reviewed version is recorded as `cso-preparation: 1.0.0` in the
|
||||
image build inputs and runtime catalog. Qualification exercises its
|
||||
registry-broker forwarder, lock-bound archive manifest, and offline cache
|
||||
seeding before a digest can be promoted.
|
||||
|
||||
Application qualification also exercises the embedded `/opt/cso/verifier`
|
||||
against positive and deliberately failing assertions. This is independent of
|
||||
the cold-start and private held-out repair gates. PostgreSQL uses its separate
|
||||
multi-database and readiness qualification and cannot present application-only
|
||||
qualification fields.
|
||||
|
||||
The Bun image includes a reviewed `/opt/cso/no-auto-install.toml`. Canonical
|
||||
Bun start and test commands also pass `--no-install` and that exact config, so
|
||||
target execution cannot trigger Bun's runtime automatic installer. The earlier
|
||||
offline `bun install` phase still runs admitted lifecycle scripts with network
|
||||
disabled.
|
||||
|
||||
`preparation.ts` emits acquisition metadata and command descriptions. Acquisition
|
||||
containers receive that metadata and verified public archives only; project code,
|
||||
Gemfiles, hooks, and native extensions run in subsequent network-none containers.
|
||||
Registry host restrictions require the trusted runner's deny-by-default egress
|
||||
mechanism and redirect/DNS checks. Package-manager flags alone are insufficient.
|
||||
|
||||
Source references inspected for these contracts:
|
||||
|
||||
- [Bun installation and frozen locks](https://bun.com/docs/pm/cli/install)
|
||||
- [uv export and `--no-emit-local`](https://docs.astral.sh/uv/reference/cli/)
|
||||
- [RubyGems fetch](https://guides.rubygems.org/command-reference/#gem-fetch)
|
||||
- [Docker attestations](https://docs.docker.com/build/metadata/attestations/)
|
||||
|
||||
Version the catalog together with helper ABI 3. A rollback selects the previous
|
||||
compatible pair. Persisted reports remain readable independently of which
|
||||
runtime pair is active.
|
||||
|
||||
Pull requests run the native build-only matrix without registry publication.
|
||||
Protected main publishes staging images. A separate protected promotion
|
||||
workflow accepts exactly ten `qualified-runtime.json` statements from one
|
||||
successful main run, checks them against the reviewed build matrix, and emits an
|
||||
attested `runtime-catalog.candidate.json`. It verifies that attestation against
|
||||
the exact candidate bytes, source commit, protected-main ref, and promotion
|
||||
workflow identity. A previous-revision compare-and-swap then copies those exact
|
||||
bytes to a fresh branch and opens an ordinary review PR. The workflow never
|
||||
updates `main` directly. The catalog validator also recomputes the retained
|
||||
runtime-matrix digest; the complete release-gate statement digest remains a
|
||||
separate provenance field.
|
||||
|
||||
GHCR creates each new staging package private. After its bootstrap publication,
|
||||
a package administrator must make it public in GitHub's package settings before
|
||||
the workflow can continue; GitHub treats that visibility change as
|
||||
irreversible. Staging, native qualification, private qualification ingress, and
|
||||
catalog promotion all fail closed unless GitHub's package API reports `public`
|
||||
and a Docker client using a fresh config with empty `auths`
|
||||
pulls the exact platform digest. The protected workflows never treat their own
|
||||
GHCR login as evidence that users can acquire a promoted runtime.
|
||||
|
||||
Each application statement must attest successful containment, public-only
|
||||
acquisition, offline lifecycle work, cold start, positive and deliberately
|
||||
failing verifier assertions, watchdog cleanup, secret-canary checks, the
|
||||
accuracy gates, and a private held-out runtime-tested repair. Rails also requires both
|
||||
database modes and native extensions. PostgreSQL requires containment, cold
|
||||
start, multiple databases, readiness, watchdog cleanup, and secret canaries.
|
||||
Until a protected run produces all ten statements, the reviewed profiles remain
|
||||
visible to `--doctor` but target execution returns
|
||||
`MISSING_QUALIFIED_RUNTIME`.
|
||||
|
||||
The protected `cso-runtime-release` environment also defines
|
||||
`CSO_QUALIFICATION_ACTOR`, the service account allowed to send the
|
||||
`cso-runtime-qualified` repository dispatch. The ingress workflow verifies the
|
||||
actor, re-verifies each staged OCI provenance and SBOM attestation, normalizes
|
||||
the evidence to its own run identity, and validates the full matrix before it
|
||||
uploads `cso-qualified-runtime-statements`. Private assertion content never
|
||||
enters this repository or the artifact.
|
||||
@@ -0,0 +1,96 @@
|
||||
{
|
||||
"schemaVersion": 1,
|
||||
"helperAbi": 3,
|
||||
"state": "reviewed",
|
||||
"revision": "cso-runtime-inputs-2026-09-10",
|
||||
"reviewedAt": "2026-09-10T00:00:00.000Z",
|
||||
"reviewMethod": "Native OCI manifest inspection plus upstream runtime version metadata; CI rechecks architecture and executable versions before every build.",
|
||||
"sbomGenerator": {
|
||||
"source": "docker.io/docker/scout-sbom-indexer:1",
|
||||
"indexImage": "docker.io/docker/scout-sbom-indexer@sha256:4b67f29eb0d1244ab0f62de867ac5dafd7262fcd7ebbdefa6ec8aacd6b15252d",
|
||||
"images": {
|
||||
"linux/amd64": "docker.io/docker/scout-sbom-indexer@sha256:dc9450ee50d985e1f5cc60069c91b5f45b4a8a7e9dbcdd33aaab259032a9cab9",
|
||||
"linux/arm64": "docker.io/docker/scout-sbom-indexer@sha256:f11b16a96cdf4d6df23994e6c424bc6717959373679e9a0dde36b92a8b03e386"
|
||||
}
|
||||
},
|
||||
"profiles": [
|
||||
{
|
||||
"id": "node-24.4.0",
|
||||
"stack": "node",
|
||||
"source": "docker.io/library/node:24.4.0-bookworm-slim",
|
||||
"indexImage": "docker.io/library/node@sha256:1b044a60874f1b57ac8c4e708ddb3a00e55b34586ebbacce09a48796dafcc799",
|
||||
"baseImages": {
|
||||
"linux/amd64": "docker.io/library/node@sha256:f2beab5c8aa1c35bfec1e7ddcdc8e78fd82a56f96fc514baf2ce86d7dc1b100f",
|
||||
"linux/arm64": "docker.io/library/node@sha256:821c8ce03d9778dbdbbb94919b3bf281837c1a31517e7dee528bd4b274991218"
|
||||
},
|
||||
"versions": {
|
||||
"node": "24.4.0",
|
||||
"npm": "11.4.2",
|
||||
"cso-preparation": "1.0.0"
|
||||
}
|
||||
},
|
||||
{
|
||||
"id": "bun-1.3.10",
|
||||
"stack": "bun",
|
||||
"source": "docker.io/oven/bun:1.3.10-debian",
|
||||
"indexImage": "docker.io/oven/bun@sha256:367842b35abbdf23f39e23c71f3a08eee940ff2679a14e08a5afcf4a1436cd89",
|
||||
"baseImages": {
|
||||
"linux/amd64": "docker.io/oven/bun@sha256:5ee6c5be4575d5ba079b5a9afb24d4600f75ccb1a92602f079ee99560b9dcee9",
|
||||
"linux/arm64": "docker.io/oven/bun@sha256:b0bdc79f333b728119c6527be6bd52cca09352b7fce46613d2fe3d24c6e395e7"
|
||||
},
|
||||
"versions": {
|
||||
"bun": "1.3.10",
|
||||
"cso-preparation": "1.0.0"
|
||||
}
|
||||
},
|
||||
{
|
||||
"id": "python-3.13.4-uv-0.8.0",
|
||||
"stack": "python",
|
||||
"source": "docker.io/library/python:3.13.4-slim-bookworm",
|
||||
"indexImage": "docker.io/library/python@sha256:9ed09f78253eb4f029f3d99e07c064f138a6f1394932c3807b3d0738a674d33b",
|
||||
"baseImages": {
|
||||
"linux/amd64": "docker.io/library/python@sha256:25fab3d7d1d7b2e955f8b39ad49b70e5ddfdc32c202069bd52e34e151eb8704c",
|
||||
"linux/arm64": "docker.io/library/python@sha256:d27f102f1850c0886b0d1df3718a0a31d8e88aae343506e61ef2966ae468abea"
|
||||
},
|
||||
"uvSource": "ghcr.io/astral-sh/uv:0.8.0",
|
||||
"uvIndexImage": "ghcr.io/astral-sh/uv@sha256:5778d479c0fd7995fedd44614570f38a9d849256851f2786c451c220d7bd8ccd",
|
||||
"uvImages": {
|
||||
"linux/amd64": "ghcr.io/astral-sh/uv@sha256:50fbd66ab876ddb7a725f4d2014a59aa31da0b69933f787b8cfba7291ea5494f",
|
||||
"linux/arm64": "ghcr.io/astral-sh/uv@sha256:24d469099a90d1348137db1ec9bf06dac5426ae9de4d669b8a4b811559058c60"
|
||||
},
|
||||
"versions": {
|
||||
"python": "3.13.4",
|
||||
"uv": "0.8.0",
|
||||
"cso-preparation": "1.0.0"
|
||||
}
|
||||
},
|
||||
{
|
||||
"id": "rails-ruby-3.4.4",
|
||||
"stack": "rails",
|
||||
"source": "docker.io/library/ruby:3.4.4-bookworm",
|
||||
"indexImage": "docker.io/library/ruby@sha256:f7ab76e2c36ab406ebc36aeba20624b26a8fae7c2998acabbe9662e2a73f00f3",
|
||||
"baseImages": {
|
||||
"linux/amd64": "docker.io/library/ruby@sha256:edfda7d45b762e5ef89d7e94f0d4405132e129928440b8c8af100bd1d07c37b1",
|
||||
"linux/arm64": "docker.io/library/ruby@sha256:9a4b3512d9fa4f1cc3b8193e141eb5f775ef5cbd8d99c8dd2a1d829c9c835541"
|
||||
},
|
||||
"versions": {
|
||||
"ruby": "3.4.4",
|
||||
"bundler": "2.6.7",
|
||||
"cso-preparation": "1.0.0"
|
||||
}
|
||||
},
|
||||
{
|
||||
"id": "postgresql-17.2",
|
||||
"stack": "postgresql",
|
||||
"source": "docker.io/library/postgres:17.2-bookworm",
|
||||
"indexImage": "docker.io/library/postgres@sha256:3267c505060a0052e5aa6e5175a7b41ab6b04da2f8c4540fc6e98a37210aa2d3",
|
||||
"baseImages": {
|
||||
"linux/amd64": "docker.io/library/postgres@sha256:0e3fd61dc630bf506330e3f2061cb6120cf4cc04cb7bd0f17683b35cc422342d",
|
||||
"linux/arm64": "docker.io/library/postgres@sha256:b1eff56c2661dadeb2a455f9197c5f4e97582e439191790d8b778e47409d10e7"
|
||||
},
|
||||
"versions": {
|
||||
"postgresql": "17.2"
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,2 @@
|
||||
[install]
|
||||
auto = "disable"
|
||||
@@ -0,0 +1,14 @@
|
||||
# Both Bun and its Node-compatible toolchain must be qualified at exact versions.
|
||||
ARG BASE_IMAGE
|
||||
FROM ${BASE_IMAGE}
|
||||
USER root
|
||||
RUN mkdir -p /opt/cso /work /metadata /archives /source /policy /fixtures && touch /opt/cso/empty-config \
|
||||
&& chown 10001:10001 /work /metadata /archives
|
||||
COPY --chmod=0555 entrypoint /opt/cso/entrypoint
|
||||
COPY --chmod=0555 run-app /opt/cso/run-app
|
||||
COPY --chmod=0555 gstack-cso-verifier /opt/cso/verifier
|
||||
COPY --chmod=0555 gstack-cso-preparation /opt/cso/preparation
|
||||
COPY --chmod=0444 bun-no-auto-install.toml /opt/cso/no-auto-install.toml
|
||||
USER 10001:10001
|
||||
WORKDIR /work
|
||||
ENTRYPOINT ["/opt/cso/entrypoint"]
|
||||
@@ -0,0 +1,14 @@
|
||||
#!/bin/sh
|
||||
set -eu
|
||||
umask 077
|
||||
export PATH=/usr/local/bin:/usr/bin:/bin
|
||||
export HOME=/work/.cso-home
|
||||
unset BUN_OPTIONS BUN_BE_BUN NODE_OPTIONS RUBYOPT RUBYLIB PYTHONPATH PYTHONHOME LD_PRELOAD LD_LIBRARY_PATH ENV BASH_ENV CDPATH
|
||||
if [ "$#" -eq 0 ]; then
|
||||
echo 'CSO runtime requires an explicit command' >&2
|
||||
exit 64
|
||||
fi
|
||||
case "$1" in
|
||||
/*) exec "$@" ;;
|
||||
*) echo 'CSO runtime requires an absolute executable path' >&2; exit 64 ;;
|
||||
esac
|
||||
@@ -0,0 +1,12 @@
|
||||
# BASE_IMAGE must be a reviewed, provenance-verified node image@sha256 digest.
|
||||
ARG BASE_IMAGE
|
||||
FROM ${BASE_IMAGE}
|
||||
RUN mkdir -p /opt/cso /work /metadata /archives /source /policy /fixtures && touch /opt/cso/empty-config \
|
||||
&& chown 10001:10001 /work /metadata /archives
|
||||
COPY --chmod=0555 entrypoint /opt/cso/entrypoint
|
||||
COPY --chmod=0555 run-app /opt/cso/run-app
|
||||
COPY --chmod=0555 gstack-cso-verifier /opt/cso/verifier
|
||||
COPY --chmod=0555 gstack-cso-preparation /opt/cso/preparation
|
||||
USER 10001:10001
|
||||
WORKDIR /work
|
||||
ENTRYPOINT ["/opt/cso/entrypoint"]
|
||||
@@ -0,0 +1,15 @@
|
||||
#!/bin/sh
|
||||
set -eu
|
||||
test "$#" -eq 1
|
||||
policy="$1"
|
||||
case "$policy" in /policy/*) ;; *) exit 64 ;; esac
|
||||
test -f /work/postgresql.ready
|
||||
export PGPASSWORD=cso-disposable-test
|
||||
count=0
|
||||
while IFS= read -r database || test -n "$database"; do
|
||||
case "$database" in cso_[A-Za-z_]*) ;; *) exit 64 ;; esac
|
||||
case "$database" in *[!A-Za-z0-9_]*) exit 64 ;; esac
|
||||
count=$((count + 1)); test "$count" -le 64
|
||||
test "$(/opt/cso/bin/psql -h 127.0.0.1 -p 5432 -U cso -d "$database" -Atqc 'SELECT 1')" = 1
|
||||
done < "$policy"
|
||||
test "$count" -gt 0
|
||||
@@ -0,0 +1,26 @@
|
||||
# BASE_IMAGE must be a reviewed PostgreSQL image@sha256 digest. The image is
|
||||
# rebuilt with a fixed non-root identity so Docker policy and initdb agree.
|
||||
ARG BASE_IMAGE
|
||||
FROM ${BASE_IMAGE} AS upstream
|
||||
|
||||
# A fresh image configuration prevents an upstream VOLUME declaration from
|
||||
# creating an unbounded anonymous host volume behind the read-only root policy.
|
||||
FROM scratch
|
||||
COPY --from=upstream / /
|
||||
ENV LANG=C.UTF-8 \
|
||||
LC_ALL=C.UTF-8 \
|
||||
PGDATA=/work/postgresql-data \
|
||||
PATH=/opt/cso/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
|
||||
USER root
|
||||
RUN set -eu; \
|
||||
if ! awk -F: '$3 == 10001 { found=1 } END { exit found ? 0 : 1 }' /etc/group; then printf 'cso:x:10001:\n' >> /etc/group; fi; \
|
||||
if ! awk -F: '$3 == 10001 { found=1 } END { exit found ? 0 : 1 }' /etc/passwd; then printf 'cso:x:10001:10001:CSO PostgreSQL:/work:/sbin/nologin\n' >> /etc/passwd; fi; \
|
||||
mkdir -p /opt/cso/bin /work /policy; chown 10001:10001 /work; \
|
||||
for tool in initdb postgres createdb psql pg_isready; do target="$(find /usr/lib/postgresql /usr/local -type f -name "$tool" -perm /0111 -print 2>/dev/null | sort | head -n 1)"; test -n "$target"; ln -s "$target" "/opt/cso/bin/$tool"; done
|
||||
COPY --chmod=0555 entrypoint /opt/cso/entrypoint
|
||||
COPY --chmod=0555 run-postgresql /opt/cso/run-postgresql
|
||||
COPY --chmod=0555 postgresql-ready /opt/cso/postgresql-ready
|
||||
COPY --chmod=0555 gstack-cso-verifier /opt/cso/verifier
|
||||
USER 10001:10001
|
||||
WORKDIR /work
|
||||
ENTRYPOINT ["/opt/cso/entrypoint"]
|
||||
@@ -0,0 +1,15 @@
|
||||
# Trusted CI supplies reviewed digest references for both stages, never tags.
|
||||
ARG UV_IMAGE
|
||||
ARG BASE_IMAGE
|
||||
FROM ${UV_IMAGE} AS uv
|
||||
FROM ${BASE_IMAGE}
|
||||
COPY --from=uv /uv /usr/local/bin/uv
|
||||
RUN mkdir -p /opt/cso /work /metadata /archives /source /policy /fixtures && touch /opt/cso/empty-config \
|
||||
&& chown 10001:10001 /work /metadata /archives
|
||||
COPY --chmod=0555 entrypoint /opt/cso/entrypoint
|
||||
COPY --chmod=0555 run-app /opt/cso/run-app
|
||||
COPY --chmod=0555 gstack-cso-verifier /opt/cso/verifier
|
||||
COPY --chmod=0555 gstack-cso-preparation /opt/cso/preparation
|
||||
USER 10001:10001
|
||||
WORKDIR /work
|
||||
ENTRYPOINT ["/opt/cso/entrypoint"]
|
||||
@@ -0,0 +1,33 @@
|
||||
{
|
||||
"schemaVersion": 1,
|
||||
"helperAbi": 3,
|
||||
"state": "enforced",
|
||||
"buildRevision": "cso-runtime-inputs-2026-09-10",
|
||||
"platforms": ["linux/amd64", "linux/arm64"],
|
||||
"profiles": ["node", "bun", "python", "rails", "postgresql"],
|
||||
"statementArtifact": "cso-qualified-runtime-statements",
|
||||
"statementFilename": "qualified-runtime.json",
|
||||
"requiredInputs": [
|
||||
"reviewed native base and SBOM generator manifests",
|
||||
"exact runtime and package-manager versions verified inside the selected base",
|
||||
"immutable staged runtime digest",
|
||||
"trusted protected-main source commit and workflow run",
|
||||
"verified SBOM and provenance digests"
|
||||
],
|
||||
"requiredChecks": [
|
||||
"non-root/read-only/capability/seccomp admission",
|
||||
"IPv4/IPv6/DNS and metadata egress denied",
|
||||
"secretless cold acquisition and offline boot",
|
||||
"application verifier positive and deliberately failing assertions",
|
||||
"lifecycle and native build hooks execute only offline",
|
||||
"Rails SQLite and PostgreSQL, all connections, native gem cold start",
|
||||
"one held-out reproduced defect and runtime-tested repair per application stack",
|
||||
"watchdog survival and exact resource cleanup",
|
||||
"secret-canary containment",
|
||||
"daily precision and comprehensive high/critical recall release thresholds",
|
||||
"signed provenance verification and SBOM digest"
|
||||
],
|
||||
"promotion": "The protected promotion workflow accepts exactly ten authenticated same-run qualified-runtime.json statements and emits an attested source-review candidate. It never writes the catalog.",
|
||||
"externalPrerequisite": "A successful protected-main qualification run must upload cso-qualified-runtime-statements after private held-out and accuracy gates finish. No such artifact exists until those external gates actually pass.",
|
||||
"rollback": "Select the prior compatible helper/catalog pair; never fall back to a mutable tag."
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
# BASE_IMAGE is a reviewed Ruby/Bundler image digest that already contains the
|
||||
# qualified compiler, SQLite development headers, and libpq development headers.
|
||||
# This recipe never resolves OS packages dynamically or installs project gems.
|
||||
ARG BASE_IMAGE
|
||||
FROM ${BASE_IMAGE}
|
||||
RUN mkdir -p /opt/cso /work /metadata /archives /source /policy /fixtures && touch /opt/cso/empty-config \
|
||||
&& chown 10001:10001 /work /metadata /archives
|
||||
COPY --chmod=0555 entrypoint /opt/cso/entrypoint
|
||||
COPY --chmod=0555 run-app /opt/cso/run-app
|
||||
COPY --chmod=0555 gstack-cso-verifier /opt/cso/verifier
|
||||
COPY --chmod=0555 gstack-cso-preparation /opt/cso/preparation
|
||||
USER 10001:10001
|
||||
WORKDIR /work
|
||||
ENTRYPOINT ["/opt/cso/entrypoint"]
|
||||
@@ -0,0 +1,5 @@
|
||||
#!/bin/sh
|
||||
set -eu
|
||||
test "$PWD" = /work
|
||||
/bin/cp -a --no-preserve=ownership /source/. /work/
|
||||
exec "$@"
|
||||
@@ -0,0 +1,55 @@
|
||||
#!/bin/sh
|
||||
set -eu
|
||||
umask 077
|
||||
test "$PWD" = /work
|
||||
test "$#" -eq 1
|
||||
policy="$1"
|
||||
case "$policy" in /policy/*) ;; *) exit 64 ;; esac
|
||||
test -f "$policy"
|
||||
count=0
|
||||
while IFS= read -r database || test -n "$database"; do
|
||||
case "$database" in cso_[A-Za-z_]*) ;; *) exit 64 ;; esac
|
||||
case "$database" in *[!A-Za-z0-9_]*) exit 64 ;; esac
|
||||
test "${#database}" -le 52
|
||||
count=$((count + 1)); test "$count" -le 64
|
||||
done < "$policy"
|
||||
test "$count" -gt 0
|
||||
|
||||
data=/work/postgresql-data
|
||||
socket=/work/postgresql-socket
|
||||
password=/work/postgresql-password
|
||||
mkdir -m 700 "$socket"
|
||||
printf '%s\n' 'cso-disposable-test' > "$password"
|
||||
/opt/cso/bin/initdb -D "$data" --username=cso --pwfile="$password" --auth-local=scram-sha-256 --auth-host=scram-sha-256 >/dev/null
|
||||
rm -f "$password"
|
||||
cat >> "$data/postgresql.conf" <<'EOF'
|
||||
listen_addresses = '127.0.0.1'
|
||||
port = 5432
|
||||
unix_socket_directories = '/work/postgresql-socket'
|
||||
ssl = off
|
||||
max_connections = 32
|
||||
password_encryption = 'scram-sha-256'
|
||||
fsync = off
|
||||
synchronous_commit = off
|
||||
full_page_writes = off
|
||||
EOF
|
||||
|
||||
cleanup() {
|
||||
if test -n "${postgres_pid:-}" && kill -0 "$postgres_pid" 2>/dev/null; then
|
||||
kill -TERM "$postgres_pid" 2>/dev/null || true
|
||||
wait "$postgres_pid" 2>/dev/null || true
|
||||
fi
|
||||
}
|
||||
trap cleanup EXIT INT TERM
|
||||
/opt/cso/bin/postgres -D "$data" >/dev/null 2>&1 &
|
||||
postgres_pid=$!
|
||||
export PGPASSWORD=cso-disposable-test
|
||||
attempt=0
|
||||
until /opt/cso/bin/pg_isready -h 127.0.0.1 -p 5432 -U cso -d postgres >/dev/null 2>&1; do
|
||||
attempt=$((attempt + 1)); test "$attempt" -lt 100; sleep 0.05
|
||||
done
|
||||
while IFS= read -r database || test -n "$database"; do
|
||||
/opt/cso/bin/createdb -h 127.0.0.1 -p 5432 -U cso "$database" >/dev/null
|
||||
done < "$policy"
|
||||
printf 'ready\n' > /work/postgresql.ready
|
||||
wait "$postgres_pid"
|
||||
Reference in New Issue
Block a user