Loading
Serve Rspack-built assets in production behind a feature flag
What
Adds a feature flag (rspack_production_assets, default off) that lets Rails serve frontend assets built by Rspack instead of Webpack in production, so the Rspack cutover can be rolled out gradually and reverted instantly.
- Rspack now emits
manifest.rspack.jsonnext to Webpack'smanifest.jsonin the same/assets/webpack/folder. Production assets are content-hashed, so both bundlers' files coexist without collisions, and nginx already serves/assets/webpack/**. Gitlab::Webpack::Manifestaccepts amanifest_filename:(memoized per filename, the default is unchanged), andWebpackHelperselects the Rspack manifest per request (actor: current user) when the flag is on. Public path is unchanged.
Design notes
The flag is evaluated at render time in the helper, not baked into the class-level manifest cache (per the feature-flag guidance against load-time flags). Keeping both manifests in one folder means no nginx change.
CI & packaging
To actually serve Rspack assets in production, the deployed assets image needs to contain both bundlers' output, not just Webpack's.
- A new
build-assets-imagejob merges the Webpack and Rspack compile jobs into a single production assets image, containing both manifests and all content-hashed chunks (they overlay cleanly with no collisions). This applies to both EE (gitlab-assets-ee) and CE (gitlab-assets-ce, viaas-if-foss).compile-production-assetskeeps compiling Webpack and still emits the image tag/hash artifacts that Omnibus, CNG, and release-environments rely on — it just no longer pushes the image itself;build-assets-imagepushes the combined image under the same tag, so downstream consumers are unaffected. - The Webpack and Rspack builds now use separate CI caches (a dedicated
ENABLE_RSPACKassets-hash job plus aGLCI_ASSETS_BUNDLERcache token), so the two builds can no longer clobber or skip each other via a shared cache key. - Trade-off: while the flag is active, the production assets payload is roughly double its usual size, since both bundlers' output ships together. This is temporary and goes away once Webpack is fully removed.
Feature flag
rspack_production_assets, typegitlab_com_derisk, disabled by default.- Disabled by default in the test env: the test asset pipeline builds Webpack only, so
manifest.rspack.jsonis not present there.
Verify
- Build both bundlers into
public/assets/webpack/(Webpackmanifest.json, Rspackmanifest.rspack.json). - With the flag off, pages load Webpack assets (unchanged). Enable
rspack_production_assets, reload, and pages load the Rspack assets with no console errors.
Rollout
This is the production leg of the Rspack cutover:
- Builds on !243058 (merged), which introduced the
ENABLE_RSPACKmechanism andmanifest.rspack.jsonselection this flag reuses. This MR adds the CI/packaging work needed to ship both bundlers in the same production assets image. - The dev cutover is gitlab-development-kit!6068 (merged) (Rspack as the default GDK bundler with zero
gdk.ymlchanges, verified end to end). This MR gates production serving separately behindrspack_production_assetsso dev and production roll out independently. - If prod validation runs beyond the
gitlab_com_derisk2-month window, convert the flag toops(with a runbook and a feature-flags-list entry).
Epic: &22569 · Proposal: #604382 (closed)
Edited by Stanislav Lashmanov