Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(lsp): Improve lsp behaviour on goto definition #1893

Open
wants to merge 4 commits into
base: main
Choose a base branch
from

Conversation

spotandjake
Copy link
Member

The previous behaviour of the lsp with goto definition failed when you selected a variable from left to right, we now try and account for this by trying to find again, but one char over if we fail the first check.

Copy link
Member

@marcusroberts marcusroberts left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Well spotted and nice fix!

@spotandjake spotandjake added the lsp Issues related to the language server. label Jul 21, 2023
Copy link
Member

@phated phated left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Need to clean up the API design on your function

| None =>
if (depth == 0 && position.character > 0) {
find_definition(
~depth=1,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You are using ~depth with an integer that is only ever 1 or 0. That seems feels like it means it should be bool but that is probably not clear enough to explain the purpose so maybe you should make variants for the states this function can handle.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I fixed this by using a better variable name and adding a comment. as I didnt feel that a variant provided enough context as to what we were doing.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Reading your comment helps, but I think this should be variants that wrap the Position.position and probably called Forwards and Backwards or something. Bool flags are almost always bad design.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I switched to a variant, named Forwards, Backwards

Comment on lines 84 to 92
if (check_position == Forward && position.character > 0) {
// If a user selects from left to right, their pointer ends up after the identifier
// this trys to check if the identifier was selected.
find_definition(
~check_position=Backward,
sourcetree,
{line: position.line, character: position.character - 1},
);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wonder if this is actually just a "bug" in the sourcetree, as such the sourcetree seems to be position exclusive when it probably should be location inclusive. Is this a correct assessment?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think so the issue really seems to be from highlighting and where your cursor is. we do not know which way the user is highlighting left to right or right to left. as such we don't know where the cursor will be.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The sourcetree is supposed to provide a correct node, no matter the position of the cursor. Whether the cursor is like: |foobar or foobar| or foo|bar or anything. And it seems that it doesn't.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The sourcetree is supposed to provide a correct node, no matter the position of the cursor. Whether the cursor is like: |foobar or foobar| or foo|bar or anything. And it seems that it doesn't.

Digging into this a bit more If we want to fix this in sourceTree then I think we should just add 1 to pos_end.charater in loc_to_interval.

I still think this is an issue in the lsp spec. mainly because of the case of foo|+1 with the cursor location being represented by | its ambigous if the user is selecting over foo from left to right or selecting + from right to left.

Note the ambiguity here really comes from the fact that the user is selecting over a range.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@ospencer does Jake's thoughts above sound correct here?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If the LSP spec doesn't say that it's in the range, then I think we should close this PR.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's up to our interpretation. The editor will send the request with whatever the cursor position is. We don't consider a cursor after something as overlapping that range. That's the correct behavior, but in the case Jake is trying to address—highlighting an identifier from the beginning to the end—your cursor ends up after, and the goto fails.

We have to decide if we care. I think it's reasonable enough to try to improve the user experience because I imagine some users do this. I don't think we should change the sourcetree though, because it's correct.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree about not changing the sourcetree. For context as to when this was a problem for me. I was double clicking on an identifier to select it and then clicking goto definition which I feel is common behavior.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We don't consider a cursor after something as overlapping that range.

If we don't consider the cursor in the range, then one of our tools shouldn't either.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree with the statement and when considering the cursor position I agree with the viewpoint. The issue in this case isn't the cursor position though it is the selection range. And the fact that when you double click on an identifier to select it, it puts the cursor at the end. Which seems like reasonable user behaviour.

Copy link
Member

@ospencer ospencer left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

While I believe that from a technical standpoint our current behavior is correct, from a user experience perspective, this change makes sense to me and is the right way forward.

I have one small nit, but otherwise this LGTM.

compiler/src/language_server/definition.re Outdated Show resolved Hide resolved
@ospencer ospencer requested a review from phated April 1, 2024 19:43
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
compiler enhancement lsp Issues related to the language server.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants