Invalid CSS selector forces rule to be excluded: what is the rationale?

I am looking more for links to mailing lists, etc., rather than speculation.

Can someone help me find out the rationale for the above error handling rules from the CSS Specors Level 3 spec.

User agents must follow the rules for handling parsing errors:

  • invalid simple selector containing invalid namespace prefix
  • invalid selector containing an invalid simple selector, invalid combinator, or invalid token.
  • invalid selector group containing invalid selector.

Specification reuse Selectors must determine how to handle parsing errors. (In the case of CSS, a general rule that uses a selector is excluded.)

I had the following rule:

#menu li.last, #menu li:last-child { ... } 

To make up for the lack of support for IE8 last month, I used the JavaScript class and fit. However, this did not work because IE8 conforms to the CSS specification for error handling and discards the entire rule because it does not recognize a single selector. This can be eliminated by dividing the two selectors into separate rules.

Why is this desirable? Why doesn't the specification just let go of an unrecognized selector, but keep the rest of the rule?

I would like to know the rationale as the rules currently seem contradictory.

+20
css css-selectors w3c
Dec 11
source share
1 answer

Why is this desirable? Why doesn't the specification just let go of an unrecognized selector, but keep the rest of the rule?

The short answer is that it would be too difficult for implementations to figure out what exactly is the “rest of the rule” (or the “rest of the selector list” if it’s not) without getting it wrong and unintentionally messing around and also for consistency in error handling and subsequent compatibility with future specifications.




I will provide my long answer with a link to my other answer to handling invalid selectors. The commentary to this answer directly points to section 4.1.7 of the CSS2.1 specification regarding errors in selectors in rule sets, which mentions commas in selectors as an example. I think he sums it up pretty nicely:

CSS 2.1 gives special meaning to the comma (,) in selectors. However, since it is not known whether the comma can get other values ​​in future CSS updates, the entire operator should be ignored if there is an error in the selector, although the rest of the selector may look reasonable in CSS 2.1.

While the comma itself still means grouping two or more selectors in relation to selectors, it turns out that selector 4 introduces new functional pseudo-classes that accept selector groups (or select lists) as arguments, for example :matches() (it even changes :not() , so it takes a list, which makes it look like :matches() , whereas at level 3 it only accepts one simple selector).

This means that you will not only find comma-separated groups of selectors associated with the rules, but also begin to find them in functional pseudo-classes (note that this is only in the stylesheet, outside of CSS, selectors can be displayed in the JavaScript code used by libraries - selectors, and the built-in selectors API ).

Although this is not the only reason, it is enough to potentially overly complicate the rules for handling parser errors with a huge risk of breaking a selector, a set of rules, or even a layout. In the case of a parsing error with a comma, the analyzer will have problems determining whether this selection group corresponds to a whole set of rules or part of another group of selectors and how to handle the rest of the selector and the corresponding set of rules, respectively, Instead of trying to guess, take a risk erroneously and it’s wrong to break the rule (for example, by matching and styling all the wrong elements), the safest bet is to abandon the rule and move on.

As an example, consider the following rule, whose selector is valid at level 4, but not at level 3, taken from this question :

 #sectors > div:not(.alpha, .beta, .gamma) { color: #808080; background-color: #e9e9e9; opacity: 0.5; } 

A naive parser that does not understand that Selectors 4 may try to split it into three different selectors that use the same ad unit, rather than one selector with a pseudo-class that accepts a list based on only commas:

 #sectors > div:not(.alpha .beta .gamma) 

If it simply discards the first and last selectors, which are clearly invalid, leaving the second selector valid, should the rule then be applied to any elements of the beta class? This is clearly not what the author intends to do, so if the browser does this, he will go into doing something unexpected for this layout . Discarding a rule using an invalid selector, the layout looks a bit more modest , but this is a simplified example; rules with layout styles can cause even greater problems if applied incorrectly.

Of course, other ambiguities may arise in the syntax selector, which may lead to the following situations:

  • I don't know where the complex selector ends
  • Not knowing where the selector list ends
  • Not knowing where the ad unit starts
  • Combination above

All this, again, is most easily resolved by abandoning a set of rules instead of playing the guessing game.

In the case of seemingly well-formed selectors that are unrecognized, for example :last-child as a pseudo-class in your example, the specification does not distinguish between unrecognized selectors and selectors that are simply distorted. Both results in a parsing error. In the same section that you are referring to:

Invalidity is caused by a parsing error, for example. an unrecognized token or token that is not allowed at the current parsing point.

And having made this statement about :last-child , I assume that the browser is able to parse a single colon, followed by an arbitrary identifier as a pseudo-class; in fact, you cannot assume that the implementation will know that parsing :last-child as a pseudo :last-child is correct or something like :lang() or :not() with functional notation, since functional pseudo-classes were not displayed before CSS2.

Selectors define a specific set of known pseudo-classes and pseudo-elements, the names of which are most likely hard-coded in each implementation. Most naive parsers have all the notation for each pseudo-class and pseudo-element, including single / double colon (s), hardcoded (I won’t be surprised if the main browsers really do this with :before ,: after,: :first-letter and :first-line as a special case ). So, what might seem like a pseudo-class for one implementation, it could well be a gobbledygook for another.

Since there are many ways for implementation failures, the specification makes no difference, making error handling more predictable. If the selector is unrecognized, regardless of whether it is unsupported or distorted, the rule is discarded. Simple, straightforward and easy to lower your head.




All that is said is at least one discussion on the www-style public mailing list, suggesting that the specification be changed, as it may not be so difficult to implement error handling by separating selectors in the end.

I should also mention that some layout mechanisms behave differently, for example, WebKit ignore selectors other than WebKit-prefixed in the rule using their own prefixes, while other browsers completely ignore this rule (you can find more examples in Stack Overflow; here is slightly different ). In a sense, you can say that WebKit bypasses the rule as it is, although it tries to rationally separate groups of selectors separated by commas, despite these selector prefixes.

I do not think that the working group has good reasons to change this behavior. In fact, in any case, they have a good reason not to change it, but because sites have relied on this behavior for many years. We used to have selector hacks for filtering older versions of IE; Today we have prefixes for filtering other browsers. These hacks all rely on the same behavior of some browsers that drop rules that they don’t recognize, with other browsers applying them if they think they are true, for example. recognizing prefixes (or throwing only unrecognized ones, as WebKit does). Sites can break in newer versions of these browsers if this rule was to change, which absolutely cannot happen in such a diverse (readable: fragmented) Web as ours.

As of April 2013, it was decided in a teleconference that this behavior remains unchanged for the reason I mentioned above:

    - RESOLVED: Do not adopt MQ-style invalidation for Selectors
                due to Web-compat concerns.

Media query style invalidation refers to invalid media requests in a comma-separated list without violating the whole @media .

+31
Dec 12
source share



All Articles