From 76ff3a1888751a452c58cb94a14389424b620b73 Mon Sep 17 00:00:00 2001 From: Owen Buckley Date: Fri, 20 Sep 2024 18:57:50 -0400 Subject: [PATCH] feature/upgrade css tree 3.0.0 with formal CSS nesting handling (#1281) * upgrade to css-tree 3.0.0 * update comment * nesting selector CSS optimization support * cleanup --- packages/cli/package.json | 2 +- .../plugins/resource/plugin-standard-css.js | 26 ++++++++++++++++--- .../fixtures/expected.css | 6 ++++- .../src/styles/main.css | 13 ++++++++++ yarn.lock | 18 ++++++------- 5 files changed, 50 insertions(+), 15 deletions(-) diff --git a/packages/cli/package.json b/packages/cli/package.json index 8023745be..0722a8162 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -38,7 +38,7 @@ "acorn-import-attributes": "^1.9.5", "acorn-walk": "^8.0.0", "commander": "^2.20.0", - "css-tree": "^2.2.1", + "css-tree": "^3.0.0", "es-module-shims": "^1.8.3", "front-matter": "^4.0.2", "koa": "^2.13.0", diff --git a/packages/cli/src/plugins/resource/plugin-standard-css.js b/packages/cli/src/plugins/resource/plugin-standard-css.js index d6985494d..c4c0ed9af 100644 --- a/packages/cli/src/plugins/resource/plugin-standard-css.js +++ b/packages/cli/src/plugins/resource/plugin-standard-css.js @@ -83,6 +83,8 @@ function bundleCss(body, url, compilation) { optimizedCss += `#${name}`; } else if (type === 'ClassSelector') { optimizedCss += `.${name}`; + } else if (type === 'NestingSelector') { + optimizedCss += '&'; } else if (type === 'PseudoClassSelector') { optimizedCss += `:${name}`; @@ -127,12 +129,25 @@ function bundleCss(body, url, compilation) { optimizedCss += ' '; } optimizedCss += `${name}(`; - } else if (type === 'MediaFeature') { + } else if (type === 'Feature') { optimizedCss += ` (${name}:`; - } else if (type === 'Parentheses') { + } else if (type === 'Parentheses' || type === 'SupportsDeclaration') { optimizedCss += '('; } else if (type === 'PseudoElementSelector') { optimizedCss += `::${name}`; + } else if (type === 'MediaQuery') { + // https://github.com/csstree/csstree/issues/285#issuecomment-2350230333 + const { mediaType, modifier } = node; + const type = mediaType !== null + ? mediaType + : ''; + const operator = mediaType && node.condition + ? ' and' + : modifier !== null + ? ` ${modifier}` + : ''; + + optimizedCss += `${type}${operator}`; } else if (type === 'Block') { optimizedCss += '{'; } else if (type === 'AttributeSelector') { @@ -209,8 +224,8 @@ function bundleCss(body, url, compilation) { optimizedCss += '}'; break; case 'Function': - case 'MediaFeature': case 'Parentheses': + case 'SupportsDeclaration': optimizedCss += ')'; break; case 'PseudoClassSelector': @@ -254,7 +269,7 @@ function bundleCss(body, url, compilation) { optimizedCss += '!important'; } - if (item.next || (item.prev && !item.next)) { + if (item?.next || (item?.prev && !item?.next)) { optimizedCss += ';'; } @@ -275,6 +290,9 @@ function bundleCss(body, url, compilation) { } optimizedCss += ']'; break; + case 'MediaQuery': + optimizedCss += ')'; + break; default: break; diff --git a/packages/cli/test/cases/build.config.optimization-default/fixtures/expected.css b/packages/cli/test/cases/build.config.optimization-default/fixtures/expected.css index bdaab6708..c311a63c3 100644 --- a/packages/cli/test/cases/build.config.optimization-default/fixtures/expected.css +++ b/packages/cli/test/cases/build.config.optimization-default/fixtures/expected.css @@ -78,4 +78,8 @@ h2 ::slotted(span){background:silver} tabbed-custom-element::part(tab){color:#0c0dcc;border-bottom:transparent solid 2px;} -::highlight(rainbow-color-1){color:#ad26ad;text-decoration:underline;} \ No newline at end of file +::highlight(rainbow-color-1){color:#ad26ad;text-decoration:underline;} + +h2{& span{color:red}} + +@media (max-width:768px){span{flex-direction:column;text-align:center;}} \ No newline at end of file diff --git a/packages/cli/test/cases/build.config.optimization-default/src/styles/main.css b/packages/cli/test/cases/build.config.optimization-default/src/styles/main.css index b31735600..a8fb5f935 100644 --- a/packages/cli/test/cases/build.config.optimization-default/src/styles/main.css +++ b/packages/cli/test/cases/build.config.optimization-default/src/styles/main.css @@ -173,4 +173,17 @@ tabbed-custom-element::part(tab) { ::highlight(rainbow-color-1) { color: #ad26ad; text-decoration: underline; +} + +h2 { + & span { + color: red; + } +} + +@media (max-width: 768px) { + span { + flex-direction: column; + text-align: center; + } } \ No newline at end of file diff --git a/yarn.lock b/yarn.lock index 7c24c2799..a2132db13 100644 --- a/yarn.lock +++ b/yarn.lock @@ -6936,12 +6936,12 @@ css-prefers-color-scheme@^5.0.0: resolved "https://registry.yarnpkg.com/css-prefers-color-scheme/-/css-prefers-color-scheme-5.0.0.tgz#a89bc1abfe946e77a1a1e12dbc25a1439705933f" integrity sha512-XpzVrdwbppHm+Nnrzcb/hQb8eq1aKv4U8Oh59LsLfTsbIZZ6Fvn9razb66ihH2aTJ0VhO9n9sVm8piyKXJAZMA== -css-tree@^2.2.1: - version "2.2.1" - resolved "https://registry.yarnpkg.com/css-tree/-/css-tree-2.2.1.tgz#36115d382d60afd271e377f9c5f67d02bd48c032" - integrity sha512-OA0mILzGc1kCOCSJerOeqDxDQ4HOh+G8NbOJFOTgOCzpw7fCBubk0fEyxp8AgOL/jvLgYA/uV0cMbe43ElF1JA== +css-tree@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/css-tree/-/css-tree-3.0.0.tgz#079c7b87e465a28cedbc826502f9a227213db0f3" + integrity sha512-o88DVQ6GzsABn1+6+zo2ct801dBO5OASVyxbbvA2W20ue2puSh/VOuqUj90eUeMSX/xqGqBmOKiRQN7tJOuBXw== dependencies: - mdn-data "2.0.28" + mdn-data "2.10.0" source-map-js "^1.0.1" cssdb@^5.0.0: @@ -11683,10 +11683,10 @@ mdast-util-to-string@^2.0.0: resolved "https://registry.yarnpkg.com/mdast-util-to-string/-/mdast-util-to-string-2.0.0.tgz#b8cfe6a713e1091cb5b728fc48885a4767f8b97b" integrity sha512-AW4DRS3QbBayY/jJmD8437V1Gombjf8RSOUCMFBuo5iHi58AGEgVCKQ+ezHkZZDpAQS75hcBMpLqjpJTjtUL7w== -mdn-data@2.0.28: - version "2.0.28" - resolved "https://registry.yarnpkg.com/mdn-data/-/mdn-data-2.0.28.tgz#5ec48e7bef120654539069e1ae4ddc81ca490eba" - integrity sha512-aylIc7Z9y4yzHYAJNuESG3hfhC+0Ibp/MAMiaOZgNv4pmEdFyfZhhhny4MNiAfWdBQ1RQ2mfDWmM1x8SvGyp8g== +mdn-data@2.10.0: + version "2.10.0" + resolved "https://registry.yarnpkg.com/mdn-data/-/mdn-data-2.10.0.tgz#701da407f8fbc7a42aa0ba0c149ec897daef8986" + integrity sha512-qq7C3EtK3yJXMwz1zAab65pjl+UhohqMOctTgcqjLOWABqmwj+me02LSsCuEUxnst9X1lCBpoE0WArGKgdGDzw== mdurl@^1.0.0: version "1.0.1"