You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
unsupported pseudo: valid with selector list #5177
jQuery has a mechanism of - simplifying a bit - trying a provided selector against querySelectorAll in a try-catch and, if it fails, falling back to its own traversal mechanism inherited from Sizzle.
In jQuery 3.6.2 we started using CSS.supports( "selector(SELECTOR)" ) (for a proper SELECTOR) before using querySelectorAll on the selector. This was to solve #5098 - some selectors, like :is(), now have their parameters parsed in a forgiving way, meaning that :is(:fakepseudo) no longer throws but just returns 0 results, breaking that jQuery mechanism.
A recent spec change made CSS.supports( "selector(SELECTOR)" ) always use non-forgiving parsing, allowing us to use this API for what we've used try-catch before. This change has only arrived in Firefox stable so far, though.
Now, I only see this behavior in Firefox as that's the only browser passing our support test. In which version of Safari are you also seeing it? Please share a test case that breaks there.
I see two ways of fixing this:
Use CSS.supports() earlier, when we still have the selector split into groups.
Use CSS.supports( "selector(:is(SELECTOR))" ) instead of CSS.supports( "selector(SELECTOR)" )
The second solution definitely only makes sense only in browsers that implement non-forgiving parsing in CSS.supports( "selector(...)" ) but we're already limiting our usage to such browsers so we should be fine with it, I think.
I'm tagging it for 3.6.3, we'll discuss this on our next team meeting.
BTW, in many cases, the only consequence of this bug would be performance issues as more selectors go through the jQuery selector engines instead of querySelectorAll. This one surfaced because jQuery doesn't support the :valid pseudo-class so such a selector can only work if the qSA code path is used.
Activity
mgol commentedon Dec 17, 2022
Thanks for the report!
jQuery has a mechanism of - simplifying a bit - trying a provided selector against
querySelectorAllin atry-catchand, if it fails, falling back to its own traversal mechanism inherited from Sizzle.In jQuery 3.6.2 we started using
CSS.supports( "selector(SELECTOR)" )(for a properSELECTOR) before usingquerySelectorAllon the selector. This was to solve #5098 - some selectors, like:is(), now have their parameters parsed in a forgiving way, meaning that:is(:fakepseudo)no longer throws but just returns 0 results, breaking that jQuery mechanism.A recent spec change made
CSS.supports( "selector(SELECTOR)" )always use non-forgiving parsing, allowing us to use this API for what we've usedtry-catchbefore. This change has only arrived in Firefox stable so far, though.Now, apparently, our implementation has a bug - in
CSS.supports( "selector(SELECTOR)" ),SELECTORneeds to be a<complex-selector>and not a<complex-selector-list>. Which means:and explains your observations. See the live test case: https://jsbin.com/vesureh/1/edit?html,js,console
Now, I only see this behavior in Firefox as that's the only browser passing our support test. In which version of Safari are you also seeing it? Please share a test case that breaks there.
I see two ways of fixing this:
CSS.supports()earlier, when we still have the selector split into groups.CSS.supports( "selector(:is(SELECTOR))" )instead ofCSS.supports( "selector(SELECTOR)" )The second solution definitely only makes sense only in browsers that implement non-forgiving parsing in
CSS.supports( "selector(...)" )but we're already limiting our usage to such browsers so we should be fine with it, I think.I'm tagging it for 3.6.3, we'll discuss this on our next team meeting.
mgol commentedon Dec 17, 2022
BTW, in many cases, the only consequence of this bug would be performance issues as more selectors go through the jQuery selector engines instead of
querySelectorAll. This one surfaced because jQuery doesn't support the:validpseudo-class so such a selector can only work if theqSAcode path is used.Selector: Make selector lists work with `qSA` again
Selector: Make selector lists work with `qSA` again
Selector: Make selector lists work with `qSA` again
Selector: Make selector lists work with `qSA` again
Selector: Make selector lists work with `qSA` again
Selector: Make selector lists work with `qSA` again
mgol commentedon Dec 17, 2022
PRs:
main, to be backported to3.x-stablefor jQuery3.7.0): Selector: Make selector lists work withqSAagain #51783.6.3): Selector: Make selector lists work withqSAagain sizzle#491Selector: Make selector lists work with `qSA` again
antti-manninen-vmv commentedon Dec 19, 2022
My mistake, Safari does not have this problem. I only saw it with Firefox.
Thanks for quick handling of the problem!
Selector: Make selector lists work with `qSA` again
Selector: Make selector lists work with `qSA` again
Selector: Update Sizzle from 2.3.8 to 2.3.9
Selector: Make selector lists work with `qSA` again
mgol commentedon Dec 19, 2022
The fix landed on
main(future jQuery4.0.0) in 09d988b and on3.x-stable(future jQuery3.7.0) in 848de62.It also landed in Sizzle in jquery/sizzle@7781b65. Then, Sizzle got updated on
3.6-stable(future jQuery3.6.3) in 8989500.The fix & all the backports are done.
mgol commentedon Dec 20, 2022
@antti-manninen-vmv jQuery
3.6.3containing the fix for this issue has been released: https://blog.jquery.com/2022/12/20/jquery-3-6-3-released-a-quick-selector-fix/. That's the only source difference from3.6.2.Thanks for reporting it!
khetaramsb commentedon Jan 13, 2023
After upgrading jQuery from 3.6.0 to3.6.3 pseudo selector :before does not work in selector list with Firefox. Everything works with Chrome.
This worked in 3.6.0
jQuery(".inline-dialog-content:before").css({'left': 40});In 3.6.3 it gives following error:
Uncaught Error: Syntax error, unrecognized expression: unsupported pseudo: before
mgol commentedon Jan 13, 2023
@khetaramsb let's move the discussion to #5194.