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: gopls falls behind user input in large repository #45089

Open
denbeigh2000 opened this issue Mar 17, 2021 · 3 comments
Open

x/tools/gopls: gopls falls behind user input in large repository #45089

denbeigh2000 opened this issue Mar 17, 2021 · 3 comments

Comments

@denbeigh2000
Copy link

@denbeigh2000 denbeigh2000 commented Mar 17, 2021

What version of Go are you using (go version)?

$ go version
go version go1.15.7 linux/amd64

Does this issue reproduce with the latest release?

Yes

What operating system and processor architecture are you using (go env)?

go env Output
$ go env
GO111MODULE="on"
GOARCH="amd64"
GOBIN=""
GOCACHE=".../.cache/go-build"
GOENV=".../.config/go/env"
GOEXE=""
GOFLAGS="-mod=readonly"
GOHOSTARCH="amd64"
GOHOSTOS="linux"
GOINSECURE=""
GOMODCACHE=".../go/pkg/mod"
GONOPROXY=""
GONOSUMDB=""
GOOS="linux"
GOPATH="/home/ubuntu/co/backend/go"
GOPRIVATE=""
GOPROXY="https://proxy.golang.org,direct"
GOROOT=".../opt/go1.15.7"
GOSUMDB="sum.golang.org"
GOTMPDIR=""
GOTOOLDIR=".../opt/go1.15.7/pkg/tool/linux_amd64"
GCCGO="gccgo"
AR="ar"
CC="gcc"
CXX="g++"
CGO_ENABLED="1"
GOMOD="/dev/null"
CGO_CFLAGS="-g -O2"
CGO_CPPFLAGS=""
CGO_CXXFLAGS="-g -O2"
CGO_FFLAGS="-g -O2"
CGO_LDFLAGS="-g -O2"
PKG_CONFIG="pkg-config"
GOGCCFLAGS="-fPIC -m64 -pthread -fmessage-length=0 -fdebug-prefix-map=/tmp/go-build854677189=/tmp/go-build -gno-record-gcc-switches"

What did you do?

  • Open a single file in VSCode, with gopls enabled.
  • This file (in my case) is very simple. It is the only file in its' package, has no imports and defines only a few constants and functions to export. But, it is part of a very large monorepo that is managed with Go Modules.
  • Add a trivial line to this file (in my case, adding a return statement to a function)
  • Save the file

What did you expect to see?

  • gopls should provide feedback that updates promptly as I type
  • (VSCode-specific): The UI-blocking "Getting code actions from Go" task should (ideally) not exceed the configured codeActionsOnSaveTimeout option.

What did you see instead?

gopls appears to take several seconds to process each keystroke, and I need to wait to allow gopls to catch up. I see feedback gradually appear character-by-character, and autocomplete shown only after this has caught up to the new state of the file.

Screen Shot 2021-03-17 at 9 28 07 AM

Screen Shot 2021-03-17 at 9 28 17 AM

If I save before gopls has caught up, I see a "Waiting for code actions from "Go"" prompt, that I can only dismiss by hard-quitting VSCode, or waiting for gopls to finish its' work (in these experiments, this took 40-60s). If I save after gopls has caught up, the action is relatively quick.

Build info

Tested with two versions - v0.6.7 and a recent master

gopls bug Output (0.6.7)
```
golang.org/x/tools/gopls v0.6.7
    golang.org/x/tools/gopls@v0.6.7 h1:l5BBHYi1VYXcqscDL4EO+GkRyxpg/jRcgrwKopgK/EU=
    github.com/BurntSushi/toml@v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ=
    github.com/google/go-cmp@v0.5.4 h1:L8R9j+yAqZuZjsqh/z+F1NCffTKKLShY6zXTItVIZ8M=
    github.com/sergi/go-diff@v1.1.0 h1:we8PVUC3FE2uYfodKH/nBHMSetSfHDR6scGdBi+erh0=
    golang.org/x/mod@v0.4.1 h1:Kvvh58BN8Y9/lBi7hTekvtMpm07eUZ0ck5pRHpsMWrY=
    golang.org/x/sync@v0.0.0-20201020160332-67f06af15bc9 h1:SQFwaSi55rU7vdNs9Yr0Z324VNlrF+0wMqRXT4St8ck=
    golang.org/x/sys@v0.0.0-20210124154548-22da62e12c0c h1:VwygUrnw9jn88c4u8GD3rZQbqrP/tgas88tPUbBxQrk=
    golang.org/x/tools@v0.1.1-0.20210310201602-f3da8934356a h1:wtsfTQvoSxHhNCmmTXFd6D3/uXlQSa9SfUZbHgvlPUA=
    golang.org/x/xerrors@v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
    honnef.co/go/tools@v0.1.1 h1:EVDuO03OCZwpV2t/tLLxPmPiomagMoBOgfPt0FM+4IY=
    mvdan.cc/gofumpt@v0.1.0 h1:hsVv+Y9UsZ/mFZTxJZuHVI6shSQCtzZ11h1JEFPAZLw=
    mvdan.cc/xurls/v2@v2.2.0 h1:NSZPykBXJFCetGZykLAxaL6SIpvbVy/UFEniIfHAa8A=
```
gopls bug Output (recent master)
```
golang.org/x/tools/gopls master
    golang.org/x/tools/gopls@v0.0.0-20210315231133-6d45e3d999c1 h1:k6B7bKOBs7YrTDv0cFs3h3Rzh6bBYbpzrrSPnFvcOxc=
    github.com/BurntSushi/toml@v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ=
    github.com/google/go-cmp@v0.5.4 h1:L8R9j+yAqZuZjsqh/z+F1NCffTKKLShY6zXTItVIZ8M=
    github.com/sergi/go-diff@v1.1.0 h1:we8PVUC3FE2uYfodKH/nBHMSetSfHDR6scGdBi+erh0=
    golang.org/x/mod@v0.4.1 h1:Kvvh58BN8Y9/lBi7hTekvtMpm07eUZ0ck5pRHpsMWrY=
    golang.org/x/sync@v0.0.0-20201020160332-67f06af15bc9 h1:SQFwaSi55rU7vdNs9Yr0Z324VNlrF+0wMqRXT4St8ck=
    golang.org/x/sys@v0.0.0-20210124154548-22da62e12c0c h1:VwygUrnw9jn88c4u8GD3rZQbqrP/tgas88tPUbBxQrk=
    golang.org/x/tools@v0.1.0 h1:po9/4sTYwZU9lPhi1tOrb4hCv3qrhiQ77LZfGa2OjwY=
    golang.org/x/xerrors@v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
    honnef.co/go/tools@v0.1.1 h1:EVDuO03OCZwpV2t/tLLxPmPiomagMoBOgfPt0FM+4IY=
    mvdan.cc/gofumpt@v0.1.0 h1:hsVv+Y9UsZ/mFZTxJZuHVI6shSQCtzZ11h1JEFPAZLw=
    mvdan.cc/xurls/v2@v2.2.0 h1:NSZPykBXJFCetGZykLAxaL6SIpvbVy/UFEniIfHAa8A=
```

Log files/debugging info

VSCode settings
go.code-workspace

Test 1: gopls@6d45e3d999c1 opened file, add statement, wait for gopls to catch up, save file
gopls-log.sanitised.out.txt-1

Test 2: gopls@6d45e3d999c1 opened file, add statement, save immediately
gopls-log.sanitised.out.txt

Test 3: gopls@v0.6.7 opened file, add statement, wait for gopls to catch up, save file
gopls-log.sanitised.out.txt

Let me know if I can provide any more info! I have also collected memory/cpu profiles and traces, but they exceed GH's file posting limit - happy to share these on Gophers Slack or similar.

@denbeigh2000 denbeigh2000 changed the title /x/tools/gopls: gopls not falls behind user input in large repository /x/tools/gopls: gopls falls behind user input in large repository Mar 17, 2021
@gopherbot gopherbot added the gopls label Mar 17, 2021
@stamblerre stamblerre changed the title /x/tools/gopls: gopls falls behind user input in large repository x/tools/gopls: gopls falls behind user input in large repository Mar 17, 2021
@gopherbot gopherbot added the Tools label Mar 17, 2021
@gopherbot gopherbot added this to the Unreleased milestone Mar 17, 2021
@stamblerre
Copy link
Contributor

@stamblerre stamblerre commented Mar 19, 2021

Thank you so much for this detailed report, @denbeigh2000. We did discover a bug that caused a performance issue in v0.6.7, and it should now be addressed at master.

Can you please test this out once again with the latest master and confirm whether there is still a problem? You can download gopls at master by running GO111MODULE=on go get golang.org/x/tools/gopls@master golang.org/x/tools@master. Thank you!

@denbeigh2000
Copy link
Author

@denbeigh2000 denbeigh2000 commented Mar 19, 2021

Howdy @stamblerre! I repeated these steps this morning, and I see an improvement in autocomplete:

  • I see an autocomplete prompt in a acceptable time, I no longer need to wait for gopls to "catch up" to see suggestions.

However, I do still see some issues in latency/saving:

  • I still observe this "falling behind typing" behaviour in this file, and the "Getting code actions..." prompt is still slow/blocks UI if gopls has not caught up by the time I save.

Steps I took:

  • Open simple file in VSCode, allow initial scan to finish ("Loading packages")
  • Enter new line in function with trivial return statement
  • Observe "red squiggly" move character by character over my new statement - takes approx. 40-60s to catch up.
  • If I save before this catches up current state, I see a "Waiting for code actions from "Go"" dialogue that remains until the "red squiggly" reaches the end of my new statement (I assume this is when gopls has finished processing my typing changes).

autocomplete

This is the version I have been testing with:

golang.org/x/tools/gopls master
    golang.org/x/tools/gopls@v0.0.0-20210319044015-1aac171fc654 h1:SN2YYteX4/2uG/2k2+Pxzaj/PpNCb3bAcdBkYB4+mEA=
    github.com/BurntSushi/toml@v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ=
    github.com/google/go-cmp@v0.5.4 h1:L8R9j+yAqZuZjsqh/z+F1NCffTKKLShY6zXTItVIZ8M=
    github.com/sergi/go-diff@v1.1.0 h1:we8PVUC3FE2uYfodKH/nBHMSetSfHDR6scGdBi+erh0=
    golang.org/x/mod@v0.4.1 h1:Kvvh58BN8Y9/lBi7hTekvtMpm07eUZ0ck5pRHpsMWrY=
    golang.org/x/sync@v0.0.0-20201020160332-67f06af15bc9 h1:SQFwaSi55rU7vdNs9Yr0Z324VNlrF+0wMqRXT4St8ck=
    golang.org/x/sys@v0.0.0-20210124154548-22da62e12c0c h1:VwygUrnw9jn88c4u8GD3rZQbqrP/tgas88tPUbBxQrk=
    golang.org/x/tools@v0.1.1-0.20210319044015-1aac171fc654 h1:nc27fqKQotOOk0DdNxjqErlc3rzIafq5t8TgfUeeFPk=
    golang.org/x/xerrors@v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
    honnef.co/go/tools@v0.1.1 h1:EVDuO03OCZwpV2t/tLLxPmPiomagMoBOgfPt0FM+4IY=
    mvdan.cc/gofumpt@v0.1.0 h1:hsVv+Y9UsZ/mFZTxJZuHVI6shSQCtzZ11h1JEFPAZLw=
    mvdan.cc/xurls/v2@v2.2.0 h1:NSZPykBXJFCetGZykLAxaL6SIpvbVy/UFEniIfHAa8A=

And here are output logs of two runs:
Run 1: open file, add line, wait for catch up, fast save
gopls-log.sanitised.out.txt

Run 2: open file, add line, immediate save, wait for code actions on save prompt
gopls-log.sanitised.out.txt


NB: Due to some logistical changes, @aws5295 and/or @kushmansingh will be carrying on this discussion - I've ensured that these reproducible troubleshooting steps have been communicated. Thank you for your attentiveness toward our gopls inquiries! 🙏

@stamblerre
Copy link
Contributor

@stamblerre stamblerre commented Mar 24, 2021

Thank you so much for sharing this information. It looks like you're working in a really big monorepo, and gopls may just not be able to cope with the number of files. We don't have any near-term plans to improve gopls in large repositories, so in the meantime, Is it possible for you to open a subdirectory of the module when you're working on it? Or you could also look into the directoryFilters setting to limit the size of the workspace.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Linked pull requests

Successfully merging a pull request may close this issue.

None yet
3 participants