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

x/tools/gopls: add go:embed support #50262

Closed
hamidfzm opened this issue Dec 10, 2021 · 26 comments
Closed

x/tools/gopls: add go:embed support #50262

hamidfzm opened this issue Dec 10, 2021 · 26 comments
Assignees
Labels
FeatureRequest gopls/analysis Issues related to running analysis in gopls gopls Issues related to the Go language server, gopls. help wanted NeedsInvestigation Someone must examine and confirm this is a valid issue and not a duplicate of an existing one. Tools This label describes issues relating to any tools in the x/tools repository.
Milestone

Comments

@hamidfzm
Copy link

Is your feature request related to a problem? Please describe.
Go embed feature introduced in version 1.16. Currently, go-vscode treats text like //go:embed app as a simple comment.

Describe the solution you'd like
Provide text highlighting or navigation by CTRL+Clicking on these comments

Describe alternatives you've considered
Goland provides this feature in its recent versions:
Screenshot from 2021-12-10 18-21-42

Additional context
VS code view
Screenshot from 2021-12-10 18-25-51

It would be really nice if we have this feature in my favorite code editor.

@findleyr
Copy link
Contributor

This could be implemented with a code action+associated command that invokes window/showDocument. It could also be implemented with jump-to-definition+hover. I am not sure which is best, but this seems to belong in the gopls issue tracker.

@findleyr findleyr transferred this issue from golang/vscode-go Dec 19, 2021
@findleyr findleyr changed the title Add go:embed support x/tools/gopls: add go:embed support Dec 19, 2021
@gopherbot gopherbot added Tools This label describes issues relating to any tools in the x/tools repository. gopls Issues related to the Go language server, gopls. labels Dec 19, 2021
@gopherbot gopherbot added this to the Unreleased milestone Dec 19, 2021
@findleyr findleyr added FeatureRequest help wanted NeedsInvestigation Someone must examine and confirm this is a valid issue and not a duplicate of an existing one. labels Dec 19, 2021
@findleyr findleyr modified the milestones: Unreleased, gopls/unplanned Dec 19, 2021
@hyangah
Copy link
Contributor

hyangah commented Jan 26, 2022

For individual files, code action associated with window/showDocument or textDocument/documentLink would work. We still need a solution for handling folder type resources. For VSCode, I filed an issue microsoft/vscode#141564.

@ansaba ansaba self-assigned this Apr 11, 2022
@ansaba
Copy link

ansaba commented May 11, 2022

List of improvements

  • checks for the "embed" import
  • Report it as semantic for highlighting
  • The directive must immediately precede a line containing the declaration of a single variable. Only blank lines and ‘//’ line comments are permitted between the directive and the declaration.

EDIT (rfindley): cross out semantic highlighting, as I think we should punt on that for now

@findleyr
Copy link
Contributor

We should also include a quick-fix to add the missing "embed" import.

netbsd-srcmastr pushed a commit to NetBSD/pkgsrc that referenced this issue May 28, 2022
New Features

New analyzer for //go:embed comments

Gopls now includes an analyzer for go:embed comment directives. At
the moment, this analyzer checks that the "embed" import is present,
but more analyses are planned for the future. See golang/go#50262
for more information.

Improved hover for imports

Hovering over an imported path now gives you the full package doc.

Final support for Go 1.13

Per our support window, gopls v0.8.4 will be the final gopls release
to support being built with Go 1.13. See golang/go#52982 for details.

Bugfixes and Performance improvements

    Faster symbol indexing. Gopls builds a symbol index the first
    time symbol search is invoked. That indexing should be 3-4x
    faster with this release.

    Improved metadata invalidation (AKA fewer restarts). v0.8.4
    fixes a couple of bugs that lead to gopls getting confused
    about packages and needing to be restarted. We're aware of more
    bugs of this nature, but are working on eliminating the need
    to ever restart gopls.
@findleyr findleyr added the gopls/analysis Issues related to running analysis in gopls label Jul 20, 2022
@findleyr findleyr modified the milestones: gopls/unplanned, gopls/later Jul 20, 2022
@findleyr
Copy link
Contributor

@vikblom expressed interest in picking this up.

I think the semantic highlighting support is a bit tricky to implement, so let's separate that bit out for now.

Viktor, if you are interested you could do the following:

  • Update the embeddirective
    analyzer to check that the embed directive immediately precedes a line containing the declaration of a single variable. Only blank lines and ‘//’ line comments are permitted between the directive and the declaration.
  • Update the analyzer to include a suggested fix to add the missing "embed" import.

I recommend doing this in two separate CLs. Adding the suggested fix is a little subtle (we should re-use the existing gopls.add_import custom command). So let's discuss the second item after the first is done.

I'll tentatively assign you. Let me know if you don't think you'll be able to work on this.

@findleyr findleyr assigned findleyr and unassigned ansaba May 31, 2023
@findleyr
Copy link
Contributor

Well, @vikblom it turns out I cannot assign you, so I assigned myself as your proxy :)

@vikblom
Copy link

vikblom commented Jun 1, 2023

@findleyr thanks, makes sense to isolate the changes.
I'll give the embeddirective analyzer a look and circle back if I get stuck or have a CL in mind.

@gopherbot
Copy link

Change https://go.dev/cl/504295 mentions this issue: internal/lsp/analysis: embed directive analyzer check following decl

gopherbot pushed a commit to golang/tools that referenced this issue Jul 10, 2023
Extend the embed directive analyzer. Verify that embed directives
are followed by a single variable declaration.

Updates golang/go#50262

Change-Id: Ib69bbfb3aab586a349360d501ceb714a5434e8bd
Reviewed-on: https://go-review.googlesource.com/c/tools/+/504295
Reviewed-by: Alan Donovan <adonovan@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Robert Findley <rfindley@google.com>
Run-TryBot: Robert Findley <rfindley@google.com>
gopls-CI: kokoro <noreply+kokoro@google.com>
@vikblom
Copy link

vikblom commented Jul 10, 2023

Hi @findleyr, with the CL above merged I've started looking at suggesting a fix from the analyzer.

analysis.Diagnostic has a field for SuggestedFixes which seems straight forward enough. You mentioned gopls.add_import, best I can tell that command is backed by source.AddImport. Am I aiming for the right things?

Are there any requirement on placement for the import? I'm used to placing blank imports like _ "embed" last.

Edit: I've also played around with a source.Analysis.Fix function instead to avoid the import cycle.

@findleyr
Copy link
Contributor

Hi @vikblom yes, it sounds like you've got the right idea. There are two aproaches: either compute the edits inline as part of the analyzer, or defer them to later using the source.Analyzer.Fix indirection. The benefit of the latter is that you avoid the performance penalty of pre-computing the edits, and you have access to other facilities that aren't part of the analysis framework, such as source.AddImport. For that reason, I suggest you do the latter, and add a source.SuggestedFixFunc that calls AddImport.

I think there's a problem though, which is that the presence of source.Analyzer.Fix signals that all diagnostics produced by the analyzer can be fixed (which means every diagnostic will have a "quick fix" in VS Code). We don't want that, as the only diagnostics we can fix are those of the missing import. That means we'll have to invent a way to filter "fixable" diagnostics. Perhaps source.Analyzer can have an isFixable func(*source.Diagnostic) bool field. And then in cache.toSourceDiagnostic, build the source.Diagnostic first and pass to isFixable, to see if a quick-fix should be added.

@vikblom
Copy link

vikblom commented Jul 12, 2023

Thanks @findleyr that approach works great 👍

I've added a TestLSP testcase with a golden file verifying that the import is added. Do you have any suggestion or tips on how to test the negative case? (That the other kind of reports (incorrect decl) does not have a code action.)

edit: I found exiting regtest tests checking for false positive quickfixes and made one for this case.

@gopherbot
Copy link

Change https://go.dev/cl/509056 mentions this issue: gopls/internal/lsp: Add SuggestedFix for embeddirective Analyzer.

@vikblom
Copy link

vikblom commented Jul 16, 2023

I noticed that I haven't kept all the docs up to speed, for example analyzers.md. That should probably be corrected as part of this issue.

@findleyr
Copy link
Contributor

@vikblom the analyzer doc is auto-generated, and there is a test to enforce this: cd gopls && go generate .

@vikblom
Copy link

vikblom commented Jul 17, 2023

@findleyr I see! Then it's the analyzers Doc field that (maybe) needs an update. I was thinking it should mention the new variable check and suggested fixes, do you agree?

gopherbot pushed a commit to golang/tools that referenced this issue Jul 27, 2023
Give the embeddirective source.Analyzer a Fix that can
add missing "embed" imports. Since not all reports
from the analyzer is this diagnostic, give source.Analyzer
an IsFixable method to filter diagnostics.

Updates golang/go#50262

Change-Id: I24abdd2d1a88fc5cabd3197ef438c4da041a6a9c
Reviewed-on: https://go-review.googlesource.com/c/tools/+/509056
Run-TryBot: Robert Findley <rfindley@google.com>
gopls-CI: kokoro <noreply+kokoro@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Robert Findley <rfindley@google.com>
Reviewed-by: Hyang-Ah Hana Kim <hyangah@gmail.com>
@gopherbot
Copy link

Change https://go.dev/cl/513895 mentions this issue: gopls/internal/lsp/source: refresh embeddirective analyzer docs

@findleyr findleyr modified the milestones: gopls/later, gopls/v0.14.0 Jul 28, 2023
gopherbot pushed a commit to golang/tools that referenced this issue Jul 28, 2023
Bring the analyzer documentation up to speed. Include the
recently added feature to check the declaration following the
directive.

Also fix typo in package comment.

Updates golang/go#50262

Change-Id: I0e7a8de0ba10cd414251afe1e9c65ded2090f408
Reviewed-on: https://go-review.googlesource.com/c/tools/+/513895
Reviewed-by: Robert Findley <rfindley@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Run-TryBot: Robert Findley <rfindley@google.com>
Reviewed-by: Hyang-Ah Hana Kim <hyangah@gmail.com>
gopls-CI: kokoro <noreply+kokoro@google.com>
@vikblom
Copy link

vikblom commented Jul 31, 2023

Hi @findleyr, is there a path forward with semantic highlighting here, given that the vscode ticket was closed by triage?

I tried out a naive textDocument/documentLink solution passing file:// URIs. Emacs could handle both files and directories. VSCode only accepted files. Does it makes sense to use that as a opt-in or base case (only files) feature?

You mentioned code action+associated command and jump-to-definition+hover above, which seems doable. However if VSCode requires specific (or new) mechanisms to handle directories, this feature might spread to codebases (vscode or vscode-go) I'm not familiar with

@findleyr
Copy link
Contributor

findleyr commented Sep 8, 2023

Hi @vikblom, very sorry for the slow response on this.

Let's not worry about semantic tokens for now, I think that's a low priority. We can treat highlighting //go: directives as a separate project.

We discussed this in our triage meeting, and I think jump-to-definition+hover is the best way to implement this feature, as it will be supported by the greatest number of LSP clients. For directories, perhaps we should just pick an arbitrary file in the directory?

@vikblom
Copy link

vikblom commented Sep 8, 2023

An arbitrary file could be unexpected as a user. But I don't see any alternatives if this is a limitation of LSP clients. I agree it is a good place to start.

I'll try to put something together and post a CL.

@findleyr
Copy link
Contributor

findleyr commented Sep 8, 2023

Great, thanks for sticking to this!

@gopherbot
Copy link

Change https://go.dev/cl/530195 mentions this issue: gopls/internal/lsp: hover over embed directives.

gopherbot pushed a commit to golang/tools that referenced this issue Sep 28, 2023
Enables hover on arguments of go:embed directives.
The hover body lists files matching the argument pattern.

Updates golang/go#50262

Change-Id: I523cec6ab633c90d6826cdbdd6d8fca6afd98935
Reviewed-on: https://go-review.googlesource.com/c/tools/+/530195
Reviewed-by: Robert Findley <rfindley@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Suzy Mueller <suzmue@golang.org>
@gopherbot
Copy link

Change https://go.dev/cl/531775 mentions this issue: gopls/internal/lsp: go to definition from embed directive

gopherbot pushed a commit to golang/tools that referenced this issue Oct 5, 2023
Enable jump to definition on //go:embed directive arguments.
If multiple files match the pattern one is picked at random.

Improve the pattern matching for both definition and hover to
exclude directories since they are not embeddable in themselves.

Updates golang/go#50262

Change-Id: I09da40f195e8edfe661acaacd99f62d9f577e9ea
Reviewed-on: https://go-review.googlesource.com/c/tools/+/531775
Reviewed-by: Robert Findley <rfindley@google.com>
Reviewed-by: Suzy Mueller <suzmue@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
@vikblom
Copy link

vikblom commented Oct 10, 2023

Hi @findleyr, what do you think is the next step? Would tackling semantic highlighting make sense?

@findleyr
Copy link
Contributor

@vikblom if we're going to highlight go:embed, I think we should highlight all go: directives. Is that something you'd be interested in?

If so, I think we should perhaps make that a separate issue, and close this one.

@vikblom
Copy link

vikblom commented Oct 10, 2023

Sure, I'd be glad to take a look directive highlights!

Thanks again for all the help in this issue.

@findleyr
Copy link
Contributor

Great! Opened https://go.dev/issue/63538.

Will close this then.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
FeatureRequest gopls/analysis Issues related to running analysis in gopls gopls Issues related to the Go language server, gopls. help wanted NeedsInvestigation Someone must examine and confirm this is a valid issue and not a duplicate of an existing one. Tools This label describes issues relating to any tools in the x/tools repository.
Projects
None yet
Development

No branches or pull requests

6 participants