mirror of
https://github.com/danog/dart-sass.git
synced 2025-01-22 05:41:14 +01:00
Check extend usage after the fact.
This means that extensions that match but fail to unify are valid, but we think that's okay; see sass/sass#2250.
This commit is contained in:
parent
9ded7e9e68
commit
9cfbf79f47
@ -180,6 +180,9 @@ Sass to update the reference behavior.
|
||||
|
||||
14. Universal selector unification is symmetrical. See [issue 2247][].
|
||||
|
||||
15. `@extend` doesn't produce an error if it matches but fails to unify. See
|
||||
[issue 2250][].
|
||||
|
||||
[issue 1599]: https://github.com/sass/sass/issues/1599
|
||||
[issue 1126]: https://github.com/sass/sass/issues/1126
|
||||
[issue 2120]: https://github.com/sass/sass/issues/2120
|
||||
@ -194,5 +197,6 @@ Sass to update the reference behavior.
|
||||
[issue 2245]: https://github.com/sass/sass/issues/2245
|
||||
[issue 303]: https://github.com/sass/sass/issues/303
|
||||
[issue 2247]: https://github.com/sass/sass/issues/2247
|
||||
[issue 2250]: https://github.com/sass/sass/issues/2250
|
||||
|
||||
Disclaimer: this is not an official Google product.
|
||||
|
@ -173,14 +173,12 @@ class Extender {
|
||||
if (rules == null) return;
|
||||
if (newExtenders == null) return;
|
||||
for (var rule in rules) {
|
||||
try {
|
||||
var extended = _extendList(
|
||||
rule.selector.value, {target: newExtenders}, _mediaContexts[rule]);
|
||||
|
||||
// A selector can't extend its own rule. We still have to run the extend
|
||||
// to set [state.isUsed] appropriately, though.
|
||||
// A selector can't extend its own rule.
|
||||
if (identical(rule.selector.value, extender)) continue;
|
||||
rule.selector.value = extended;
|
||||
|
||||
try {
|
||||
rule.selector.value = _extendList(
|
||||
rule.selector.value, {target: newExtenders}, _mediaContexts[rule]);
|
||||
} on SassException catch (error) {
|
||||
throw new SassException(
|
||||
"From ${rule.selector.span.message('')}\n"
|
||||
@ -195,13 +193,15 @@ class Extender {
|
||||
/// Throws a [SassException] if any (non-optional) extensions failed to match
|
||||
/// any selectors.
|
||||
void finalize() {
|
||||
_extensions.forEach((target, sources) {
|
||||
sources.forEach((_, state) {
|
||||
if (state.isOptional || state.isUsed) return;
|
||||
_extensions.forEach((target, extensions) {
|
||||
if (_selectors.containsKey(target)) return;
|
||||
|
||||
extensions.forEach((_, extension) {
|
||||
if (extension.isOptional) return;
|
||||
throw new SassException(
|
||||
'The target selector was not found.\n'
|
||||
'Use "@extend $target !optional" to avoid this error.',
|
||||
state.span);
|
||||
extension.span);
|
||||
});
|
||||
});
|
||||
}
|
||||
@ -343,7 +343,6 @@ class Extender {
|
||||
// need any unification.
|
||||
if (options.length == 1) {
|
||||
return options.first.map((state) {
|
||||
state.isUsed = true;
|
||||
state.assertCompatibleMediaContext(mediaQueryContext);
|
||||
return state.extender;
|
||||
}).toList();
|
||||
@ -416,7 +415,6 @@ class Extender {
|
||||
var specificity = _sourceSpecificityFor(compound);
|
||||
for (var state in path) {
|
||||
state.assertCompatibleMediaContext(mediaQueryContext);
|
||||
state.isUsed = true;
|
||||
lineBreak = lineBreak || state.extender.lineBreak;
|
||||
specificity = math.max(specificity, state.specificity);
|
||||
}
|
||||
|
@ -29,9 +29,6 @@ class Extension {
|
||||
/// originally in the document, rather than one defined with `@extend`.
|
||||
final bool isOriginal;
|
||||
|
||||
/// Whether this extension matched a selector.
|
||||
var isUsed = false;
|
||||
|
||||
/// The media query context to which this extend is restricted, or `null` if
|
||||
/// it can apply within any context.
|
||||
List<CssMediaQuery> get mediaContext => _mediaContext;
|
||||
|
Loading…
x
Reference in New Issue
Block a user