Skip to content

Commit 949df80

Browse files
fix(compiler-sfc): add scoping tag to trailing universal selector (#12918)
close #12906
1 parent a683c80 commit 949df80

File tree

2 files changed

+47
-4
lines changed

2 files changed

+47
-4
lines changed

packages/compiler-sfc/__tests__/compileStyle.spec.ts

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -493,7 +493,31 @@ describe('SFC style preprocessors', () => {
493493
}"
494494
`)
495495
expect(compileScoped(`.foo * { color: red; }`)).toMatchInlineSnapshot(`
496-
".foo[data-v-test] * { color: red;
496+
".foo[data-v-test] [data-v-test] { color: red;
497+
}"
498+
`)
499+
expect(compileScoped(`.foo :active { color: red; }`))
500+
.toMatchInlineSnapshot(`
501+
".foo[data-v-test] :active { color: red;
502+
}"
503+
`)
504+
expect(compileScoped(`.foo *:active { color: red; }`))
505+
.toMatchInlineSnapshot(`
506+
".foo[data-v-test] [data-v-test]:active { color: red;
507+
}"
508+
`)
509+
expect(compileScoped(`.foo * .bar { color: red; }`)).toMatchInlineSnapshot(`
510+
".foo * .bar[data-v-test] { color: red;
511+
}"
512+
`)
513+
expect(compileScoped(`:last-child * { color: red; }`))
514+
.toMatchInlineSnapshot(`
515+
"[data-v-test]:last-child [data-v-test] { color: red;
516+
}"
517+
`)
518+
expect(compileScoped(`:last-child *:active { color: red; }`))
519+
.toMatchInlineSnapshot(`
520+
"[data-v-test]:last-child [data-v-test]:active { color: red;
497521
}"
498522
`)
499523
})

packages/compiler-sfc/src/style/pluginScoped.ts

Lines changed: 22 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,7 @@ function rewriteSelector(
102102
slotted = false,
103103
) {
104104
let node: selectorParser.Node | null = null
105+
let starNode: selectorParser.Node | null = null
105106
let shouldInject = !deep
106107
// find the last child node to insert attribute selector
107108
selector.each(n => {
@@ -216,17 +217,21 @@ function rewriteSelector(
216217
return false
217218
}
218219
}
219-
// .foo * -> .foo[xxxxxxx] *
220-
if (node) return
220+
// store the universal selector so it can be rewritten later
221+
// .foo * -> .foo[xxxxxxx] [xxxxxxx]
222+
starNode = n
221223
}
222224

223225
if (
224-
(n.type !== 'pseudo' && n.type !== 'combinator') ||
226+
(n.type !== 'pseudo' &&
227+
n.type !== 'combinator' &&
228+
n.type !== 'universal') ||
225229
(n.type === 'pseudo' &&
226230
(n.value === ':is' || n.value === ':where') &&
227231
!node)
228232
) {
229233
node = n
234+
starNode = null
230235
}
231236
})
232237

@@ -274,6 +279,20 @@ function rewriteSelector(
274279
quoteMark: `"`,
275280
}),
276281
)
282+
// Used for trailing universal selectors (#12906)
283+
// `.foo * {}` -> `.foo[xxxxxxx] [xxxxxxx] {}`
284+
if (starNode) {
285+
selector.insertBefore(
286+
starNode,
287+
selectorParser.attribute({
288+
attribute: idToAdd,
289+
value: idToAdd,
290+
raws: {},
291+
quoteMark: `"`,
292+
}),
293+
)
294+
selector.removeChild(starNode)
295+
}
277296
}
278297
}
279298

0 commit comments

Comments
 (0)