fix(compiler): support complex selectors in :nth-child()#65010
fix(compiler): support complex selectors in :nth-child()#65010AndrewKushnir merged 1 commit intoangular:mainfrom
Conversation
:nth-child() (and its siblings) support complex expressions, e.g. `:nth-child(2n of :is(.foo, .bar))`. Previously we'd choke because of the `:is()`. Now, we reuse the `_parenSuffix` subexpression to match nested parentheses the same way we do for :host() and :host-context(). Note that we only support 3 levels of nesting, so a selector like `:nth-child(n of :is(:has(:not(.foo))))` will still break. I'll say yet again that we really should add a proper parser so we stop getting bug reports like this :) Fixes angular#64913
| // Matches content with at most TWO levels of nesting, e.g., "a(b(c)d)e" | ||
| const _level2Parens = String.raw`(?:\(${_level1Parens}\)|${_noParens})+?`; | ||
| const _parenSuffix = String.raw`(?:\((${_level2Parens})\))`; | ||
| const nthRegex = new RegExp(String.raw`(:nth-[-\w]+)` + _parenSuffix, 'g'); |
There was a problem hiding this comment.
Regexes with the g flag have a state. Is that a concern for this case?
There was a problem hiding this comment.
I don't think it's a concern. You may know more or be more familiar, though. The existing expression also uses the global flag, so I believe this produces the same results. (I know regexp literals are compiled on script load, but IIRC otherwise they behave identically to instantiating a RegExp?)
From my read of the spec and docs on MDN, it looks like while using the g flag makes the RegExp track its lastIndex for the match. This is relevant for the RegExp.prototype.exec() method, which it appears String.prototype.replace() calls repeatedly. Since this should replace all occurrences in the string, lastIndex should be reset to 0 by the end (MDN description).
The statefulness seems like more of a concern if you exec against one string then exec against another string without resetting lastIndex.
|
This issue has been automatically locked due to inactivity. Read more about our automatic conversation locking policy. This action has been performed automatically by a bot. |
:nth-child() (and its siblings) support complex expressions, e.g.
:nth-child(2n of :is(.foo, .bar)). Previously we'd choke because of the:is(). Now, we reuse the_parenSuffixsubexpression to match nested parentheses the same way we do for :host() and :host-context(). Note that we only support 3 levels of nesting, so a selector like:nth-child(n of :is(:has(:not(.foo))))will still break.I'll say yet again that we really should add a proper parser so we stop getting bug reports like this :)
Fixes #64913