1
- # Builder step
1
+ # Start with the latest version of hardened builder image
2
+ FROM cgr.dev/chainguard/wolfi-base:latest AS builder
2
3
3
- # Use version defined in .nvmrc when calling build command
4
- ARG NODE_VERSION=latest
5
- # Need dev version to use corepack
6
- # FROM cgr.dev/chainguard/node:${NODE_VERSION}-dev AS build
7
- FROM node:${NODE_VERSION}-alpine AS builder
4
+ # Install required dependencies
5
+ RUN apk add --no-cache bash curl git ca-certificates libstdc++ coreutils && \
6
+ update-ca-certificates && \
7
+ touch ~/.bash_profile
8
+
9
+ # Get desired Node.js version and install it
10
+ COPY .nvmrc /tmp/.nvmrc
11
+ RUN export NODE_VERSION=$(cat /tmp/.nvmrc | tr -d '[:space:]' ) && \
12
+ ARCH=$(uname -m) && \
13
+ echo $ARCH && \
14
+ case $ARCH in \
15
+ x86_64) ARCH_NAME="x64" ;; \
16
+ aarch64) ARCH_NAME="arm64" ;; \
17
+ *) echo "Unsupported architecture: $ARCH" && exit 1;; \
18
+ esac && \
19
+ echo "Architecture: $ARCH_NAME" && \
20
+ PLATFORM_ARCH="linux-${ARCH_NAME}" && \
21
+ echo "Platform architecture: $PLATFORM_ARCH https://nodejs.org/dist/v${NODE_VERSION}/node-v${NODE_VERSION}-${PLATFORM_ARCH}.tar.gz" && \
22
+ echo "Installing Node.js version: ${NODE_VERSION} for $ARCH_NAME" && \
23
+ DOWNLOAD_URL="https://nodejs.org/dist/v${NODE_VERSION}/node-v${NODE_VERSION}-${PLATFORM_ARCH}.tar.gz" && \
24
+ echo "Downloading from: $DOWNLOAD_URL" && \
25
+ curl -fsSL --retry 3 "$DOWNLOAD_URL" -o /tmp/node.tar.gz && \
26
+ tar -xzf /tmp/node.tar.gz -C /usr/local --strip-components=1 && \
27
+ rm /tmp/node.tar.gz /tmp/.nvmrc && \
28
+ echo -n "Node.js installed version: " && node -v && \
29
+ echo -n "npm installed version: " && npm -v
30
+
31
+ # Install yarn and resolve vulnerability in cross-spawn, by upgrading it to a version with resolved CVE
32
+ # Newly found CVEs can be resolved in similar manner - by upgrading to the closest fixed version
33
+ RUN apk add --no-cache yarn && \
34
+
35
+ # Extract Node.js version from the image
36
+ SHELL ["/bin/ash" , "-o" , "pipefail" , "-c" ]
37
+ RUN node --version | awk -F'v' '{print $2}'
8
38
WORKDIR /app
9
- # Prep package manager as root
39
+ # Prep package manager as root and drop privileges
10
40
USER root
11
- COPY --chown=node . .
12
- RUN chown node:node ./ && npm install -g corepack
13
- # Run scripts as node
14
- USER node
41
+ COPY --chown=nonroot . .
42
+ RUN chown nonroot:nonroot ./ && npm install -g corepack
43
+ # Run install/buiuld as unprivileged user
44
+ USER nonroot
15
45
RUN yarn install --immutable && yarn build:production
16
46
17
- # Server step
18
-
47
+ # Web server stage
48
+ # This image runs as a unprivileged user by default, so there's no need to explicitly set user - see the Note block in the link below for more context
49
+ # https://edu.chainguard.dev/chainguard/chainguard-images/getting-started/nginx/#advanced-usage
19
50
FROM cgr.dev/chainguard/nginx AS server
20
- COPY ./ nginx.conf /etc/nginx/nginx.conf
51
+ COPY nginx.conf /etc/nginx/nginx.conf
21
52
COPY --from=builder /app/build /usr/share/nginx/html
22
- EXPOSE 8080
53
+ EXPOSE 8080
54
+ CMD ["nginx" , "-g" , "daemon off;" ]
0 commit comments