From 6e2d637ac3a0ef99c194c4ba393ed24f40a6cf09 Mon Sep 17 00:00:00 2001 From: Natalie Weizenbaum Date: Tue, 12 Mar 2024 14:16:10 -0700 Subject: [PATCH] Allow adjacent forward slashes in plain CSS expressions (#2190) See sass/sass#3797 --- CHANGELOG.md | 3 +++ lib/src/parse/css.dart | 4 +++- lib/src/parse/parser.dart | 8 +++++--- lib/src/parse/stylesheet.dart | 10 ++++++++++ 4 files changed, 21 insertions(+), 4 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 1eb735f4f..790613be0 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,8 @@ ## 1.72.0 +* Support adjacent `/`s without whitespace in between when parsing plain CSS + expressions. + * Allow the Node.js `pkg:` importer to load Sass stylesheets for `package.json` `exports` field entries without extensions. diff --git a/lib/src/parse/css.dart b/lib/src/parse/css.dart index 754a3614a..747d22c49 100644 --- a/lib/src/parse/css.dart +++ b/lib/src/parse/css.dart @@ -32,7 +32,9 @@ class CssParser extends ScssParser { CssParser(super.contents, {super.url, super.logger}); - void silentComment() { + bool silentComment() { + if (inExpression) return false; + var start = scanner.state; super.silentComment(); error("Silent comments aren't allowed in plain CSS.", diff --git a/lib/src/parse/parser.dart b/lib/src/parse/parser.dart index 6dd17c80d..a16b871e7 100644 --- a/lib/src/parse/parser.dart +++ b/lib/src/parse/parser.dart @@ -114,8 +114,7 @@ class Parser { switch (scanner.peekChar(1)) { case $slash: - silentComment(); - return true; + return silentComment(); case $asterisk: loudComment(); return true; @@ -135,12 +134,15 @@ class Parser { } /// Consumes and ignores a silent (Sass-style) comment. + /// + /// Returns whether the comment was consumed. @protected - void silentComment() { + bool silentComment() { scanner.expect("//"); while (!scanner.isDone && !scanner.peekChar().isNewline) { scanner.readChar(); } + return true; } /// Consumes and ignores a loud (CSS-style) comment. diff --git a/lib/src/parse/stylesheet.dart b/lib/src/parse/stylesheet.dart index 15c568f66..d0c620f24 100644 --- a/lib/src/parse/stylesheet.dart +++ b/lib/src/parse/stylesheet.dart @@ -56,6 +56,11 @@ abstract class StylesheetParser extends Parser { /// Whether the parser is currently within a parenthesized expression. var _inParentheses = false; + /// Whether the parser is currently within an expression. + @protected + bool get inExpression => _inExpression; + var _inExpression = false; + /// A map from all variable names that are assigned with `!global` in the /// current stylesheet to the nodes where they're defined. /// @@ -1686,7 +1691,9 @@ abstract class StylesheetParser extends Parser { } var start = scanner.state; + var wasInExpression = _inExpression; var wasInParentheses = _inParentheses; + _inExpression = true; // We use the convention below of referring to nullable variables that are // shared across anonymous functions in this method with a trailing @@ -2039,11 +2046,13 @@ abstract class StylesheetParser extends Parser { _inParentheses = wasInParentheses; var singleExpression = singleExpression_; if (singleExpression != null) commaExpressions.add(singleExpression); + _inExpression = wasInExpression; return ListExpression(commaExpressions, ListSeparator.comma, scanner.spanFrom(beforeBracket ?? start), brackets: bracketList); } else if (bracketList && spaceExpressions != null) { resolveOperations(); + _inExpression = wasInExpression; return ListExpression(spaceExpressions..add(singleExpression_!), ListSeparator.space, scanner.spanFrom(beforeBracket!), brackets: true); @@ -2054,6 +2063,7 @@ abstract class StylesheetParser extends Parser { ListSeparator.undecided, scanner.spanFrom(beforeBracket!), brackets: true); } + _inExpression = wasInExpression; return singleExpression_!; } }