ty icon indicating copy to clipboard operation
ty copied to clipboard

Filter out language-keyword completions in places where only an expression can be valid syntax

Open AlexWaygood opened this issue 3 weeks ago • 6 comments

For example, in this situation, raise should not be included as a completion suggestion, because for x in raise is invalid syntax (Python's grammar dictates that only an expression can follow the sequence for <EXPR> in ):

Image

AlexWaygood avatar Dec 05 '25 14:12 AlexWaygood

Similarly, it's a bit annoying that finally is at the top of the list here when syntactically it would only ever be invalid syntax for a keyword to appear in this position:

Image

AlexWaygood avatar Dec 13 '25 21:12 AlexWaygood

https://github.com/astral-sh/ruff/pull/21979 did this for for ... in <CURSOR>.

I wonder if it make senses to approach this issue more methodically. That is, enumerate all classes of "must be an expression" locations, and then try to convert that to code so that we can more holistically rule out things that aren't expressions (or can't become expressions).

Otherwise it seems likely this will just be a whack-a-mole kind of thing.

BurntSushi avatar Dec 15 '25 18:12 BurntSushi

enumerate all classes of "must be an expression" locations

Why not just use the formal Python grammar for this, then you can avoid suggesting something that leads to invalid syntax in all cases? Should also make it easy to support different Python versions (maintaining https://github.com/astral-sh/ruff/pull/22002 as the grammar grows is going to lead to a lot of conditionals, I imagine).

gablank avatar Dec 17 '25 07:12 gablank

@gablank Can you elaborate? What specifically are you suggesting?

BurntSushi avatar Dec 17 '25 13:12 BurntSushi

I am making quite a few assumptions on how ty works here, but reading https://github.com/astral-sh/ruff/pull/22002 it seems to me like what ty lists as valid next keywords is just based on "hardcoding", i.e. "if the current state is for x in <iter>:<CURSOR>, then yield, return, await etc. are valid keywords".

What I'm asking is why the grammar itself isn't used to generate up all this, instead of encoding that logic by hand?

I guess you're kind of suggesting the same in this comment, although maybe a special case of what I'm asking about?

I wonder if it make senses to approach this issue more methodically. That is, enumerate all classes of "must be an expression" locations, and then try to convert that to code so that we can more holistically rule out things that aren't expressions (or can't become expressions).

gablank avatar Dec 17 '25 13:12 gablank

What I'm asking is why the grammar itself isn't used to generate up all this, instead of encoding that logic by hand?

generating some kind of schema from the formal grammar at https://github.com/python/cpython/blob/3.14/Grammar/python.gram is an interesting idea. It sounds hard, though

AlexWaygood avatar Dec 17 '25 13:12 AlexWaygood

I believe this should now be closed by https://github.com/astral-sh/ruff/pull/22002

BurntSushi avatar Dec 18 '25 17:12 BurntSushi