mirror of
https://github.com/paperclipai/paperclip
synced 2026-04-25 17:25:15 +02:00
ci: validate Dockerfile deps stage in PR policy (#1799)
* ci: add Dockerfile deps stage validation to PR policy Checks that all workspace package.json files and the patches/ directory are copied into the Dockerfile deps stage. Prevents the Docker build from breaking when new packages or patches are added without updating the Dockerfile. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * ci: scope Dockerfile check to deps stage and derive workspace roots Address Greptile review feedback: - Use awk to extract only the deps stage before grepping, preventing false positives from COPY lines in other stages - Derive workspace search roots from pnpm-workspace.yaml instead of hardcoding them, so new top-level workspaces are automatically covered * ci: guard against empty workspace roots in Dockerfile check Fail early if pnpm-workspace.yaml parsing yields no search roots, preventing a silent false-pass from find defaulting to cwd. * ci: guard against empty deps stage extraction Fail early with a clear error if awk cannot find the deps stage in the Dockerfile, instead of producing misleading "missing COPY" errors. * ci: deduplicate find results from overlapping workspace roots Use sort -u instead of sort to prevent duplicate error messages when nested workspace globs (e.g. packages/* and packages/adapters/*) cause the same package.json to be found twice. * ci: anchor grep to ^COPY to ignore commented-out Dockerfile lines Prevents false negatives when a COPY directive is commented out (e.g. # COPY packages/foo/package.json). --------- Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
40
.github/workflows/pr.yml
vendored
40
.github/workflows/pr.yml
vendored
@@ -40,6 +40,46 @@ jobs:
|
||||
with:
|
||||
node-version: 24
|
||||
|
||||
- name: Validate Dockerfile deps stage
|
||||
run: |
|
||||
missing=0
|
||||
|
||||
# Extract only the deps stage from the Dockerfile
|
||||
deps_stage="$(awk '/^FROM .* AS deps$/{found=1; next} found && /^FROM /{exit} found{print}' Dockerfile)"
|
||||
|
||||
if [ -z "$deps_stage" ]; then
|
||||
echo "::error::Could not extract deps stage from Dockerfile (expected 'FROM ... AS deps')"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Derive workspace search roots from pnpm-workspace.yaml (exclude dev-only packages)
|
||||
search_roots="$(grep '^ *- ' pnpm-workspace.yaml | sed 's/^ *- //' | sed 's/\*$//' | grep -v 'examples' | grep -v 'create-paperclip-plugin' | tr '\n' ' ')"
|
||||
|
||||
if [ -z "$search_roots" ]; then
|
||||
echo "::error::Could not derive workspace roots from pnpm-workspace.yaml"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Check all workspace package.json files are copied in the deps stage
|
||||
for pkg in $(find $search_roots -maxdepth 2 -name package.json -not -path '*/examples/*' -not -path '*/create-paperclip-plugin/*' -not -path '*/node_modules/*' 2>/dev/null | sort -u); do
|
||||
dir="$(dirname "$pkg")"
|
||||
if ! echo "$deps_stage" | grep -q "^COPY ${dir}/package.json"; then
|
||||
echo "::error::Dockerfile deps stage missing: COPY ${pkg} ${dir}/"
|
||||
missing=1
|
||||
fi
|
||||
done
|
||||
|
||||
# Check patches directory is copied if it exists
|
||||
if [ -d patches ] && ! echo "$deps_stage" | grep -q '^COPY patches/'; then
|
||||
echo "::error::Dockerfile deps stage missing: COPY patches/ patches/"
|
||||
missing=1
|
||||
fi
|
||||
|
||||
if [ "$missing" -eq 1 ]; then
|
||||
echo "Dockerfile deps stage is out of sync. Update it to include the missing files."
|
||||
exit 1
|
||||
fi
|
||||
|
||||
- name: Validate dependency resolution when manifests change
|
||||
run: |
|
||||
changed="$(git diff --name-only "${{ github.event.pull_request.base.sha }}" "${{ github.event.pull_request.head.sha }}")"
|
||||
|
||||
Reference in New Issue
Block a user