Skip to content

Commit f2aafad

Browse files
committed
ci(docker): build site once and package per-arch
The multi-arch Docker build previously ran npm ci + npm run build for each target platform despite producing identical static assets. Add an overridable site-dist stage to the Dockerfile that CI replaces via --build-context site-dist=./dist. The workflow now builds the site once natively with Node.js on the runner, then the multi-arch step only packages the pre-built dist into nginx.
1 parent 013721d commit f2aafad

3 files changed

Lines changed: 27 additions & 10 deletions

File tree

.dockerignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,3 @@
11
node_modules/
2+
dist/
23
.git/

.github/workflows/docker-publish.yml

Lines changed: 20 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -62,16 +62,30 @@ jobs:
6262
type=semver,pattern={{major}}.{{minor}},value=${{ steps.release_tag.outputs.value }},enable=${{ steps.release_tag.outputs.is_release == 'true' }}
6363
type=semver,pattern={{major}},value=${{ steps.release_tag.outputs.value }},enable=${{ steps.release_tag.outputs.is_release == 'true' && !startsWith(steps.release_tag.outputs.value, 'v0.') }}
6464
65+
- name: Compute short SHA
66+
id: vars
67+
run: echo "short_sha=$(git rev-parse --short HEAD)" >> $GITHUB_OUTPUT
68+
69+
- name: Set up Node.js
70+
uses: actions/setup-node@53b83947a5a98c8d113130e565377fae1a50d02f # v6.3.0
71+
with:
72+
node-version: '24'
73+
cache: 'npm'
74+
75+
- name: Build site
76+
env:
77+
VITE_BUILD_HASH: ${{ steps.vars.outputs.short_sha }}
78+
VITE_IS_RELEASE_TAG: ${{ steps.release_tag.outputs.is_release }}
79+
run: |
80+
npm ci --ignore-scripts
81+
NODE_OPTIONS=--max_old_space_size=4096 npm run build
82+
6583
- name: Set up QEMU
6684
uses: docker/setup-qemu-action@c7c53464625b32c7a7e944ae62b3e17d2b600130 # v3.7.0
6785

6886
- name: Set up Docker Buildx
6987
uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3.12.0
7088

71-
- name: Compute short SHA
72-
id: vars
73-
run: echo "short_sha=$(git rev-parse --short HEAD)" >> $GITHUB_OUTPUT
74-
7589
- name: Build and push Docker image
7690
id: push
7791
uses: docker/build-push-action@10e90e3645eae34f1e60eeb005ba3a3d33f178e8 # v6.19.2
@@ -83,9 +97,8 @@ jobs:
8397
labels: ${{ steps.meta.outputs.labels }}
8498
cache-from: type=gha
8599
cache-to: type=gha,mode=max
86-
build-args: |
87-
VITE_BUILD_HASH=${{ steps.vars.outputs.short_sha }}
88-
VITE_IS_RELEASE_TAG=${{ steps.release_tag.outputs.is_release }}
100+
build-contexts: |
101+
site-dist=./dist
89102
90103
- name: Generate artifact attestation
91104
uses: actions/attest-build-provenance@a2bbfa25375fe432b6a289bc6b6cd05ecd0c4c32 # v4.1.0

Dockerfile

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
## Builder
1+
## Builder (skipped in CI via --build-context site-dist=./dist)
22
FROM --platform=$BUILDPLATFORM node:24.13.1-alpine AS builder
33

44
WORKDIR /src
@@ -14,12 +14,15 @@ COPY . /src/
1414
ENV NODE_OPTIONS=--max_old_space_size=4096
1515
RUN npm run build
1616

17+
## Overridable dist stage — CI replaces this with pre-built assets
18+
FROM scratch AS site-dist
19+
COPY --from=builder /src/dist /
1720

1821
## App
1922
FROM nginx:1.29.5-alpine
2023

21-
COPY --from=builder /src/dist /app
22-
COPY --from=builder /src/docker-nginx.conf /etc/nginx/conf.d/default.conf
24+
COPY --from=site-dist / /app
25+
COPY docker-nginx.conf /etc/nginx/conf.d/default.conf
2326

2427
RUN rm -rf /usr/share/nginx/html \
2528
&& ln -s /app /usr/share/nginx/html

0 commit comments

Comments
 (0)