Skip to content

x/tools/gopls: detect and recover from snapshot/disk incoherence #78859

Description

@findleyr

A snapshot caches the content of every file it has read, to keep derived calculations such as type-checked packages coherent. But go list reads disk, not the cache, so the two can diverge whenever a closed file changes on disk without a corresponding didChangeWatchedFiles event. #64235 is one symptom (repro and mechanism); #63822 is probably another.

In other words, we hold every workspace file in memory to defend against incoherence, and it isn't sufficient: with the current go command APIs there is no way to guarantee that go list and gopls observe the same file state. We should stop paying the memory cost for a guarantee we don't get, and instead make incoherence recoverable.

Concretely:

  • Detect the inconsistency by checking for inconsistent metadata from Load, or unexpected file content changes. It would be nice if the go command returned a manifest of file identities for files it read.
  • Recover by recreating the view from scratch; we've so heavily optimized start up time so that this should be possible.
  • Degrade gracefully by making most things work when gopls is initializing or reinitializing (x/tools/gopls: long initial workspace load durations for workspace with many packages #69523) -- I'm doing this.
  • Alert the user. Mechanism T.B.D., a "reinitializing" progress at least, but maybe also a popup warning of incoherent disk state.
  • Drop file contents 🥳

Alternatives:

  • copy all the files to a temp directory and run go list there (this is effectively like passing a full overlay). 🤮

Metadata

Metadata

Assignees

No one assigned

    Labels

    FeatureRequestIssues asking for a new feature that does not need a proposal.ToolsThis label describes issues relating to any tools in the x/tools repository.goplsIssues related to the Go language server, gopls.

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions