Conversation
Addresses the first increment of #47 (Build reusable, testable, and maintainable Nextcloud container images). One Dockerfile per image, both build channels: - .docker/app/Dockerfile now covers the stable ("release") and the development ("daily") channel through NEXTCLOUD_SOURCE instead of a separate version-specific Dockerfile. Dockerfile.35 is removed; the next Nextcloud major is expressed as build arguments, never as a new file, so a major bump does not add another implementation. - The development channel still verifies the daily tarball against its published .sha512 and now optionally asserts NEXTCLOUD_MAJOR. - Runtime tooling is shared by both channels, so stable and development images follow the same maintenance and security rules. Traceability and reproducibility: - OCI labels (source, revision, created, version) plus LibreCode labels recording the resolved upstream base image and the Nextcloud major. - CI injects VCS_REF and BUILD_DATE so any running container can be traced back to the commit that produced it. - docker-php-extension-installer is pinned to a released version instead of "latest". One reusable build path: - .github/actions/build-and-scan builds and scans a single image for linux/amd64 and linux/arm64, and is reused by every build channel. - The development workflow reuses it, so development images are now scanned with the same Trivy policy before being pushed and are built for both architectures like the stable ones. - The development workflow is version agnostic (workflow_dispatch inputs + a weekly schedule to keep following Nextcloud master). Naming and tagging rules are documented in docs/images.md, together with the reuse policy for consuming repositories. New stable tag nc-<major> allows consumers to pin a Nextcloud major; latest and sha-<commit> keep working exactly as before, and the bare <major> tag is kept as a deprecated alias so existing environments do not break. AGENTS.md records the hard rules and the roadmap so contributors and AI tools follow the same constraints.
|
You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard. |
Second increment of #47. A green build only proves an image compiles; this proves it boots. tests/smoke-test.sh starts the real stack on a throwaway Docker network (postgres 16 + app + web) from the images this repository builds, and asserts that: - Nextcloud actually installs and `occ status --output=json` reports `"installed":true` (the official entrypoint performs the install from the runtime environment, exactly like a real deployment); - the reported Nextcloud major matches the requested one, so a daily build cannot silently ship the wrong major; - the HTTP front-end answers on `status.php` and reports the install; - the OCI traceability labels are present on the app image. The containers are named and aliased exactly like the real compose stack (the web image resolves `app:9000`), so the test exercises the contract the images are published with, not a simplified variant. Everything is torn down on exit; `--keep` preserves the state for debugging and failure logs are printed before exiting. CI runs it on every change to `.docker/**` through .github/workflows/image-smoke-test.yml, for both channels: the stable channel follows `.env.example` (the same source of truth the publish workflow uses) and the development channel accepts major/base inputs. `make smoke-test` and `make smoke-test-dev` run the same check locally.
The scan step is what fails in CI today for both images: the web image is untouched by this pull request and still fails, while the app job only fails after the full build completes, so the failure is in the shared scan step rather than in the build. Two problems made that failure impossible to diagnose from the job summary: the SARIF reports were only uploaded when the scan succeeded, and the script exited silently with a bare status code. Neither told the reader whether Trivy found vulnerabilities or the scanner itself broke. - Upload the SARIF reports with `if: always()` in every workflow, so a red build is diagnosable from the artifacts alone. - Make scripts/scan-images.sh end with an explicit summary: which images failed the policy, which policy file was used and what the policy means. A successful scan now says so explicitly. - Bump Trivy v0.74.0 -> v0.75.0 (released 2026-10-01). The vulnerability DB and the EOL detection evolve with the scanner, and an outdated scanner is a classic source of opaque failures. The policy in trivy.yaml is unchanged: a red scan still blocks publication. - Document the pinned scanner version in README.md and record the "keep local and CI versions identical" rule in docs/images.md, so the next person does not have to guess which Trivy to install.
The scan fails on CVEs that are already fixed in the distribution repository but not present in the published base image: libexpat CVE-2026-93990 2.8.4-r0 -> 2.8.5-r0 pcre2 CVE-2026-103111 10.48-r0 -> 10.49-r0 The upstream tag is not rebuilt the moment a security fix lands in Alpine or Debian, so building straight from it ships vulnerabilities that have a published fix. trivy.yaml only ignores vulnerabilities without a fix, so these findings are correct and the images are what has to change. - web: `apk upgrade --no-cache` after FROM nginx:alpine - app: `apt-get upgrade -y` in the shared tooling layer Both channels get it, since the layer is shared by design. Documented in docs/images.md together with the accepted consequence: building the same commit at different times can produce different OS package versions. That trade-off is deliberate; shipping known vulnerabilities is the worse option. sha-<commit> tags stay immutable. Also recorded the follow-up this exposes: without a scheduled rebuild, published images go stale again and the scan fails the same way the next time a CVE lands. Tracked in AGENTS.md, with the constraint that scheduled runs must not rewrite sha-<commit> tags.
Publication is now behind a boot test, and both channels are refreshed on a schedule so security fixes reach the published images without waiting for a code change. The pattern just seen in this repository is the one being fixed: a CVE lands in the distribution repository, the upstream tag is not rebuilt, the published image ships a vulnerability that already has a fix, and the scan goes red on the next change. Rebuilding weekly breaks that cycle at the source. - docker-image.yml gains a weekly schedule and a `smoke` job that boots the real stack (postgres + app + web) and asserts the install, `occ status`, `status.php` and the OCI labels. `publish` needs it, so an image that compiles but does not boot never reaches the registry, on any run including the scheduled ones. - nextcloud-development.yml runs the same smoke test against the exact development image it scanned, before pushing it. Same gate, and no duplicate build. - Scheduled runs must not rewrite `sha-<commit>`: those tags are immutable by contract and a scheduled rebuild re-reads the distribution repositories, producing a different image for the same commit. They publish internal `build-<run_id>-<arch>` tags and only refresh the rolling tags (`latest`, `nc-<major>`, `dev*`). The standalone image-smoke-test.yml workflow is removed: its job is now performed by the lifecycle workflow itself, which avoids building the images three times on every pull request while keeping the check where it gates something. Local use is unchanged (`make smoke-test`, `make smoke-test-dev`). Docs updated: the `build-*` tag rule, the scheduled refresh contract and the fact that the smoke test is a publication gate.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Addresses the first increment of #47 (Build reusable, testable, and maintainable Nextcloud container images).
One Dockerfile per image, both build channels:
Traceability and reproducibility:
One reusable build path:
Naming and tagging rules are documented in docs/images.md, together with the reuse policy for consuming repositories. New stable tag nc- allows consumers to pin a Nextcloud major; latest and sha- keep working exactly as before, and the bare tag is kept as a deprecated alias so existing environments do not break.
AGENTS.md records the hard rules and the roadmap so contributors and AI tools follow the same constraints.