Skip to content

Commit c0e8cf4

Browse files
authored
fix: prevent !important from being renamed in CSS modules (#20798)
* test: add test case reproducing !important rename bug in CSS modules Adds animation/color declarations with !important to css-modules test to reproduce the issue where !important gets treated as a local identifier and renamed (e.g. !my-app-style_module_css-important). Ref: #20794 * fix: prevent !important from being renamed in CSS modules Add a delim callback to track exclamation marks during CSS declaration value parsing, so the subsequent "important" identifier is skipped instead of being collected as a renameable local identifier. Fixes #20794 * chore: add changeset for !important CSS modules fix
1 parent f8d274b commit c0e8cf4

7 files changed

Lines changed: 97 additions & 0 deletions

File tree

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
"webpack": patch
3+
---
4+
5+
Prevent `!important` from being renamed as a local identifier in CSS modules.

lib/css/CssParser.js

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@ const CC_HYPHEN_MINUS = "-".charCodeAt(0);
5151
const CC_TILDE = "~".charCodeAt(0);
5252
const CC_EQUAL = "=".charCodeAt(0);
5353
const CC_FULL_STOP = ".".charCodeAt(0);
54+
const CC_EXCLAMATION = "!".charCodeAt(0);
5455

5556
// https://www.w3.org/TR/css-syntax-3/#newline
5657
// We don't have `preprocessing` stage, so we need specify all of them
@@ -1772,10 +1773,16 @@ class CssParser extends Parser {
17721773
)
17731774
: false;
17741775

1776+
let afterExclamation = false;
1777+
17751778
const end = walkCssTokens.consumeUntil(
17761779
input,
17771780
pos,
17781781
{
1782+
delim(input, start, end) {
1783+
afterExclamation = input.charCodeAt(start) === CC_EXCLAMATION;
1784+
return end;
1785+
},
17791786
leftSquareBracket(input, start, end) {
17801787
let i = end;
17811788

@@ -1824,6 +1831,11 @@ class CssParser extends Parser {
18241831
return end;
18251832
}
18261833

1834+
if (afterExclamation) {
1835+
afterExclamation = false;
1836+
return end;
1837+
}
1838+
18271839
const identifier = input.slice(start, end);
18281840
const keyword = identifier.toLowerCase();
18291841

test/configCases/css/css-modules/__snapshots__/ConfigCacheTest.snap

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2736,6 +2736,12 @@ p:not(#my-app-style_module_css-main-paragraph) {
27362736
grid-template-columns: [my-app-style_module_css-col-start-col-start] 1fr [my-app-style_module_css-col-end-col-end my-app-style_module_css-col-start-col-start] 1fr [my-app-style_module_css-col-end-col-end my-app-style_module_css-col-start-col-start] 1fr [my-app-style_module_css-col-end-col-end my-app-style_module_css-col-start-col-start] 1fr [my-app-style_module_css-col-end-col-end];
27372737
}
27382738
2739+
.my-app-style_module_css-importantAnimation {
2740+
animation: none !important;
2741+
animation-name: none !important;
2742+
color: red !important;
2743+
}
2744+
27392745
/*!*********************************!*\\\\
27402746
!*** css ./style.module.my-css ***!
27412747
\\\\*********************************/
@@ -5511,6 +5517,12 @@ p:not(#my-app-style_module_css-main-paragraph) {
55115517
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
55125518
}
55135519
5520+
.importantAnimation {
5521+
animation: none !important;
5522+
animation-name: none !important;
5523+
color: red !important;
5524+
}
5525+
55145526
55155527
/*# sourceMappingURL=use-style-global_js.bundle4.css.map*/"
55165528
`;
@@ -8200,6 +8212,12 @@ p:not(#dBVRDQ) {
82008212
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
82018213
}
82028214
8215+
.importantAnimation {
8216+
animation: none !important;
8217+
animation-name: none !important;
8218+
color: red !important;
8219+
}
8220+
82038221
"
82048222
`;
82058223
@@ -10939,6 +10957,12 @@ p:not(#dBVRDQ) {
1093910957
grid-template-columns: [_1Yrglr-col-start] 1fr [UIbRwt-col-end _1Yrglr-col-start] 1fr [UIbRwt-col-end _1Yrglr-col-start] 1fr [UIbRwt-col-end _1Yrglr-col-start] 1fr [UIbRwt-col-end];
1094010958
}
1094110959
10960+
.fR4zhQ {
10961+
animation: none !important;
10962+
animation-name: none !important;
10963+
color: red !important;
10964+
}
10965+
1094210966
/*!*********************************!*\\\\
1094310967
!*** css ./style.module.my-css ***!
1094410968
\\\\*********************************/
@@ -11147,6 +11171,7 @@ Object {
1114711171
"id-bar": "my-app-style_module_css-id-bar",
1114811172
"id-foo": "my-app-style_module_css-id-foo",
1114911173
"ident": "my-app-style_module_css-ident",
11174+
"importantAnimation": "my-app-style_module_css-importantAnimation",
1115011175
"in-local-global-scope": "my-app-style_module_css-in-local-global-scope",
1115111176
"inSupportScope": "my-app-style_module_css-inSupportScope",
1115211177
"infobox": "my-app-style_module_css-infobox",
@@ -13916,6 +13941,12 @@ p:not(#my-app-style_module_css-main-paragraph) {
1391613941
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
1391713942
}
1391813943
13944+
.my-app-style_module_css-importantAnimation {
13945+
animation: none !important;
13946+
animation-name: none !important;
13947+
color: red !important;
13948+
}
13949+
1391913950
1392013951
/*# sourceMappingURL=bundle6.css.map*/"
1392113952
`;

test/configCases/css/css-modules/__snapshots__/ConfigTest.snap

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2736,6 +2736,12 @@ p:not(#my-app-style_module_css-main-paragraph) {
27362736
grid-template-columns: [my-app-style_module_css-col-start-col-start] 1fr [my-app-style_module_css-col-end-col-end my-app-style_module_css-col-start-col-start] 1fr [my-app-style_module_css-col-end-col-end my-app-style_module_css-col-start-col-start] 1fr [my-app-style_module_css-col-end-col-end my-app-style_module_css-col-start-col-start] 1fr [my-app-style_module_css-col-end-col-end];
27372737
}
27382738
2739+
.my-app-style_module_css-importantAnimation {
2740+
animation: none !important;
2741+
animation-name: none !important;
2742+
color: red !important;
2743+
}
2744+
27392745
/*!*********************************!*\\\\
27402746
!*** css ./style.module.my-css ***!
27412747
\\\\*********************************/
@@ -5511,6 +5517,12 @@ p:not(#my-app-style_module_css-main-paragraph) {
55115517
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
55125518
}
55135519
5520+
.importantAnimation {
5521+
animation: none !important;
5522+
animation-name: none !important;
5523+
color: red !important;
5524+
}
5525+
55145526
55155527
/*# sourceMappingURL=use-style-global_js.bundle4.css.map*/"
55165528
`;
@@ -8200,6 +8212,12 @@ p:not(#dBVRDQ) {
82008212
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
82018213
}
82028214
8215+
.importantAnimation {
8216+
animation: none !important;
8217+
animation-name: none !important;
8218+
color: red !important;
8219+
}
8220+
82038221
"
82048222
`;
82058223
@@ -10939,6 +10957,12 @@ p:not(#dBVRDQ) {
1093910957
grid-template-columns: [_1Yrglr-col-start] 1fr [UIbRwt-col-end _1Yrglr-col-start] 1fr [UIbRwt-col-end _1Yrglr-col-start] 1fr [UIbRwt-col-end _1Yrglr-col-start] 1fr [UIbRwt-col-end];
1094010958
}
1094110959
10960+
.fR4zhQ {
10961+
animation: none !important;
10962+
animation-name: none !important;
10963+
color: red !important;
10964+
}
10965+
1094210966
/*!*********************************!*\\\\
1094310967
!*** css ./style.module.my-css ***!
1094410968
\\\\*********************************/
@@ -11147,6 +11171,7 @@ Object {
1114711171
"id-bar": "my-app-style_module_css-id-bar",
1114811172
"id-foo": "my-app-style_module_css-id-foo",
1114911173
"ident": "my-app-style_module_css-ident",
11174+
"importantAnimation": "my-app-style_module_css-importantAnimation",
1115011175
"in-local-global-scope": "my-app-style_module_css-in-local-global-scope",
1115111176
"inSupportScope": "my-app-style_module_css-inSupportScope",
1115211177
"infobox": "my-app-style_module_css-infobox",
@@ -13916,6 +13941,12 @@ p:not(#my-app-style_module_css-main-paragraph) {
1391613941
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
1391713942
}
1391813943
13944+
.my-app-style_module_css-importantAnimation {
13945+
animation: none !important;
13946+
animation-name: none !important;
13947+
color: red !important;
13948+
}
13949+
1391913950
1392013951
/*# sourceMappingURL=bundle6.css.map*/"
1392113952
`;

test/configCases/css/css-modules/style.module.css

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2055,3 +2055,9 @@ p:not(:local(#main-paragraph)) {
20552055
.wrapper {
20562056
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
20572057
}
2058+
2059+
.importantAnimation {
2060+
animation: none !important;
2061+
animation-name: none !important;
2062+
color: red !important;
2063+
}

test/configCases/css/pure-css/__snapshots__/ConfigCacheTest.snap

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2626,6 +2626,12 @@ p:not(:local(#main-paragraph)) {
26262626
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
26272627
}
26282628
2629+
.importantAnimation {
2630+
animation: none !important;
2631+
animation-name: none !important;
2632+
color: red !important;
2633+
}
2634+
26292635
/*!***********************!*\\\\
26302636
!*** css ./style.css ***!
26312637
\\\\***********************/

test/configCases/css/pure-css/__snapshots__/ConfigTest.snap

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2626,6 +2626,12 @@ p:not(:local(#main-paragraph)) {
26262626
grid-template-columns: [col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end col-start] 1fr [col-end];
26272627
}
26282628
2629+
.importantAnimation {
2630+
animation: none !important;
2631+
animation-name: none !important;
2632+
color: red !important;
2633+
}
2634+
26292635
/*!***********************!*\\\\
26302636
!*** css ./style.css ***!
26312637
\\\\***********************/

0 commit comments

Comments
 (0)