33// https://opensource.org/licenses/MIT.
44
55import 'package:charcode/charcode.dart' ;
6+ import 'package:meta/meta.dart' ;
67import 'package:source_span/source_span.dart' ;
78import 'package:string_scanner/string_scanner.dart' ;
89
@@ -24,20 +25,23 @@ abstract class Parser {
2425 // ## Tokens
2526
2627 /// Consumes whitespace, including any comments.
28+ @protected
2729 void whitespace () {
2830 do {
2931 whitespaceWithoutComments ();
3032 } while (scanComment ());
3133 }
3234
3335 /// Like [whitespace] , but returns whether any was consumed.
36+ @protected
3437 bool scanWhitespace () {
3538 var start = scanner.position;
3639 whitespace ();
3740 return scanner.position != start;
3841 }
3942
4043 /// Consumes whitespace, but not comments.
44+ @protected
4145 void whitespaceWithoutComments () {
4246 while (! scanner.isDone && isWhitespace (scanner.peekChar ())) {
4347 scanner.readChar ();
@@ -47,6 +51,7 @@ abstract class Parser {
4751 /// Consumes and ignores a comment if possible.
4852 ///
4953 /// Returns whether the comment was consumed.
54+ @protected
5055 bool scanComment () {
5156 if (scanner.peekChar () != $slash) return false ;
5257
@@ -63,6 +68,7 @@ abstract class Parser {
6368 }
6469
6570 /// Consumes and ignores a silent (Sass-style) comment.
71+ @protected
6672 void silentComment () {
6773 scanner.expect ("//" );
6874 while (! scanner.isDone && ! isNewline (scanner.peekChar ())) {
@@ -71,6 +77,7 @@ abstract class Parser {
7177 }
7278
7379 /// Consumes and ignores a loud (CSS-style) comment.
80+ @protected
7481 void loudComment () {
7582 scanner.expect ("/*" );
7683 while (true ) {
@@ -89,6 +96,7 @@ abstract class Parser {
8996 /// If [unit] is `true` , this doesn't parse a `-` followed by a digit. This
9097 /// ensures that `1px-2px` parses as subtraction rather than the unit
9198 /// `px-2px` .
99+ @protected
92100 String identifier ({bool unit: false }) {
93101 // NOTE: this logic is largely duplicated in ScssParser.identifier.
94102 // Most changes here should be mirrored there.
@@ -114,6 +122,7 @@ abstract class Parser {
114122 }
115123
116124 /// Consumes a chunk of a plain CSS identifier after the name start.
125+ @protected
117126 String identifierBody () {
118127 var text = new StringBuffer ();
119128 _identifierBody (text);
@@ -146,6 +155,7 @@ abstract class Parser {
146155 ///
147156 /// This returns the parsed contents of the string—that is, it doesn't include
148157 /// quotes and its escapes are resolved.
158+ @protected
149159 String string () {
150160 // NOTE: this logic is largely duplicated in ScssParser._interpolatedString.
151161 // Most changes here should be mirrored there.
@@ -181,6 +191,7 @@ abstract class Parser {
181191
182192 /// Consumes tokens until it reaches a top-level `":"` , `"!"` , `")"` , `"]"` ,
183193 /// or `"}"` and returns their contents as a string.
194+ @protected
184195 String declarationValue () {
185196 // NOTE: this logic is largely duplicated in
186197 // StylesheetParser._interpolatedDeclarationValue. Most changes here should
@@ -281,6 +292,7 @@ abstract class Parser {
281292 }
282293
283294 /// Consumes a `url()` token if possible, and returns `null` otherwise.
295+ @protected
284296 String tryUrl () {
285297 // NOTE: this logic is largely duplicated in ScssParser._urlContents and
286298 // ScssParser._tryUrlContents. Most changes here should be mirrored there.
@@ -327,6 +339,7 @@ abstract class Parser {
327339
328340 /// Consumes a Sass variable name, and returns its name without the dollar
329341 /// sign.
342+ @protected
330343 String variableName () {
331344 scanner.expectChar ($dollar);
332345 return identifier ();
@@ -335,6 +348,7 @@ abstract class Parser {
335348 // ## Characters
336349
337350 /// Consumes an escape sequence and returns the text that defines it.
351+ @protected
338352 String escape () {
339353 // See https://drafts.csswg.org/css-syntax-3/#consume-escaped-code-point.
340354
@@ -365,6 +379,7 @@ abstract class Parser {
365379 }
366380
367381 /// Consumes an escape sequence and returns the character it represents.
382+ @protected
368383 int escapeCharacter () {
369384 // See https://drafts.csswg.org/css-syntax-3/#consume-escaped-code-point.
370385
@@ -399,6 +414,7 @@ abstract class Parser {
399414 // Consumes the next character if it matches [condition].
400415 //
401416 // Returns whether or not the character was consumed.
417+ @protected
402418 bool scanCharIf (bool condition (int character)) {
403419 var next = scanner.peekChar ();
404420 if (! condition (next)) return false ;
@@ -408,6 +424,7 @@ abstract class Parser {
408424
409425 /// Consumes the next character if it's equal to [letter] , ignoring ASCII
410426 /// case.
427+ @protected
411428 bool scanCharIgnoreCase (int letter) {
412429 if (! equalsLetterIgnoreCase (letter, scanner.peekChar ())) return false ;
413430 scanner.readChar ();
@@ -416,6 +433,7 @@ abstract class Parser {
416433
417434 /// Consumes the next character and asserts that it's equal to [letter] ,
418435 /// ignoring ASCII case.
436+ @protected
419437 void expectCharIgnoreCase (int letter) {
420438 var actual = scanner.readChar ();
421439 if (equalsLetterIgnoreCase (letter, actual)) return ;
@@ -431,6 +449,7 @@ abstract class Parser {
431449 /// This follows [the CSS algorithm][] .
432450 ///
433451 /// [the CSS algorithm] : https://drafts.csswg.org/css-syntax-3/#starts-with-a-number
452+ @protected
434453 bool lookingAtNumber () {
435454 var first = scanner.peekChar ();
436455 if (first == null ) return false ;
@@ -460,6 +479,7 @@ abstract class Parser {
460479 /// start escapes.
461480 ///
462481 /// [the CSS algorithm] : https://drafts.csswg.org/css-syntax-3/#would-start-an-identifier
482+ @protected
463483 bool lookingAtIdentifier ([int forward]) {
464484 // See also [ScssParser._lookingAtInterpolatedIdentifier].
465485
@@ -480,6 +500,7 @@ abstract class Parser {
480500
481501 /// Returns whether the scanner is immediately before a sequence of characters
482502 /// that could be part of a plain CSS identifier body.
503+ @protected
483504 bool lookingAtIdentifierBody () {
484505 var next = scanner.peekChar ();
485506 return next != null && (isName (next) || next == $backslash);
@@ -488,6 +509,7 @@ abstract class Parser {
488509 /// Consumes an identifier if its name exactly matches [text] .
489510 ///
490511 /// If [ignoreCase] is `true` , does a case-insensitive match.
512+ @protected
491513 bool scanIdentifier (String text, {bool ignoreCase: false }) {
492514 if (! lookingAtIdentifier ()) return false ;
493515
@@ -507,6 +529,7 @@ abstract class Parser {
507529 /// Consumes an identifier and asserts that its name exactly matches [text] .
508530 ///
509531 /// If [ignoreCase] is `true` , does a case-insensitive match.
532+ @protected
510533 void expectIdentifier (String text, {String name, bool ignoreCase: false }) {
511534 name ?? = '"$text "' ;
512535
@@ -522,6 +545,7 @@ abstract class Parser {
522545 }
523546
524547 /// Runs [consumer] and returns the source text that it consumes.
548+ @protected
525549 String rawText (void consumer ()) {
526550 var start = scanner.position;
527551 consumer ();
@@ -532,6 +556,7 @@ abstract class Parser {
532556 ///
533557 /// If [message] is passed, prints that as well. This is intended for use when
534558 /// debugging parser failures.
559+ @protected
535560 void debug ([message]) {
536561 if (message == null ) {
537562 print (scanner.emptySpan.highlight (color: true ));
@@ -542,6 +567,7 @@ abstract class Parser {
542567
543568 /// Runs [callback] and wraps any [SourceSpanFormatException] it throws in a
544569 /// [SassFormatException] .
570+ @protected
545571 T wrapSpanFormatException <T >(T callback ()) {
546572 try {
547573 return callback ();
0 commit comments