golang / vscode-go

Go extension for Visual Studio Code
https://marketplace.visualstudio.com/items?itemName=golang.Go
Other
3.79k stars 728 forks source link

Extremely slow language server startup time with bazel #3212

Closed zack-littke-smith closed 4 months ago

zack-littke-smith commented 4 months ago

What version of Go, VS Code & VS Code Go extension are you using?

Version Information
* Run `go version` to get version of Go from _the VS Code integrated terminal_. - go version go1.21.1 linux/amd64 * Run `gopls -v version` to get version of Gopls from _the VS Code integrated terminal_. ``` Build info ---------- golang.org/x/tools/gopls v0.15.1 golang.org/x/tools/gopls@v0.15.1 h1:WBLlqa3auWKt/jbezarYT204f7IDtCdOn260vY0q4Vk= github.com/BurntSushi/toml@v1.2.1 h1:9F2/+DoOYIOksmaJFPw1tGFy1eDnIJXg+UHjuD8lTak= github.com/google/go-cmp@v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI= golang.org/x/exp/typeparams@v0.0.0-20221212164502-fae10dda9338 h1:2O2DON6y3XMJiQRAS1UWU+54aec2uopH3x7MAiqGW6Y= golang.org/x/mod@v0.15.0 h1:SernR4v+D55NyBH2QiEQrlBAnj1ECL6AGrA5+dPaMY8= golang.org/x/sync@v0.6.0 h1:5BMeUDZ7vkXGfEr1x9B4bRcTH4lpkTkpdh0T/J+qjbQ= golang.org/x/telemetry@v0.0.0-20240209200032-7b892fcb8a78 h1:vcVnuftN4J4UKLRcgetjzfU9FjjgXUUYUc3JhFplgV4= golang.org/x/text@v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ= golang.org/x/tools@v0.18.1-0.20240227180630-1c466157abc9 h1:DAFzI/OUTyNjVKs2nsM593aR8oHWjVh3ftZ7XQFEKXw= golang.org/x/vuln@v1.0.1 h1:KUas02EjQK5LTuIx1OylBQdKKZ9jeugs+HiqO5HormU= honnef.co/go/tools@v0.4.6 h1:oFEHCKeID7to/3autwsWfnuv69j3NsfcXbvJKuIcep8= mvdan.cc/gofumpt@v0.6.0 h1:G3QvahNDmpD+Aek/bNOLrFR2XC6ZAdo62dZu65gmwGo= mvdan.cc/xurls/v2@v2.5.0 h1:lyBNOm8Wo71UknhUs4QTFUNNMyxy2JEIaKKo0RWOh+8= go: go1.21.1 ``` * Run `code -v` or `code-insiders -v` to get version of VS Code or VS Code Insiders. ``` 1.86.2 903b1e9d8990623e3d7da1df3d33db3e42d80eda x64 ``` * Check your installed extensions to get the version of the VS Code Go extension - 0.41.1 * Run Ctrl+Shift+P (Cmd+Shift+P on Mac OS) > `Go: Locate Configured Go Tools` command. ``` # Tools Configuration ## Environment GOBIN: undefined toolsGopath: gopath: /home/zack/go GOROOT: /usr/local/go PATH: /home/zack/go/bin:/usr/local/go/bin:/home/zack/.local/bin:/home/zack/bin:/home/zack/go/bin:/usr/local/go/bin:/home/zack/.local/bin:/home/zack/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin:/home/zack/bin ## Tools go: /usr/local/go/bin/go: go version go1.21.1 linux/amd64 gopls: /home/zack/go/bin/gopls (version: v0.15.1 built with go: go1.21.1) gotests: /home/zack/go/bin/gotests (version: v1.6.0 built with go: go1.21.1) gomodifytags: /home/zack/go/bin/gomodifytags (version: v1.16.0 built with go: go1.21.1) impl: /home/zack/go/bin/impl (version: v1.1.0 built with go: go1.21.1) goplay: /home/zack/go/bin/goplay (version: v1.0.0 built with go: go1.21.1) dlv: /home/zack/go/bin/dlv (version: v1.22.1 built with go: go1.21.1) staticcheck: /home/zack/go/bin/staticcheck (version: v0.4.7 built with go: go1.21.1) ## Go env Workspace Folder (applied2): /applied2 GO111MODULE='' GOARCH='amd64' GOBIN='' GOCACHE='/home/zack/.cache/go-build' GOENV='/home/zack/.config/go/env' GOEXE='' GOEXPERIMENT='' GOFLAGS='' GOHOSTARCH='amd64' GOHOSTOS='linux' GOINSECURE='' GOMODCACHE='/home/zack/go/pkg/mod' GONOPROXY='' GONOSUMDB='' GOOS='linux' GOPATH='/home/zack/go' GOPRIVATE='' GOPROXY='https://proxy.golang.org,direct' GOROOT='/usr/local/go' GOSUMDB='sum.golang.org' GOTMPDIR='' GOTOOLCHAIN='auto' GOTOOLDIR='/usr/local/go/pkg/tool/linux_amd64' GOVCS='' GOVERSION='go1.21.1' GCCGO='gccgo' GOAMD64='v1' AR='ar' CC='gcc' CXX='g++' CGO_ENABLED='1' GOMOD='/applied2/go.mod' GOWORK='' CGO_CFLAGS='-O2 -g' CGO_CPPFLAGS='' CGO_CXXFLAGS='-O2 -g' CGO_FFLAGS='-O2 -g' CGO_LDFLAGS='-O2 -g' PKG_CONFIG='pkg-config' GOGCCFLAGS='-fPIC -m64 -pthread -Wl,--no-gc-sections -fmessage-length=0 -ffile-prefix-map=/tmp/go-build833713955=/tmp/go-build -gno-record-gcc-switches' ```

I am also running https://github.com/bazelbuild/rules_go to interact with bazel which we rely on for our building

Share the Go related settings you have added/edited

  "go.toolsEnvVars": {
    "GOPACKAGESDRIVER": " ..."
  },
  "go.enableCodeLens": {
    "runtest": false
  },
  "go.languageServerFlags": [
    "-rpc.trace", // for more detailed debug logging
    "serve",
    "--debug=localhost:6060", // to investigate memory usage, see profiles
  ],
  "gopls": {
    "build.directoryFilters": [
      ...
    ],
    "ui.completion.usePlaceholders": true,
    "ui.semanticTokens": true,
    "ui.codelenses": {
      "gc_details": false,
      "regenerate_cgo": false,
      "generate": false,
      "test": false,
      "tidy": false,
      "upgrade_dependency": false,
      "vendor": false
    },
    "verboseOutput": true
  },
  "go.trace.server": "verbose",
  "go.useLanguageServer": true,
  "go.buildOnSave": "off",
  "go.lintOnSave": "off",
  "go.vetOnSave": "off",

Describe the bug

On starting vscode, the language server takes minutes, sometimes tens of minutes, to start. Requests to restart the server are not received by the server. Running top on the machine reveals no significant resource usage by any processes while the server is starting.

server_logs.txt

Our codebase is not terribly large.

Steps to reproduce the behavior:

I encounter this issue when opening a .go file, code completion is constantly 'loading...' and file save takes an unreasonable amount of time. Apologies for not having a better repro process.

Are there any settings that stand out, or steps I can take to diagnose this issue?

zack-littke-smith commented 4 months ago

This may also be an issue with the bazel integration we have, pursuing that currently

hyangah commented 4 months ago

@zack-littke-smith Did you see this problem prior to goplps upgrade? (gopls v0.15.x was released recently) Can you test if downgrading gopls to v0.14.2 makes any difference?

go install golang.org/x/tools/gopls@v0.14.2

zack-littke-smith commented 4 months ago

I believe it's roughly the same with both versions

adonovan commented 4 months ago

We don't actively support or test gopls on Bazel or other non-default GOPACKAGESDRIVERs, but still startup shouldn't take much longer than a bazel query for the workspace.

I notice in the log that the "loading packages..." operation never finishes (no subsequent notifications with the same token).

Params: {"token":"154022641030505768","value":{"kind":"begin","title":"Setting up workspace","message":"Loading packages..."}}

Next time you observe the slowness, can you report what happens when you run the following commands?

$ go install golang.org/x/tools/go/packages/gopackages@latest
$ time GOPACKAGESDRIVER=/applied2/dev/go_packages_driver.bash gopackages ./dev/...

(You needn't share the names of the packages, just the running time and success status.)

zack-littke-smith commented 4 months ago

@adonovan On initial start im getting:

real    24m0.224s
user    0m0.122s
sys 0m0.033s

Subsequent invocations take only a couple seconds

adonovan commented 4 months ago

Wow, that is very slow. Clearly though the problem is in the Bazel go/packages driver tool, so I think you will need to get in touch with its maintainers. (Ah, I see you already tried in bazelbuild/rules_go#3878.)

By comparison, how slow is a simple bazel query //... command? Usually the driver is a very thin wrapper over the underlying build system's query tool, so if 'bazel query' is very slow, that's a more fundamental problem of your build, not of the go/packages driver.

zack-littke-smith commented 4 months ago

@adonovan I agree, will do! Thanks for your help here