Skip to content

fix(css): terminate a string or url() the tokenizer closed at EOF - #21624

Merged
alexander-akait merged 14 commits into
mainfrom
fix/css-printer-equivalence-defects
Aug 7, 2026
Merged

alexander-akait merged 14 commits into
mainfrom
fix/css-printer-equivalence-defects

Conversation

@alexander-akait

@alexander-akait alexander-akait commented Aug 6, 2026

Copy link
Copy Markdown
Member

Summary

Three defects found while auditing what the browser equivalence suite had filed. Printer: CSS Syntax §4.3.5 and §4.3.6 end a string and a url() at EOF, so their content stops there; the printer re-emitted such a token as written and then wrote the enclosing }, which the still-open token took into its content — .a{content:"abc printed as .a{content:"abc}. The terminator is now written back, and a \ left dangling at EOF is dropped rather than escaping it. Test suite: every declaration was applied to one shared probe, so a declaration carrying transition-* animated the probe away from the previous rule's value and getComputedStyle read the interpolation — color: limegreen read back as rgb(0, 0, 0) on one side and rgb(0, 128, 0) on the other. Cancelling running animations before the read fixes it, and at-rule-value.module.css leaves FILED_CSS_DEFECTS with the printer untouched, since its CSS and CSSOM were identical on both sides all along. Persistent cache: ModuleDependencyError was never registered with makeSerializable, though its structurally identical sibling ModuleDependencyWarning was, so any module recording one was skipped by the pack ("No serializer registered for ModuleDependencyError") and rebuilt on every run. Refs #21608.

What kind of change does this PR introduce?

fix

Did you add tests for your changes?

For the printer and the suite, yes: two fixtures leave FILED_CSS_DEFECTS in test/SyntaxBrowserEquivalence.unittest.js, whose assertion is exact in both directions — it fails if a defect returns and also if an entry is left behind after a fix — and test/CssSyntax.unittest.js covers the printer directly, including the dangling \ at EOF. Three assertions there were updated because they encoded the old output, which re-parsed to a different string than the source held. The serializer registration has no test of its own yet: its natural one is un-skipping the four configCases/html cases that test.filter.js excludes from the cache suite, and those still fail on further unrelated Restoring failed gaps, so the filters stay for now.

Does this PR introduce a breaking change?

No. The printer path only runs for a string or url() left unterminated at end of file; well-formed input is byte-identical.

If relevant, what needs to be documented once your changes are merged or what have you already documented?

n/a

Use of AI

AI was used. Claude Code reduced each filed defect to a minimal reproduction, proved the second was a measurement artifact rather than a printer bug by logging identical helper input against differing output, traced the third from a PackFileCacheStrategy infrastructure log to the unregistered class, and verified each fix in both directions. A dangling-backslash case reported by Bugbot on an earlier revision was reproduced and fixed here. All changes were reviewed before committing.


Note

Medium Risk
Substantial changes to CSS media parsing and dev-server HTML HMR runtime, plus cache serialization for a common error type; mitigated by broad config/hot-case coverage but HMR head patching has edge cases (duplicate tags, script removal).

Overview
CSS @custom-media now resolves chained names, treats true/false as boolean constants (folding whole @media preludes via a captured MediaNode tree), and inlines condition/type values with clearer warnings for cycles and invalid uses.

CSS printing writes closing quotes/) for strings and url() the tokenizer left open at EOF, using _terminate so a trailing \ does not escape the added terminator (including U+FFFD for unterminated url()).

HTML HMR reconciles authored <head> changes as a multiset delta on outerHTML instead of reloading when only safe edits occur: injected webpack runtime tags stay put, new <script> nodes are recreated so inline code runs, and removing a <script> still forces location.reload(). FakeDocument parses innerHTML for children/outerHTML to exercise this in hot cases.

Persistent cache: ModuleDependencyError is registered with makeSerializable and its constructor tolerates deserialization with no err. AGENTS.md documents cache invalidation causes and discourages test.filter.js cache exclusions; several HTML/error config cases now expect pack writes via infrastructure-log.js instead of being dropped from the cache suite.

Tests: custom-media cases and warnings updated; browser-equivalence probe cancels animations before getComputedStyle; CSS syntax unit tests cover EOF behavior.

Reviewed by Cursor Bugbot for commit 97a00f7. Bugbot is set up for automated code reviews on this repo. Configure here.

@codecov

codecov Bot commented Aug 6, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 94.48052% with 17 lines in your changes missing coverage. Please review.
✅ Project coverage is 94.22%. Comparing base (57177cc) to head (1dedc3b).
⚠️ Report is 1 commits behind head on main.

Files with missing lines Patch % Lines
lib/css/CssParser.js 93.60% 16 Missing ⚠️
lib/css/syntax.js 96.29% 1 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main   #21624      +/-   ##
==========================================
- Coverage   94.23%   94.22%   -0.01%     
==========================================
  Files         628      628              
  Lines       79388    79590     +202     
  Branches    23456    23548      +92     
==========================================
+ Hits        74810    74997     +187     
- Misses       4578     4593      +15     
Flag Coverage Δ
css-parsing 25.97% <10.10%> (-0.05%) ⬇️
html5lib 27.37% <70.00%> (+<0.01%) ⬆️
integration 88.96% <88.96%> (-0.01%) ⬇️
test262 49.19% <50.00%> (+0.03%) ⬆️
unit 51.92% <93.75%> (+0.01%) ⬆️

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@github-actions

github-actions Bot commented Aug 6, 2026

Copy link
Copy Markdown
Contributor

This PR is packaged and the instant preview is available (21af4f5).

Install it locally:

  • npm
npm i -D webpack@https://pkg.pr.new/webpack@21af4f5
  • yarn
yarn add -D webpack@https://pkg.pr.new/webpack@21af4f5
  • pnpm
pnpm add -D webpack@https://pkg.pr.new/webpack@21af4f5

Comment thread lib/css/syntax.js Outdated
expect(min('@unknown [foo="bar\\"')).toBe('@unknown [foo="bar\\""];');
// A `\` left dangling at EOF contributes nothing, so it goes rather than
// escaping the quote written back after it.
expect(min('@unknown [foo="bar\\')).toBe('@unknown [foo="bar"];');

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Config snapshots retain broken output

Low Severity

The direct expectations reflect the added closing quote, but both minimize-strings snapshots still expect the unterminated output. The corresponding ConfigTestCases and ConfigCacheTestCases snapshot assertions will fail.

Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit b5f46f2. Configure here.

@changeset-bot

changeset-bot Bot commented Aug 6, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 1dedc3b

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 1 package
Name Type
webpack Minor

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@codspeed

codspeed Bot commented Aug 6, 2026

Copy link
Copy Markdown

Merging this PR will degrade performance by 11.39%

⚠️ Different runtime environments detected

Some benchmarks with significant performance changes were compared across different runtime environments,
which may affect the accuracy of the results.

Open the report in CodSpeed to investigate

⚡ 1 improved benchmark
❌ 2 regressed benchmarks
✅ 217 untouched benchmarks

Warning

Please fix the performance issues or acknowledge them on CodSpeed.

Performance Changes

Mode Benchmark BASE HEAD Efficiency
Memory benchmark "devtool-eval", scenario '{"name":"mode-development-rebuild","mode":"development","watch":true}' 514 KB 950.1 KB -45.9%
Memory benchmark "future-defaults", scenario '{"name":"mode-production","mode":"production"}' 8.4 MB 10.7 MB -21.29%
Memory benchmark "three-long", scenario '{"name":"mode-development-rebuild","mode":"development","watch":true}' 1,158.6 KB 709.2 KB +63.36%

Tip

Investigate this regression by commenting @codspeedbot fix this regression on this PR, or directly use the CodSpeed MCP with your agent.


Comparing fix/css-printer-equivalence-defects (1dedc3b) with main (57177cc)

Open in CodSpeed

Comment thread lib/errors/ModuleDependencyError.js

@cursor cursor Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes using default effort and found 4 potential issues.

There are 5 total unresolved issues (including 1 from previous review).

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit 96113ad. Configure here.

Comment thread lib/css/CssParser.js
);
if (extra.hasExtra) return CUSTOM_MEDIA_UNSUPPORTED;
if (nested !== undefined) return { kind: "alias", name: nested };
return { kind: "condition", text: valueText };

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Compound aliases discard remaining media conditions

Medium Severity

classifyCustomMedia treats a leading (--name) as a complete alias without checking for subsequent tokens, silently discarding the rest of a compound media condition.

Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit 96113ad. Configure here.

Comment thread lib/css/CssParser.js Outdated
Comment thread lib/html/HtmlGenerator.js
)};`,
`${declare} removed = surplus(oldChildren, newChildren);`,
`${declare} added = surplus(newChildren, oldChildren);`,
"if (removed.length === 0 && added.length === 0) return true;",

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Head patches do not preserve element order

Medium Severity

The multiset diff treats reorder-only updates as unchanged and appends every added node at the end. Head ordering therefore diverges from the updated HTML, affecting stylesheet cascade and script ordering.

Additional Locations (1)
Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit 96113ad. Configure here.

Comment thread test/helpers/FakeDocument.js Outdated
@cursor

cursor Bot commented Aug 7, 2026

Copy link
Copy Markdown

You have used all Bugbot PR reviews included in your team's free trial on GitHub.

To continue using Bugbot reviews, enable Bugbot for your team in the Cursor dashboard.

1 similar comment
@cursor

cursor Bot commented Aug 7, 2026

Copy link
Copy Markdown

You have used all Bugbot PR reviews included in your team's free trial on GitHub.

To continue using Bugbot reviews, enable Bugbot for your team in the Cursor dashboard.

…light

A declaration carrying `transition-*` started a CSS transition on the
shared probe, so `getComputedStyle` returned a value interpolating away
from the previous rule's rather than the one the declaration sets. The
walk order is deterministic, so the two arms read different points of the
same animation and one fixture was filed as a printer defect it never had.
CSS Syntax 4.3.5 and 4.3.6 end a string and a url-token at EOF, so their
content stops there. The printer re-emitted the token as written and then
wrote the enclosing `}`, which the still-open token took into its content:
`.a{content:"abc` printed as `.a{content:"abc}`. Write the terminator back
so the token ends where it ended for the tokenizer. A terminator that is
itself escaped (`"x\\"`) does not close the token, so the check counts
trailing backslashes rather than reading the last character.
A module that records one could not be written to the persistent cache —
"No serializer registered for ModuleDependencyError" — so the pack was
invalidated and the module rebuilt on every run. Its structurally
identical sibling ModuleDependencyWarning was already registered.
Deserialization constructs the class with no arguments, so `err.message`
threw and every restore of a cached compilation error failed. With the
guard the `html/srcset` case restores from the persistent cache and its
`test.filter.js` skip can go.
webpack always rebuilds a module that carries a build error, so the pack
is written to on every run. That is expected, and the repo already states
it with an `infrastructure-log.js` expectation; these three cases skipped
the whole cache suite instead.
A dangling `\` is dropped when a string is closed at EOF (4.3.5 has it
contribute nothing) but not when a url is: 4.3.6 reads it as an escape and
4.3.7 ends one at EOF with U+FFFD, so dropping it changed the url's value.
Write that code point back instead.
Media Queries 5 3 defines `true` and `false` as always- and never-matching,
and lets a value name another custom media. Both were classified unsupported
and left as written.

No `<media-in-parens>` is unconditionally true on every engine, so a constant
is folded into the query around it instead of written out: it drops out of an
`and` / `or` chain, takes the whole query with it when it decides one, and a
list with nothing left prints `not all`. A name standing for another resolves
transitively, with a cycle falling back to the old leave-as-written warning.

Definitions now hold their classification rather than their tokens — node ids
are recycled per top-level rule, so an at-rule's AST cannot outlive the walk
that reaches it, and a name may be defined below its use.
Any `<head>` edit beyond `<title>` reloaded the page, because replacing
`document.head.innerHTML` would tear down the runtime scripts and stylesheet
links webpack injects there on load. Applying only the delta between the two
authored heads cannot: neither string contains an injected node.

A `<script>` in the delta still reloads — one parsed out of a string carries
the already-started flag, so inserting it would never run it — as does a
removal whose element is no longer in the head.

FakeDocument now parses an `innerHTML` fragment (through webpack's own HTML
parser) and exposes `children` / `outerHTML`, which the reconciliation walks.
`Pack got invalid because of write to: X` names something that was rebuilt
rather than restored — work a user's incremental build redoes every time. The
guide had no rule for it, so the reflex was to drop the case from the cache
suite with a `test.filter.js`, which removes every cache assertion the case
had. Name the diagnostics that point at the real cause, allow exactly the one
expected write webpack ships (a module carrying a build error is rebuilt
unconditionally), and require any other expectation to carry its reason.

`define-plugin-runtime-value-errors` was skipping the cache suite for that
one expected write; it states it and runs cached now. The other two opt-outs
assert a throw from `webpack()` itself, which the pre-compile runs have
nowhere to report — they keep the filter, with the reason written down.
Capturing walked node arrays, so every level sliced a fresh one and every
`@media` in a file that defines a custom media built a tree even with no
reference in it. Walk index ranges instead, and check for a reference first —
`childAt` reaches the nested blocks without materializing a child list.

On a stylesheet with one `@custom-media` and 200 unrelated `@media` rules the
capture allocates 1 node instead of 801 and 0 arrays instead of 1604. Emitted
bytes and warnings are unchanged on that file and on both custom-media cases.
An element parsed out of a string carries the already-started flag, so
appending it never runs it — the reconciliation reloaded on any <script> in
the delta. Building a fresh element from its attributes and body does run it,
which is what the reload it replaces would have done.

Removing one still reloads: a script that has run cannot be un-run.

FakeDocument grew what that walks — attributes off the parsed fragment, an
outerHTML serialized from the element's own state rather than the source that
spelled it, and a load that fires only for a script that has a src, matching
when a browser fetches one.
A miss in the memory cache returns `null`, and `null` bails `Cache.hooks.get`
— so it is not "ask the next stage", it is "definitively not cached", and the
file cache is never consulted. Etags were compared by identity, so any asset
whose `Source` is rebuilt each compilation missed on an etag that stringifies
identically to the stored one, then recomputed and stored: re-minified every
build, and the pack invalidated with it.

Three cases already recorded the symptom as unavoidable — "each time returns
different OriginalSource … this prevents hit in inmemory cache". Identity
still decides a hit first, so a warm hit costs no hashing; only a mismatch
falls back to the value the rest of the cache compares etags by.

Ten `infrastructure-log.js` expectations go with it, and stand as the
regression test: they fail again the moment the pack is written to.
…g a miss

Comparing the stringified etags was treating the symptom. A lazy etag is
interned per source object (`getLazyHashedEtag` keys a WeakMap by it), so
equal content reached through a second object is a different etag by
construction — and hashing to tell those apart would cost every hit exactly
what laziness saves.

The defect is that the memory layer answered `null` there. `hooks.get` is an
`AsyncSeriesBailHook`, so `null` bails the chain and the file cache — which
compares etags by value — is never asked. It also buys the caller nothing:
`Cache.get` maps `null` to `undefined` either way. So a mismatch now falls
through, and only an identifier nothing was known about records a miss: an
entry reached with a different etag still answers its own.

Measured on a two-run build of `benchmarkCases/cache-filesystem`: 1029
identity hits out of 2556 gets and zero fall-throughs, so the added stage
costs nothing outside the pattern it fixes.
…in order

Two review findings, both real.

`classifyCustomMedia` read a leading `(--name)` as the whole value, so
`@custom-media --a (--b) and (min-width: 1px)` resolved to `--b` and dropped
the rest. Only a block that *is* the whole value is an alias now; a reference
anywhere else makes the value unresolvable, because nothing outside a `@media`
prelude scans for one — the same hole was open in `not (--b)` and in a comma
segment, and both are closed too.

The head reconciliation appended every addition, so an element authored
between two others landed after them and changed the cascade. Retained
elements are now paired with their live nodes scanning only forward, which
places each addition before the element it precedes and turns a reordering the
delta cannot express into the reload it needs.

FakeDocument's `insertBefore` ignored its reference argument, and parsing into
a detached container registered its children document-wide.
@alexander-akait
alexander-akait force-pushed the fix/css-printer-equivalence-defects branch from 28305e1 to 1dedc3b Compare August 7, 2026 13:05
@cursor

cursor Bot commented Aug 7, 2026

Copy link
Copy Markdown

You have used all Bugbot PR reviews included in your team's free trial on GitHub.

To continue using Bugbot reviews, enable Bugbot for your team in the Cursor dashboard.

@github-actions

github-actions Bot commented Aug 7, 2026

Copy link
Copy Markdown
Contributor

Types Coverage

Coverage after merging fix/css-printer-equivalence-defects into main will be
99.29%
Coverage Report
FileStmtsBranchesFuncsLinesUncovered Lines
bin
   webpack.js98.82%100%100%98.82%103
examples
   build-common.js100%100%100%100%
   buildAll.js100%100%100%100%
   examples.js100%100%100%100%
   template-common.js98.21%100%100%98.21%72
examples/custom-javascript-parser
   test.filter.js100%100%100%100%
examples/custom-javascript-parser/internals
   acorn-parse.js100%100%100%100%
   meriyah-parse.js100%100%100%100%
   oxc-parse.js100%100%100%100%
examples/markdown
   webpack.config.mjs100%100%100%100%
examples/module-federation
   test.filter.js100%100%100%100%
examples/reexport-components
   test.filter.js100%100%100%100%
examples/typescript
   test.filter.js100%100%100%100%
examples/typescript-non-erasable
   test.filter.js50%100%100%50%5
examples/virtual-modules
   test.filter.js100%100%100%100%
examples/wasm-bindgen-esm
   test.filter.js100%100%100%100%
examples/wasm-complex
   test.filter.js100%100%100%100%
examples/wasm-emscripten
   test.filter.js100%100%100%100%
examples/wasm-simple
   test.filter.js100%100%100%100%
examples/wasm-simple-source-phase
   test.filter.js100%100%100%100%
lib
   APIPlugin.js100%100%100%100%
   AsyncDependenciesBlock.js100%100%100%100%
   AutomaticPrefetchPlugin.js100%100%100%100%
   BannerPlugin.js100%100%100%100%
   Cache.js98.21%100%100%98.21%101
   CacheFacade.js100%100%100%100%
   Chunk.js99.72%100%100%99.72%39
   ChunkGraph.js100%100%100%100%
   ChunkGroup.js100%100%100%100%
   ChunkTemplate.js100%100%100%100%
   CircularModulesPlugin.js98.81%100%100%98.81%136
   CleanPlugin.js99.13%100%100%99.13%214, 234
   CodeGenerationResults.js100%100%100%100%
   CompatibilityPlugin.js100%100%100%100%
   Compilation.js98.42%100%100%98.42%1648, 1967, 1974, 1982, 2004, 2007, 2946, 3425–3426, 3458, 4162, 4192, 4245–4246, 4250, 4255, 4271–4272, 4286–4287, 4292–4293, 4773, 4799, 527, 532, 5607, 5639, 5656, 5672, 5688, 5703, 5728–5729, 5731, 6061, 6066, 6072, 6075, 6082, 6094, 6096, 6100, 6116, 6131, 6163, 6217, 6241, 6356, 778–779
   Compiler.js99.56%100%100%99.56%1159–1160, 1168
   ConcatenationScope.js99.12%100%100%99.12%300
   ConditionalInitFragment.js100%100%100%100%
   ConstPlugin.js100%100%100%100%
   ContextExclusionPlugin.js100%100%100%100%
   ContextModule.js99.88%100%100%99.88%1461
   ContextModuleFactory.js97.20%100%100%97.20%266, 435, 456, 461, 501, 512, 514, 518, 527–528
   ContextReplacementPlugin.js100%100%100%100%
   DefinePlugin.js99.08%100%100%99.08%1080, 176–177, 193, 212, 286
   DependenciesBlock.js100%100%100%100%
   Dependency.js98.51%100%100%98.51%480, 527
   DependencyTemplate.js100%100%100%100%
   DependencyTemplates.js100%100%100%100%
   DotenvPlugin.js98.41%100%100%98.41%378, 391–392
   DynamicEntryPlugin.js100%100%100%100%
   EntryOptionPlugin.js100%100%100%100%
   EntryPlugin.js100%100%100%100%
   Entrypoint.js100%100%100%100%
   EnvironmentPlugin.js97.14%100%100%97.14%49
   ErrorHelpers.js100%100%100%100%
   EvalDevToolModulePlugin.js100%100%100%100%
   EvalSourceMapDevToolPlugin.js100%100%100%100%
   ExportsInfo.js100%100%100%100%
   ExportsInfoApiPlugin.js100%100%100%100%
   ExternalModule.js98.67%100%100%98.67%1216, 1219, 515–519, 521, 667
   ExternalModuleFactoryPlugin.js100%100%100%100%
   ExternalsPlugin.js100%100%100%100%
   FileSystemInfo.js99.16%100%100%99.16%1267, 1269–1274, 1281, 1284, 182, 2502–2503, 2506, 2517, 2528, 2539, 280, 3976, 3991, 4015
   FlagAllModulesAsUsedPlugin.js100%100%100%100%
   FlagDependencyExportsPlugin.js98.21%100%100%98.21%448, 457, 460, 464, 476
   FlagDependencyUsagePlugin.js100%100%100%100%
   FlagEntryExportAsUsedPlugin.js100%100%100%100%
   Generator.js100%100%100%100%
   HotModuleReplacementPlugin.js100%100%100%100%
   HotUpdateChunk.js100%100%100%100%
   IgnorePlugin.js100%100%100%100%
   IgnoreWarningsPlugin.js100%100%100%100%
   InitFragment.js100%100%100%100%
   JavascriptMetaInfoPlugin.js100%100%100%100%
   LazyBarrel.js100%100%100%100%
   LibraryTemplatePlugin.js100%100%100%100%
   LoaderOptionsPlugin.js100%100%100%100%
   LoaderTargetPlugin.js100%100%100%100%
   MainTemplate.js100%100%100%100%
   ManifestPlugin.js100%100%100%100%
   Module.js98.51%100%100%98.51%1303, 1308, 1368, 1382, 1444, 1453
   ModuleFactory.js100%100%100%100%
   ModuleFilenameHelpers.js98.90%100%100%98.90%111, 113
   ModuleGraph.js99.78%100%100%99.78%1170
   ModuleGraphConnection.js100%100%100%100%
   ModuleInfoHeaderPlugin.js100%100%100%100%
   ModuleNotFoundError.js100%100%100%100%
   ModuleProfile.js100%100%100%100%
   ModuleSourceTypeConstants.js100%100%100%100%
   ModuleTemplate.js100%100%100%100%
   ModuleTypeConstants.js100%100%100%100%
   MultiCompiler.js99.71%100%100%99.71%692
   MultiStats.js100%100%100%100%
   MultiWatching.js100%100%100%100%
   NoEmitOnErrorsPlugin.js100%100%100%100%
   NodeStuffPlugin.js100%100%100%100%
   NormalModule.js97.98%100%100%97.98%1020, 1023, 1040, 1057, 1305, 1339, 1355, 1803, 2100, 2105–2115, 34
   NormalModuleFactory.js98.72%100%100%98.72%1123, 1391, 1402, 1412, 1463–1465, 1472, 526, 538
   NormalModuleReplacementPlugin.js100%100%100%100%
   NullFactory.js100%100%100%100%
   OptimizationStages.js100%100%100%100%
   OptionsApply.js100%100%100%100%
   Parser.js100%100%100%100%
   PlatformPlugin.js100%100%100%100%
   PrefetchPlugin.js100%100%100%100%
   ProgressPlugin.js99.80%100%100%99.80%691
   ProvidePlugin.js100%100%100%100%
   RawModule.js100%100%100%100%
   RecordIdsPlugin.js100%100%100%100%
   RequestShortener.js100%100%100%100%
   ResolverFactory.js100%100%100%100%
   RuntimeGlobals.js100%100%100%100%
   RuntimeModule.js100%100%100%100%
   RuntimePlugin.js100%100%100%100%
   RuntimeTemplate.js100%100%100%100%
   SelfModuleFactory.js100%100%100%100%
   SingleEntryPlugin.js100%100%100%100%
   SourceMapDevToolModuleOptionsPlugin.js100%100%100%100%
   SourceMapDevToolPlugin.js98.63%100%100%98.63%220, 224, 226, 420, 431, 890
   Stats.js100%100%100%100%
   Template.js100%100%100%100%
   TemplatedPathPlugin.js99.47%100%100%99.47%352–353
   UseStrictPlugin.js100%100%100%100%
   WarnCaseSensitiveModulesPlugin.js100%100%100%100%
   WarnDeprecatedOptionPlugin.js100%100%100%100%
   WarnNoModeSetPlugin.js100%100%100%100%
   WatchIgnorePlugin.js100%100%100%100%
   Watching.js100%100%100%100%
   WebpackError.js100%100%100%100%
   WebpackIsIncludedPlugin.js100%100%100%100%
   WebpackOptionsApply.js100%100%100%100%
   WebpackOptionsDefaulter.js100%100%100%100%
   buildChunkGraph.js99.87%100%100%99.87%371
   cli.js98.63%100%100%98.63%10, 119, 549, 581, 631, 905
   index.js99.73%100%100%99.73%184
   validateSchema.js94.67%100%100%94.67%100, 87, 89, 98
   webpack.js97.10%100%100%97.10%10, 263, 285, 287
lib/asset
   AssetBytesGenerator.js100%100%100%100%
   AssetBytesParser.js100%100%100%100%
   AssetGenerator.js100%100%100%100%
   AssetModule.js100%100%100%100%
   AssetModulesPlugin.js97.95%100%100%97.95%295, 319, 322, 42, 452, 47
   AssetParser.js100%100%100%100%
   AssetSourceGenerator.js100%100%100%100%
   AssetSourceParser.js100%100%100%100%
   RawDataUrlModule.js100%100%100%100%
   WebManifestGenerator.js100%100%100%100%
   WebManifestParser.js100%100%100%100%
lib/async-modules
   AsyncModuleHelpers.js100%100%100%100%
   AwaitDependenciesInitFragment.js100%100%100%100%
   InferAsyncModulesPlugin.js100%100%100%100%
   isGeneratorLowered.js100%100%100%100%
lib/bun
   BunTargetPlugin.js100%100%100%100%
lib/cache
   AddBuildDependenciesPlugin.js100%100%100%100%
   AddManagedPathsPlugin.js100%100%100%100%
   IdleFileCachePlugin.js97.92%100%100%97.92%75, 87, 95
   MemoryCachePlugin.js92%100%100%92%34, 43
   MemoryWithGcCachePlugin.js93.42%100%100%93.42%108, 122–123, 132, 90
   PackFileCacheStrategy.js96.52%100%100%96.52%1310, 1410, 1414, 1476, 1712, 1796, 1819, 1851, 675, 694, 704–706, 708, 724–725, 730, 733, 735, 740, 745, 770, 776, 810, 816, 822, 827, 838, 847, 852–853, 855, 872, 878–879, 881
   ResolverCachePlugin.js100%100%100%100%
   

@github-actions

github-actions Bot commented Aug 7, 2026

Copy link
Copy Markdown
Contributor

Generated code size

Comparing 1dedc3b against 57177cc. Merging this PR will change the code webpack generates.

Changed New Deleted Unchanged Raw change
Cases 4 0 0 1500 🔴 ↑ +4.88 KiB
Assets 8 0 0 5893 🔴 ↑ +4.88 KiB
Runtimes 0 0 0 1858
8 asset(s) changed size
Asset Before After Change Gzip (9) Brotli (11) Zstd (19)
🔴 ↑ css/custom-media-selectors bundle0.css.map 2.32 KiB 4.00 KiB +1.68 KiB (+72.72%) +44.93% +47.58% +43.44%
🔴 ↑ css/custom-media-selectors bundle0.js 5.89 KiB 7.01 KiB +1.12 KiB (+18.99%) +14.44% +15.67% +14.27%
🔴 ↑ css/custom-media-selectors bundle0.css 1.43 KiB 2.32 KiB +910 B (+62.29%) +40.64% +32.66% +39.23%
🔴 ↑ css/custom-media-warnings bundle0.css.map 1.65 KiB 2.32 KiB +680 B (+40.17%) +23.05% +24.18% +22.79%
🔴 ↑ css/custom-media-warnings bundle0.css 903 B 1.19 KiB +318 B (+35.22%) +21.17% +19.59% +20.79%
🔴 ↑ css/custom-media-warnings bundle0.js 2.67 KiB 2.88 KiB +214 B (+7.82%) +5.63% +5.44% +5.41%
🔴 ↑ externals/externals-array 0/bundle0.js 414 B 414 B 0 B (—) +0.34%
🔴 ↑ externals/node-require bundle0.js 502 B 502 B 0 B (—) +0.30%

No runtime gained or lost a runtime module.

Built test/configCases with the defaults a user gets: 1504 case(s), 5901 asset(s), 35 emitted nothing.

@alexander-akait
alexander-akait merged commit 21af4f5 into main Aug 7, 2026
62 of 63 checks passed
@alexander-akait
alexander-akait deleted the fix/css-printer-equivalence-defects branch August 7, 2026 13:56
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant

Sponsor
SponsoredKunjungi sekarang
Promo