fix(docker): pin node base back to 24.16.0 to stop premature-close fetch failures (#22673)

## Context

Since v2.19.0 rolled out to prod (2026-07-07), workers are flooded with
mid-body fetch failures — `Invalid response body while trying to fetch
…: Premature close` — on Gmail message import (Sentry TWENTY-SERVER-D3X,
~22k events/day, ~1k users) and, simultaneously, on Cloudflare
custom-domain checks (TWENTY-SERVER-HXW/HXT). Both code paths were
unchanged between v2.18.5 and v2.19.0; their only shared layer is the
runtime HTTP stack.

The one relevant change in v2.19.0 is #22529: the base image bump
`node:24.16.0-alpine` → `node:24.17.0-alpine`. Node 24.17.0 patched
exactly the components under these fetches:
- `http`: CVE-2026-48931 — idle keep-alive sockets in the Agent pool now
get `socket.resume()` + a destroy-on-data guard on every free→reuse
cycle
- `deps`: llhttp 9.4.2 (security bump of the HTTP parser that decides
when a chunked body is complete)

The messaging import loop cycles the same keep-alive socket through the
pool once per message fetched, so any per-cycle failure probability is
amplified by prod volume. (Note: undici's equivalent CVE fix needed two
follow-up commits for races of this exact kind — sockets destroyed while
freshly handed to a request.)

## What this PR does

Pins the base image back to `node:24.16.0-alpine3.23` (same digest
v2.18.5 shipped with) on all four stages, and updates the security note
accordingly.

This doubles as the definitive root-cause test: if the premature-close
rate drops back to its historical baseline on the rebuilt image, the
24.17.0 HTTP-stack change is confirmed and we can file a solid upstream
report to nodejs/node.

## Trade-off — please weigh in

This re-exposes what #22529 fixed: 24.16.0 statically links OpenSSL
3.5.6, so the scanner will re-flag CVE-2026-48930 (TLS embedded-nul
hostname authority rebinding, CVSS 9.8) on the node binary. There is no
24.x release newer than 24.17.0 yet. The Dockerfile carries a TODO to
re-bump as soon as a fixed 24.x ships.

## Related

- #22671 classifies `ERR_STREAM_PREMATURE_CLOSE` as a transient
(retryable) network error at the application level — worth landing
regardless of this rollback, since sync channels currently hard-fail to
`FAILED_UNKNOWN` on what is a plain network race.

<!-- This is an auto-generated description by cubic. -->
<a
href="https://cubic.dev/pr/twentyhq/twenty/pull/22673?utm_source=github"
target="_blank" rel="noopener noreferrer"
data-no-image-dialog="true"><picture><source
media="(prefers-color-scheme: dark)"
srcset="https://www.cubic.dev/buttons/review-in-cubic-dark.svg"><source
media="(prefers-color-scheme: light)"
srcset="https://www.cubic.dev/buttons/review-in-cubic-light.svg"><img
alt="Review in cubic"
src="https://www.cubic.dev/buttons/review-in-cubic-dark.svg"></picture></a>
<!-- End of auto-generated description by cubic. -->
This commit is contained in:
Charles Bochet
2026-07-08 17:19:09 +02:00
committed by GitHub
parent 34c5054bac
commit 840c41e6b7
+11 -8
View File
@@ -2,7 +2,7 @@
# Dependency stages
# ===========================================================================
FROM node:24.17.0-alpine3.23@sha256:7c70d1235c0b4c2bc9eeed5393d19f1bbdde6885ba0d58ba62bb385d7b0f3ff1 AS front-deps
FROM node:24.16.0-alpine3.23@sha256:2bdb65ed1dab192432bc31c95f94155ca5ad7fc1392fb7eb7526ab682fa5bf14 AS front-deps
WORKDIR /app
@@ -20,7 +20,7 @@ COPY ./packages/twenty-client-sdk/package.json /app/packages/twenty-client-sdk/
RUN yarn workspaces focus twenty twenty-front twenty-front-component-renderer twenty-ui twenty-shared twenty-sdk twenty-client-sdk && yarn cache clean && npx nx reset
FROM node:24.17.0-alpine3.23@sha256:7c70d1235c0b4c2bc9eeed5393d19f1bbdde6885ba0d58ba62bb385d7b0f3ff1 AS server-deps
FROM node:24.16.0-alpine3.23@sha256:2bdb65ed1dab192432bc31c95f94155ca5ad7fc1392fb7eb7526ab682fa5bf14 AS server-deps
WORKDIR /app
@@ -84,7 +84,7 @@ RUN if [ -d /app/packages/twenty-front/build ]; then \
# docker build --target twenty-server -f packages/twenty-docker/twenty/Dockerfile .
# ===========================================================================
FROM node:24.17.0-alpine3.23@sha256:7c70d1235c0b4c2bc9eeed5393d19f1bbdde6885ba0d58ba62bb385d7b0f3ff1 AS twenty-server
FROM node:24.16.0-alpine3.23@sha256:2bdb65ed1dab192432bc31c95f94155ca5ad7fc1392fb7eb7526ab682fa5bf14 AS twenty-server
# Force the patched Alpine OpenSSL libs (base bakes 3.5.6-r0; repo ships
# 3.5.7-r0). Node bundles its own OpenSSL, but psql/curl link these system
@@ -137,10 +137,13 @@ LABEL org.opencontainers.image.description="Twenty server image (no frontend)."
# - the Node dev headers: only node-gyp needs them and native addons are
# compiled in the build stages; their vendored openssl/opensslv.h is what
# scanners fingerprint whenever OpenSSL patches ahead of Node releases.
# The pinned node:24.17.0-alpine base (June 18, 2026 security release) statically
# links OpenSSL 3.5.7 and fixes CVE-2026-48930 (TLS embedded-nul hostname
# authority rebinding, CVSS 9.8). Keep the base current when Node ships 24.x
# security releases — the scanner flags the statically-linked node binary itself.
# TODO(2026-07-08): the base is deliberately pinned back to node:24.16.0-alpine.
# 24.17.0's http.Agent/llhttp security patches cause a flood of mid-body
# "Premature close" failures on keep-alive fetches in prod (Gmail/Calendar sync,
# Cloudflare API — see #22671). Trade-off: 24.16.0 statically links OpenSSL 3.5.6,
# so the scanner will re-flag CVE-2026-48930 (TLS embedded-nul hostname authority
# rebinding, CVSS 9.8) on the node binary until we re-bump. Re-bump to the next
# 24.x once the premature-close regression is fixed upstream (nodejs/node).
RUN rm -rf /usr/local/lib/node_modules/npm /usr/local/bin/npm /usr/local/bin/npx \
/usr/local/include/node && \
find /app/node_modules -type d -name example -prune -exec rm -rf {} +
@@ -215,7 +218,7 @@ RUN S6_ARCH=$(cat /tmp/s6arch) && \
echo "$NOARCH_SUM s6-overlay-noarch.tar.xz" | sha256sum -c - && \
echo "$ARCH_SUM s6-overlay-arch.tar.xz" | sha256sum -c -
FROM node:24.17.0-alpine3.23@sha256:7c70d1235c0b4c2bc9eeed5393d19f1bbdde6885ba0d58ba62bb385d7b0f3ff1 AS twenty-app-dev
FROM node:24.16.0-alpine3.23@sha256:2bdb65ed1dab192432bc31c95f94155ca5ad7fc1392fb7eb7526ab682fa5bf14 AS twenty-app-dev
# s6-overlay
COPY --from=s6-fetch /tmp/s6-overlay-noarch.tar.xz /tmp/