gopls: move file-related types to a 'file' package
There is no reason for the source package to define 'FileHandle', a
fundamental type that does not pertain specifically to Go source.
This type is blocking other refactoring, so move it and related types
to a new 'file' package.
Change-Id: Ic5cd9c0f77d842b4316ae6d7f7086f3b747a2452
Reviewed-on: https://go-review.googlesource.com/c/tools/+/543441
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Alan Donovan <adonovan@google.com>
diff --git a/gopls/internal/file/file.go b/gopls/internal/file/file.go
new file mode 100644
index 0000000..5a9d0ac
--- /dev/null
+++ b/gopls/internal/file/file.go
@@ -0,0 +1,62 @@
+// Copyright 2023 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+// The file package defines types used for working with LSP files.
+package file
+
+import (
+ "context"
+ "fmt"
+
+ "golang.org/x/tools/gopls/internal/lsp/protocol"
+)
+
+// An Identity identifies the name and contents of a file.
+//
+// TODO(rfindley): Identity may not carry its weight. Consider instead just
+// exposing Handle.Hash, and using an ad-hoc key type where necessary.
+// Or perhaps if mod/work parsing is moved outside of the memoize cache,
+// a notion of Identity simply isn't needed.
+type Identity struct {
+ URI protocol.DocumentURI
+ Hash Hash // digest of file contents
+}
+
+func (id Identity) String() string {
+ return fmt.Sprintf("%s%s", id.URI, id.Hash)
+}
+
+// A FileHandle represents the URI, content, hash, and optional
+// version of a file tracked by the LSP session.
+//
+// File content may be provided by the file system (for Saved files)
+// or from an overlay, for open files with unsaved edits.
+// A FileHandle may record an attempt to read a non-existent file,
+// in which case Content returns an error.
+type Handle interface {
+ // URI is the URI for this file handle.
+ URI() protocol.DocumentURI
+ // Identity returns an Identity for the file, even if there was an error
+ // reading it.
+ Identity() Identity
+ // SameContentsOnDisk reports whether the file has the same content on disk:
+ // it is false for files open on an editor with unsaved edits.
+ SameContentsOnDisk() bool
+ // Version returns the file version, as defined by the LSP client.
+ // For on-disk file handles, Version returns 0.
+ Version() int32
+ // Content returns the contents of a file.
+ // If the file is not available, returns a nil slice and an error.
+ Content() ([]byte, error)
+}
+
+// A Source maps URIs to Handles.
+type Source interface {
+ // ReadFile returns the Handle for a given URI, either by reading the content
+ // of the file or by obtaining it from a cache.
+ //
+ // Invariant: ReadFile must only return an error in the case of context
+ // cancellation. If ctx.Err() is nil, the resulting error must also be nil.
+ ReadFile(ctx context.Context, uri protocol.DocumentURI) (Handle, error)
+}
diff --git a/gopls/internal/file/hash.go b/gopls/internal/file/hash.go
new file mode 100644
index 0000000..8c19236
--- /dev/null
+++ b/gopls/internal/file/hash.go
@@ -0,0 +1,40 @@
+// Copyright 2023 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package file
+
+import (
+ "crypto/sha256"
+ "fmt"
+)
+
+// A Hash is a cryptographic digest of the contents of a file.
+// (Although at 32B it is larger than a 16B string header, it is smaller
+// and has better locality than the string header + 64B of hex digits.)
+type Hash [sha256.Size]byte
+
+// HashOf returns the hash of some data.
+func HashOf(data []byte) Hash {
+ return Hash(sha256.Sum256(data))
+}
+
+// Hashf returns the hash of a printf-formatted string.
+func Hashf(format string, args ...interface{}) Hash {
+ // Although this looks alloc-heavy, it is faster than using
+ // Fprintf on sha256.New() because the allocations don't escape.
+ return HashOf([]byte(fmt.Sprintf(format, args...)))
+}
+
+// String returns the digest as a string of hex digits.
+func (h Hash) String() string {
+ return fmt.Sprintf("%64x", [sha256.Size]byte(h))
+}
+
+// XORWith updates *h to *h XOR h2.
+func (h *Hash) XORWith(h2 Hash) {
+ // Small enough that we don't need crypto/subtle.XORBytes.
+ for i := range h {
+ h[i] ^= h2[i]
+ }
+}
diff --git a/gopls/internal/file/kind.go b/gopls/internal/file/kind.go
new file mode 100644
index 0000000..e1902e7
--- /dev/null
+++ b/gopls/internal/file/kind.go
@@ -0,0 +1,64 @@
+// Copyright 2023 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package file
+
+import "fmt"
+
+// Kind describes the kind of the file in question.
+// It can be one of Go,mod, Sum, or Tmpl.
+type Kind int
+
+const (
+ // UnknownKind is a file type we don't know about.
+ UnknownKind = Kind(iota)
+
+ // Go is a Go source file.
+ Go
+ // Mod is a go.mod file.
+ Mod
+ // Sum is a go.sum file.
+ Sum
+ // Tmpl is a template file.
+ Tmpl
+ // Work is a go.work file.
+ Work
+)
+
+func (k Kind) String() string {
+ switch k {
+ case Go:
+ return "go"
+ case Mod:
+ return "go.mod"
+ case Sum:
+ return "go.sum"
+ case Tmpl:
+ return "tmpl"
+ case Work:
+ return "go.work"
+ default:
+ return fmt.Sprintf("internal error: unknown file kind %d", k)
+ }
+}
+
+// KindForLang returns the file kind associated with the given language ID
+// (from protocol.TextDocumentItem.LanguageID), or UnknownKind if the language
+// ID is not recognized.
+func KindForLang(langID string) Kind {
+ switch langID {
+ case "go":
+ return Go
+ case "go.mod":
+ return Mod
+ case "go.sum":
+ return Sum
+ case "tmpl", "gotmpl":
+ return Tmpl
+ case "go.work":
+ return Work
+ default:
+ return UnknownKind
+ }
+}
diff --git a/gopls/internal/file/modification.go b/gopls/internal/file/modification.go
new file mode 100644
index 0000000..97313dd
--- /dev/null
+++ b/gopls/internal/file/modification.go
@@ -0,0 +1,57 @@
+// Copyright 2023 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package file
+
+import "golang.org/x/tools/gopls/internal/lsp/protocol"
+
+// Modification represents a modification to a file.
+type Modification struct {
+ URI protocol.DocumentURI
+ Action Action
+
+ // OnDisk is true if a watched file is changed on disk.
+ // If true, Version will be -1 and Text will be nil.
+ OnDisk bool
+
+ // Version will be -1 and Text will be nil when they are not supplied,
+ // specifically on textDocument/didClose and for on-disk changes.
+ Version int32
+ Text []byte
+
+ // LanguageID is only sent from the language client on textDocument/didOpen.
+ LanguageID string
+}
+
+// An Action is a type of file state change.
+type Action int
+
+const (
+ UnknownAction = Action(iota)
+ Open
+ Change
+ Close
+ Save
+ Create
+ Delete
+)
+
+func (a Action) String() string {
+ switch a {
+ case Open:
+ return "Open"
+ case Change:
+ return "Change"
+ case Close:
+ return "Close"
+ case Save:
+ return "Save"
+ case Create:
+ return "Create"
+ case Delete:
+ return "Delete"
+ default:
+ return "Unknown"
+ }
+}
diff --git a/gopls/internal/lsp/cache/analysis.go b/gopls/internal/lsp/cache/analysis.go
index a937b08..684b912 100644
--- a/gopls/internal/lsp/cache/analysis.go
+++ b/gopls/internal/lsp/cache/analysis.go
@@ -32,6 +32,7 @@
"golang.org/x/sync/errgroup"
"golang.org/x/tools/go/analysis"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/filecache"
"golang.org/x/tools/gopls/internal/lsp/frob"
"golang.org/x/tools/gopls/internal/lsp/progress"
@@ -154,7 +155,7 @@
// Steps:
// - define a narrow driver.Snapshot interface with only these methods:
// Metadata(PackageID) source.Metadata
-// ReadFile(Context, URI) (source.FileHandle, error)
+// ReadFile(Context, URI) (file.Handle, error)
// View() *View // for Options
// - share cache.{goVersionRx,parseGoImpl}
@@ -289,7 +290,7 @@
// Load the contents of each compiled Go file through
// the snapshot's cache. (These are all cache hits as
// files are pre-loaded following packages.Load)
- an.files = make([]source.FileHandle, len(m.CompiledGoFiles))
+ an.files = make([]file.Handle, len(m.CompiledGoFiles))
for i, uri := range m.CompiledGoFiles {
fh, err := snapshot.ReadFile(ctx, uri)
if err != nil {
@@ -503,7 +504,7 @@
type analysisNode struct {
fset *token.FileSet // file set shared by entire batch (DAG)
m *source.Metadata // metadata for this package
- files []source.FileHandle // contents of CompiledGoFiles
+ files []file.Handle // contents of CompiledGoFiles
analyzers []*analysis.Analyzer // set of analyzers to run
preds []*analysisNode // graph edges:
succs map[PackageID]*analysisNode // (preds -> self -> succs)
@@ -578,10 +579,10 @@
// analyzeSummary is a gob-serializable summary of successfully
// applying a list of analyzers to a package.
type analyzeSummary struct {
- Export []byte // encoded types of package
- DeepExportHash source.Hash // hash of reflexive transitive closure of export data
- Compiles bool // transitively free of list/parse/type errors
- Actions actionMap // maps analyzer stablename to analysis results (*actionSummary)
+ Export []byte // encoded types of package
+ DeepExportHash file.Hash // hash of reflexive transitive closure of export data
+ Compiles bool // transitively free of list/parse/type errors
+ Actions actionMap // maps analyzer stablename to analysis results (*actionSummary)
}
// actionMap defines a stable Gob encoding for a map.
@@ -626,8 +627,8 @@
// actionSummary is a gob-serializable summary of one possibly failed analysis action.
// If Err is non-empty, the other fields are undefined.
type actionSummary struct {
- Facts []byte // the encoded facts.Set
- FactsHash source.Hash // hash(Facts)
+ Facts []byte // the encoded facts.Set
+ FactsHash file.Hash // hash(Facts)
Diagnostics []gobDiagnostic
Err string // "" => success
}
@@ -735,7 +736,7 @@
// file names and contents
fmt.Fprintf(hasher, "files: %d\n", len(an.files))
for _, fh := range an.files {
- fmt.Fprintln(hasher, fh.FileIdentity())
+ fmt.Fprintln(hasher, fh.Identity())
}
// vdeps, in PackageID order
@@ -1103,8 +1104,8 @@
types *types.Package
compiles bool // package is transitively free of list/parse/type errors
factsDecoder *facts.Decoder
- export []byte // encoding of types.Package
- deepExportHash source.Hash // reflexive transitive hash of export data
+ export []byte // encoding of types.Package
+ deepExportHash file.Hash // reflexive transitive hash of export data
typesInfo *types.Info
typeErrors []types.Error
typesSizes types.Sizes
@@ -1368,7 +1369,7 @@
return result, &actionSummary{
Diagnostics: diagnostics,
Facts: factsdata,
- FactsHash: source.HashOf(factsdata),
+ FactsHash: file.HashOf(factsdata),
}, nil
}
diff --git a/gopls/internal/lsp/cache/check.go b/gopls/internal/lsp/cache/check.go
index 7ab16ba..ab9a0d2 100644
--- a/gopls/internal/lsp/cache/check.go
+++ b/gopls/internal/lsp/cache/check.go
@@ -23,6 +23,7 @@
"golang.org/x/sync/errgroup"
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/immutable"
"golang.org/x/tools/gopls/internal/lsp/filecache"
"golang.org/x/tools/gopls/internal/lsp/protocol"
@@ -264,7 +265,7 @@
// common case nothing has changed.
unchanged := lastImportGraph != nil && len(handles) == len(lastImportGraph.depKeys)
var ids []PackageID
- depKeys := make(map[PackageID]source.Hash)
+ depKeys := make(map[PackageID]file.Hash)
for id, ph := range handles {
ids = append(ids, id)
depKeys[id] = ph.key
@@ -300,9 +301,9 @@
// An importGraph holds selected results of a type-checking pass, to be re-used
// by subsequent snapshots.
type importGraph struct {
- fset *token.FileSet // fileset used for type checking imports
- depKeys map[PackageID]source.Hash // hash of direct dependencies for this graph
- imports map[PackageID]pkgOrErr // results of type checking
+ fset *token.FileSet // fileset used for type checking imports
+ depKeys map[PackageID]file.Hash // hash of direct dependencies for this graph
+ imports map[PackageID]pkgOrErr // results of type checking
}
// Package visiting functions used by forEachPackage; see the documentation of
@@ -786,7 +787,7 @@
// dependencies.
localInputs typeCheckInputs
// localKey is a hash of localInputs.
- localKey source.Hash
+ localKey file.Hash
// refs is the result of syntactic dependency analysis produced by the
// typerefs package.
refs map[string][]typerefs.Symbol
@@ -800,12 +801,12 @@
// depKeys records the key of each dependency that was used to calculate the
// key above. If the handle becomes invalid, we must re-check that each still
// matches.
- depKeys map[PackageID]source.Hash
+ depKeys map[PackageID]file.Hash
// key is the hashed key for the package.
//
// It includes the all bits of the transitive closure of
// dependencies's sources.
- key source.Hash
+ key file.Hash
}
// clone returns a copy of the receiver with the validated bit set to the
@@ -1154,7 +1155,7 @@
}
// Deps have changed, so we must re-evaluate the key.
- n.ph.depKeys = make(map[PackageID]source.Hash)
+ n.ph.depKeys = make(map[PackageID]file.Hash)
// See the typerefs package: the reachable set of packages is defined to be
// the set of packages containing syntax that is reachable through the
@@ -1209,7 +1210,7 @@
// typerefs returns typerefs for the package described by m and cgfs, after
// either computing it or loading it from the file cache.
-func (s *snapshot) typerefs(ctx context.Context, m *source.Metadata, cgfs []source.FileHandle) (map[string][]typerefs.Symbol, error) {
+func (s *snapshot) typerefs(ctx context.Context, m *source.Metadata, cgfs []file.Handle) (map[string][]typerefs.Symbol, error) {
imports := make(map[ImportPath]*source.Metadata)
for impPath, id := range m.DepsByImpPath {
if id != "" {
@@ -1233,7 +1234,7 @@
// typerefData retrieves encoded typeref data from the filecache, or computes it on
// a cache miss.
-func (s *snapshot) typerefData(ctx context.Context, id PackageID, imports map[ImportPath]*source.Metadata, cgfs []source.FileHandle) ([]byte, error) {
+func (s *snapshot) typerefData(ctx context.Context, id PackageID, imports map[ImportPath]*source.Metadata, cgfs []file.Handle) ([]byte, error) {
key := typerefsKey(id, imports, cgfs)
if data, err := filecache.Get(typerefsKind, key); err == nil {
return data, nil
@@ -1259,7 +1260,7 @@
// typerefsKey produces a key for the reference information produced by the
// typerefs package.
-func typerefsKey(id PackageID, imports map[ImportPath]*source.Metadata, compiledGoFiles []source.FileHandle) source.Hash {
+func typerefsKey(id PackageID, imports map[ImportPath]*source.Metadata, compiledGoFiles []file.Handle) file.Hash {
hasher := sha256.New()
fmt.Fprintf(hasher, "typerefs: %s\n", id)
@@ -1278,7 +1279,7 @@
fmt.Fprintf(hasher, "compiledGoFiles: %d\n", len(compiledGoFiles))
for _, fh := range compiledGoFiles {
- fmt.Fprintln(hasher, fh.FileIdentity())
+ fmt.Fprintln(hasher, fh.Identity())
}
var hash [sha256.Size]byte
@@ -1297,7 +1298,7 @@
// Used for type checking:
pkgPath PackagePath
name PackageName
- goFiles, compiledGoFiles []source.FileHandle
+ goFiles, compiledGoFiles []file.Handle
sizes types.Sizes
depsByImpPath map[ImportPath]PackageID
goVersion string // packages.Module.GoVersion, e.g. "1.18"
@@ -1351,8 +1352,8 @@
// readFiles reads the content of each file URL from the source
// (e.g. snapshot or cache).
-func readFiles(ctx context.Context, fs source.FileSource, uris []protocol.DocumentURI) (_ []source.FileHandle, err error) {
- fhs := make([]source.FileHandle, len(uris))
+func readFiles(ctx context.Context, fs file.Source, uris []protocol.DocumentURI) (_ []file.Handle, err error) {
+ fhs := make([]file.Handle, len(uris))
for i, uri := range uris {
fhs[i], err = fs.ReadFile(ctx, uri)
if err != nil {
@@ -1364,7 +1365,7 @@
// localPackageKey returns a key for local inputs into type-checking, excluding
// dependency information: files, metadata, and configuration.
-func localPackageKey(inputs typeCheckInputs) source.Hash {
+func localPackageKey(inputs typeCheckInputs) file.Hash {
hasher := sha256.New()
// In principle, a key must be the hash of an
@@ -1390,11 +1391,11 @@
// file names and contents
fmt.Fprintf(hasher, "compiledGoFiles: %d\n", len(inputs.compiledGoFiles))
for _, fh := range inputs.compiledGoFiles {
- fmt.Fprintln(hasher, fh.FileIdentity())
+ fmt.Fprintln(hasher, fh.Identity())
}
fmt.Fprintf(hasher, "goFiles: %d\n", len(inputs.goFiles))
for _, fh := range inputs.goFiles {
- fmt.Fprintln(hasher, fh.FileIdentity())
+ fmt.Fprintln(hasher, fh.Identity())
}
// types sizes
@@ -1636,7 +1637,7 @@
// of pkg, or to 'requires' declarations in the package's go.mod file.
//
// TODO(rfindley): move this to load.go
-func depsErrors(ctx context.Context, m *source.Metadata, meta *metadataGraph, fs source.FileSource, workspacePackages immutable.Map[PackageID, PackagePath]) ([]*source.Diagnostic, error) {
+func depsErrors(ctx context.Context, m *source.Metadata, meta *metadataGraph, fs file.Source, workspacePackages immutable.Map[PackageID, PackagePath]) ([]*source.Diagnostic, error) {
// Select packages that can't be found, and were imported in non-workspace packages.
// Workspace packages already show their own errors.
var relevantErrors []*packagesinternal.PackageError
diff --git a/gopls/internal/lsp/cache/errors.go b/gopls/internal/lsp/cache/errors.go
index 75d8a78..fef123b 100644
--- a/gopls/internal/lsp/cache/errors.go
+++ b/gopls/internal/lsp/cache/errors.go
@@ -23,6 +23,7 @@
"golang.org/x/tools/go/packages"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
@@ -35,7 +36,7 @@
// diagnostic, using the provided metadata and filesource.
//
// The slice of diagnostics may be empty.
-func goPackagesErrorDiagnostics(ctx context.Context, e packages.Error, m *source.Metadata, fs source.FileSource) ([]*source.Diagnostic, error) {
+func goPackagesErrorDiagnostics(ctx context.Context, e packages.Error, m *source.Metadata, fs file.Source) ([]*source.Diagnostic, error) {
if diag, err := parseGoListImportCycleError(ctx, e, m, fs); err != nil {
return nil, err
} else if diag != nil {
@@ -510,7 +511,7 @@
// an import cycle, returning a diagnostic if successful.
//
// If the error is not detected as an import cycle error, it returns nil, nil.
-func parseGoListImportCycleError(ctx context.Context, e packages.Error, m *source.Metadata, fs source.FileSource) (*source.Diagnostic, error) {
+func parseGoListImportCycleError(ctx context.Context, e packages.Error, m *source.Metadata, fs file.Source) (*source.Diagnostic, error) {
re := regexp.MustCompile(`(.*): import stack: \[(.+)\]`)
matches := re.FindStringSubmatch(strings.TrimSpace(e.Msg))
if len(matches) < 3 {
@@ -559,7 +560,7 @@
// It returns an error if the file could not be read.
//
// TODO(rfindley): eliminate this helper.
-func parseGoURI(ctx context.Context, fs source.FileSource, uri protocol.DocumentURI, mode parser.Mode) (*source.ParsedGoFile, error) {
+func parseGoURI(ctx context.Context, fs file.Source, uri protocol.DocumentURI, mode parser.Mode) (*source.ParsedGoFile, error) {
fh, err := fs.ReadFile(ctx, uri)
if err != nil {
return nil, err
@@ -571,7 +572,7 @@
// source fs.
//
// It returns an error if the file could not be read.
-func parseModURI(ctx context.Context, fs source.FileSource, uri protocol.DocumentURI) (*source.ParsedModule, error) {
+func parseModURI(ctx context.Context, fs file.Source, uri protocol.DocumentURI) (*source.ParsedModule, error) {
fh, err := fs.ReadFile(ctx, uri)
if err != nil {
return nil, err
diff --git a/gopls/internal/lsp/cache/filemap.go b/gopls/internal/lsp/cache/filemap.go
index dbdb249..f3525fe 100644
--- a/gopls/internal/lsp/cache/filemap.go
+++ b/gopls/internal/lsp/cache/filemap.go
@@ -7,8 +7,8 @@
import (
"path/filepath"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
- "golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/persistent"
)
@@ -16,14 +16,14 @@
// It keeps track of overlays as well as directories containing any observed
// file.
type fileMap struct {
- files *persistent.Map[protocol.DocumentURI, source.FileHandle]
+ files *persistent.Map[protocol.DocumentURI, file.Handle]
overlays *persistent.Map[protocol.DocumentURI, *Overlay] // the subset of files that are overlays
dirs *persistent.Set[string] // all dirs containing files; if nil, dirs have not been initialized
}
func newFileMap() *fileMap {
return &fileMap{
- files: new(persistent.Map[protocol.DocumentURI, source.FileHandle]),
+ files: new(persistent.Map[protocol.DocumentURI, file.Handle]),
overlays: new(persistent.Map[protocol.DocumentURI, *Overlay]),
dirs: new(persistent.Set[string]),
}
@@ -31,7 +31,7 @@
// Clone creates a copy of the fileMap, incorporating the changes specified by
// the changes map.
-func (m *fileMap) Clone(changes map[protocol.DocumentURI]source.FileHandle) *fileMap {
+func (m *fileMap) Clone(changes map[protocol.DocumentURI]file.Handle) *fileMap {
m2 := &fileMap{
files: m.files.Clone(),
overlays: m.overlays.Clone(),
@@ -73,18 +73,18 @@
// Get returns the file handle mapped by the given key, or (nil, false) if the
// key is not present.
-func (m *fileMap) Get(key protocol.DocumentURI) (source.FileHandle, bool) {
+func (m *fileMap) Get(key protocol.DocumentURI) (file.Handle, bool) {
return m.files.Get(key)
}
// Range calls f for each (uri, fh) in the map.
-func (m *fileMap) Range(f func(uri protocol.DocumentURI, fh source.FileHandle)) {
+func (m *fileMap) Range(f func(uri protocol.DocumentURI, fh file.Handle)) {
m.files.Range(f)
}
// Set stores the given file handle for key, updating overlays and directories
// accordingly.
-func (m *fileMap) Set(key protocol.DocumentURI, fh source.FileHandle) {
+func (m *fileMap) Set(key protocol.DocumentURI, fh file.Handle) {
m.files.Set(key, fh, nil)
// update overlays
@@ -143,7 +143,7 @@
func (m *fileMap) Dirs() *persistent.Set[string] {
if m.dirs == nil {
m.dirs = new(persistent.Set[string])
- m.files.Range(func(u protocol.DocumentURI, _ source.FileHandle) {
+ m.files.Range(func(u protocol.DocumentURI, _ file.Handle) {
m.addDirs(u)
})
}
diff --git a/gopls/internal/lsp/cache/filemap_test.go b/gopls/internal/lsp/cache/filemap_test.go
index 24b9495..d829d24 100644
--- a/gopls/internal/lsp/cache/filemap_test.go
+++ b/gopls/internal/lsp/cache/filemap_test.go
@@ -10,8 +10,8 @@
"testing"
"github.com/google/go-cmp/cmp"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
- "golang.org/x/tools/gopls/internal/lsp/source"
)
func TestFileMap(t *testing.T) {
@@ -70,7 +70,7 @@
uri := protocol.URIFromPath(filepath.FromSlash(op.path))
switch op.op {
case set:
- var fh source.FileHandle
+ var fh file.Handle
if op.overlay {
fh = &Overlay{uri: uri}
} else {
@@ -83,7 +83,7 @@
}
var gotFiles []string
- m.Range(func(uri protocol.DocumentURI, _ source.FileHandle) {
+ m.Range(func(uri protocol.DocumentURI, _ file.Handle) {
gotFiles = append(gotFiles, normalize(uri.Path()))
})
sort.Strings(gotFiles)
diff --git a/gopls/internal/lsp/cache/fs_memoized.go b/gopls/internal/lsp/cache/fs_memoized.go
index d5a0b7a..3ca0473 100644
--- a/gopls/internal/lsp/cache/fs_memoized.go
+++ b/gopls/internal/lsp/cache/fs_memoized.go
@@ -10,8 +10,8 @@
"sync"
"time"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
- "golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
"golang.org/x/tools/internal/event/tag"
"golang.org/x/tools/internal/robustio"
@@ -33,14 +33,14 @@
uri protocol.DocumentURI
modTime time.Time
content []byte
- hash source.Hash
+ hash file.Hash
err error
}
func (h *DiskFile) URI() protocol.DocumentURI { return h.uri }
-func (h *DiskFile) FileIdentity() source.FileIdentity {
- return source.FileIdentity{
+func (h *DiskFile) Identity() file.Identity {
+ return file.Identity{
URI: h.uri,
Hash: h.hash,
}
@@ -51,7 +51,7 @@
func (h *DiskFile) Content() ([]byte, error) { return h.content, h.err }
// ReadFile stats and (maybe) reads the file, updates the cache, and returns it.
-func (fs *memoizedFS) ReadFile(ctx context.Context, uri protocol.DocumentURI) (source.FileHandle, error) {
+func (fs *memoizedFS) ReadFile(ctx context.Context, uri protocol.DocumentURI) (file.Handle, error) {
id, mtime, err := robustio.GetFileID(uri.Path())
if err != nil {
// file does not exist
@@ -161,7 +161,7 @@
modTime: mtime,
uri: uri,
content: content,
- hash: source.HashOf(content),
+ hash: file.HashOf(content),
err: err,
}, nil
}
diff --git a/gopls/internal/lsp/cache/fs_overlay.go b/gopls/internal/lsp/cache/fs_overlay.go
index 5fc8f4d..8abfbc9 100644
--- a/gopls/internal/lsp/cache/fs_overlay.go
+++ b/gopls/internal/lsp/cache/fs_overlay.go
@@ -8,20 +8,20 @@
"context"
"sync"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
- "golang.org/x/tools/gopls/internal/lsp/source"
)
-// An overlayFS is a source.FileSource that keeps track of overlays on top of a
+// An overlayFS is a file.Source that keeps track of overlays on top of a
// delegate FileSource.
type overlayFS struct {
- delegate source.FileSource
+ delegate file.Source
mu sync.Mutex
overlays map[protocol.DocumentURI]*Overlay
}
-func newOverlayFS(delegate source.FileSource) *overlayFS {
+func newOverlayFS(delegate file.Source) *overlayFS {
return &overlayFS{
delegate: delegate,
overlays: make(map[protocol.DocumentURI]*Overlay),
@@ -39,7 +39,7 @@
return overlays
}
-func (fs *overlayFS) ReadFile(ctx context.Context, uri protocol.DocumentURI) (source.FileHandle, error) {
+func (fs *overlayFS) ReadFile(ctx context.Context, uri protocol.DocumentURI) (file.Handle, error) {
fs.mu.Lock()
overlay, ok := fs.overlays[uri]
fs.mu.Unlock()
@@ -50,13 +50,13 @@
}
// An Overlay is a file open in the editor. It may have unsaved edits.
-// It implements the source.FileHandle interface.
+// It implements the file.Handle interface.
type Overlay struct {
uri protocol.DocumentURI
content []byte
- hash source.Hash
+ hash file.Hash
version int32
- kind source.FileKind
+ kind file.Kind
// saved is true if a file matches the state on disk,
// and therefore does not need to be part of the overlay sent to go/packages.
@@ -65,8 +65,8 @@
func (o *Overlay) URI() protocol.DocumentURI { return o.uri }
-func (o *Overlay) FileIdentity() source.FileIdentity {
- return source.FileIdentity{
+func (o *Overlay) Identity() file.Identity {
+ return file.Identity{
URI: o.uri,
Hash: o.hash,
}
@@ -75,4 +75,4 @@
func (o *Overlay) Content() ([]byte, error) { return o.content, nil }
func (o *Overlay) Version() int32 { return o.version }
func (o *Overlay) SameContentsOnDisk() bool { return o.saved }
-func (o *Overlay) Kind() source.FileKind { return o.kind }
+func (o *Overlay) Kind() file.Kind { return o.kind }
diff --git a/gopls/internal/lsp/cache/imports.go b/gopls/internal/lsp/cache/imports.go
index 3ed513d..2bd7477 100644
--- a/gopls/internal/lsp/cache/imports.go
+++ b/gopls/internal/lsp/cache/imports.go
@@ -12,6 +12,7 @@
"sync"
"time"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
"golang.org/x/tools/internal/event/keys"
@@ -26,7 +27,7 @@
processEnv *imports.ProcessEnv
cacheRefreshDuration time.Duration
cacheRefreshTimer *time.Timer
- cachedModFileHash source.Hash
+ cachedModFileHash file.Hash
cachedBuildFlags []string
cachedDirectoryFilters []string
}
@@ -43,13 +44,13 @@
// the mod file shouldn't be changing while people are autocompleting.
//
// TODO(rfindley): consider instead hashing on-disk modfiles here.
- var modFileHash source.Hash
+ var modFileHash file.Hash
for m := range snapshot.workspaceModFiles {
fh, err := snapshot.ReadFile(ctx, m)
if err != nil {
return err
}
- modFileHash.XORWith(fh.FileIdentity().Hash)
+ modFileHash.XORWith(fh.Identity().Hash)
}
// view.goEnv is immutable -- changes make a new view. Options can change.
diff --git a/gopls/internal/lsp/cache/load.go b/gopls/internal/lsp/cache/load.go
index 00538bb..538f498 100644
--- a/gopls/internal/lsp/cache/load.go
+++ b/gopls/internal/lsp/cache/load.go
@@ -17,6 +17,7 @@
"golang.org/x/tools/go/packages"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/immutable"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -67,7 +68,7 @@
panic(fmt.Sprintf("internal error: load called with multiple scopes when a file scope is present (file: %s)", uri))
}
fh := s.FindFile(uri)
- if fh == nil || s.FileKind(fh) != source.Go {
+ if fh == nil || s.FileKind(fh) != file.Go {
// Don't try to load a file that doesn't exist, or isn't a go file.
continue
}
@@ -360,14 +361,14 @@
// Place the diagnostics on the package or module declarations.
var rng protocol.Range
switch s.FileKind(fh) {
- case source.Go:
+ case file.Go:
if pgf, err := s.ParseGo(ctx, fh, source.ParseHeader); err == nil {
// Check that we have a valid `package foo` range to use for positioning the error.
if pgf.File.Package.IsValid() && pgf.File.Name != nil && pgf.File.Name.End().IsValid() {
rng, _ = pgf.PosRange(pgf.File.Package, pgf.File.Name.End())
}
}
- case source.Mod:
+ case file.Mod:
if pmf, err := s.ParseMod(ctx, fh); err == nil {
if mod := pmf.File.Module; mod != nil && mod.Syntax != nil {
rng, _ = pmf.Mapper.OffsetRange(mod.Syntax.Start.Byte, mod.Syntax.End.Byte)
@@ -557,7 +558,7 @@
// computeLoadDiagnostics computes and sets m.Diagnostics for the given metadata m.
//
// It should only be called during metadata construction in snapshot.load.
-func computeLoadDiagnostics(ctx context.Context, m *source.Metadata, meta *metadataGraph, fs source.FileSource, workspacePackages immutable.Map[PackageID, PackagePath]) {
+func computeLoadDiagnostics(ctx context.Context, m *source.Metadata, meta *metadataGraph, fs file.Source, workspacePackages immutable.Map[PackageID, PackagePath]) {
for _, packagesErr := range m.Errors {
// Filter out parse errors from go list. We'll get them when we
// actually parse, and buggy overlay support may generate spurious
diff --git a/gopls/internal/lsp/cache/mod.go b/gopls/internal/lsp/cache/mod.go
index 8f8ebc7..36206ed 100644
--- a/gopls/internal/lsp/cache/mod.go
+++ b/gopls/internal/lsp/cache/mod.go
@@ -14,6 +14,7 @@
"golang.org/x/mod/modfile"
"golang.org/x/mod/module"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -24,14 +25,14 @@
)
// ParseMod parses a go.mod file, using a cache. It may return partial results and an error.
-func (s *snapshot) ParseMod(ctx context.Context, fh source.FileHandle) (*source.ParsedModule, error) {
+func (s *snapshot) ParseMod(ctx context.Context, fh file.Handle) (*source.ParsedModule, error) {
uri := fh.URI()
s.mu.Lock()
entry, hit := s.parseModHandles.Get(uri)
s.mu.Unlock()
- type parseModKey source.FileIdentity
+ type parseModKey file.Identity
type parseModResult struct {
parsed *source.ParsedModule
err error
@@ -39,7 +40,7 @@
// cache miss?
if !hit {
- promise, release := s.store.Promise(parseModKey(fh.FileIdentity()), func(ctx context.Context, _ interface{}) interface{} {
+ promise, release := s.store.Promise(parseModKey(fh.Identity()), func(ctx context.Context, _ interface{}) interface{} {
parsed, err := parseModImpl(ctx, fh)
return parseModResult{parsed, err}
})
@@ -61,7 +62,7 @@
// parseModImpl parses the go.mod file whose name and contents are in fh.
// It may return partial results and an error.
-func parseModImpl(ctx context.Context, fh source.FileHandle) (*source.ParsedModule, error) {
+func parseModImpl(ctx context.Context, fh file.Handle) (*source.ParsedModule, error) {
_, done := event.Start(ctx, "cache.ParseMod", tag.URI.Of(fh.URI()))
defer done()
@@ -102,14 +103,14 @@
// ParseWork parses a go.work file, using a cache. It may return partial results and an error.
// TODO(adonovan): move to new work.go file.
-func (s *snapshot) ParseWork(ctx context.Context, fh source.FileHandle) (*source.ParsedWorkFile, error) {
+func (s *snapshot) ParseWork(ctx context.Context, fh file.Handle) (*source.ParsedWorkFile, error) {
uri := fh.URI()
s.mu.Lock()
entry, hit := s.parseWorkHandles.Get(uri)
s.mu.Unlock()
- type parseWorkKey source.FileIdentity
+ type parseWorkKey file.Identity
type parseWorkResult struct {
parsed *source.ParsedWorkFile
err error
@@ -117,7 +118,7 @@
// cache miss?
if !hit {
- handle, release := s.store.Promise(parseWorkKey(fh.FileIdentity()), func(ctx context.Context, _ interface{}) interface{} {
+ handle, release := s.store.Promise(parseWorkKey(fh.Identity()), func(ctx context.Context, _ interface{}) interface{} {
parsed, err := parseWorkImpl(ctx, fh)
return parseWorkResult{parsed, err}
})
@@ -138,7 +139,7 @@
}
// parseWorkImpl parses a go.work file. It may return partial results and an error.
-func parseWorkImpl(ctx context.Context, fh source.FileHandle) (*source.ParsedWorkFile, error) {
+func parseWorkImpl(ctx context.Context, fh file.Handle) (*source.ParsedWorkFile, error) {
_, done := event.Start(ctx, "cache.ParseWork", tag.URI.Of(fh.URI()))
defer done()
@@ -187,7 +188,7 @@
// TODO(rfindley): but that's not right. Changes to sum files should
// invalidate content, even if it's nonexistent content.
sumURI := protocol.URIFromPath(sumFilename(modURI))
- var sumFH source.FileHandle = s.FindFile(sumURI)
+ var sumFH file.Handle = s.FindFile(sumURI)
if sumFH == nil {
var err error
sumFH, err = s.view.fs.ReadFile(ctx, sumURI)
@@ -209,10 +210,10 @@
// ModWhy returns the "go mod why" result for each module named in a
// require statement in the go.mod file.
// TODO(adonovan): move to new mod_why.go file.
-func (s *snapshot) ModWhy(ctx context.Context, fh source.FileHandle) (map[string]string, error) {
+func (s *snapshot) ModWhy(ctx context.Context, fh file.Handle) (map[string]string, error) {
uri := fh.URI()
- if s.FileKind(fh) != source.Mod {
+ if s.FileKind(fh) != file.Mod {
return nil, fmt.Errorf("%s is not a go.mod file", uri)
}
@@ -248,7 +249,7 @@
}
// modWhyImpl returns the result of "go mod why -m" on the specified go.mod file.
-func modWhyImpl(ctx context.Context, snapshot *snapshot, fh source.FileHandle) (map[string]string, error) {
+func modWhyImpl(ctx context.Context, snapshot *snapshot, fh file.Handle) (map[string]string, error) {
ctx, done := event.Start(ctx, "cache.ModWhy", tag.URI.Of(fh.URI()))
defer done()
diff --git a/gopls/internal/lsp/cache/mod_tidy.go b/gopls/internal/lsp/cache/mod_tidy.go
index ffbee78..896fd05 100644
--- a/gopls/internal/lsp/cache/mod_tidy.go
+++ b/gopls/internal/lsp/cache/mod_tidy.go
@@ -15,6 +15,7 @@
"strings"
"golang.org/x/mod/modfile"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -483,7 +484,7 @@
// CompiledGoFiles, after cgo processing.)
//
// TODO(rfindley): this should key off source.ImportPath.
-func parseImports(ctx context.Context, s *snapshot, files []source.FileHandle) (map[string]bool, error) {
+func parseImports(ctx context.Context, s *snapshot, files []file.Handle) (map[string]bool, error) {
pgfs, err := s.view.parseCache.parseFiles(ctx, token.NewFileSet(), source.ParseHeader, false, files...)
if err != nil { // e.g. context cancellation
return nil, err
diff --git a/gopls/internal/lsp/cache/parse.go b/gopls/internal/lsp/cache/parse.go
index 74de9c3..5135581 100644
--- a/gopls/internal/lsp/cache/parse.go
+++ b/gopls/internal/lsp/cache/parse.go
@@ -16,6 +16,7 @@
"reflect"
goplsastutil "golang.org/x/tools/gopls/internal/astutil"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -25,8 +26,8 @@
)
// ParseGo parses the file whose contents are provided by fh, using a cache.
-// The resulting tree may have beeen fixed up.
-func (s *snapshot) ParseGo(ctx context.Context, fh source.FileHandle, mode parser.Mode) (*source.ParsedGoFile, error) {
+// The resulting tree may have been fixed up.
+func (s *snapshot) ParseGo(ctx context.Context, fh file.Handle, mode parser.Mode) (*source.ParsedGoFile, error) {
pgfs, err := s.view.parseCache.parseFiles(ctx, token.NewFileSet(), mode, false, fh)
if err != nil {
return nil, err
@@ -35,7 +36,7 @@
}
// parseGoImpl parses the Go source file whose content is provided by fh.
-func parseGoImpl(ctx context.Context, fset *token.FileSet, fh source.FileHandle, mode parser.Mode, purgeFuncBodies bool) (*source.ParsedGoFile, error) {
+func parseGoImpl(ctx context.Context, fset *token.FileSet, fh file.Handle, mode parser.Mode, purgeFuncBodies bool) (*source.ParsedGoFile, error) {
ext := filepath.Ext(fh.URI().Path())
if ext != ".go" && ext != "" { // files generated by cgo have no extension
return nil, fmt.Errorf("cannot parse non-Go file %s", fh.URI())
diff --git a/gopls/internal/lsp/cache/parse_cache.go b/gopls/internal/lsp/cache/parse_cache.go
index 6afc7a5..669de65 100644
--- a/gopls/internal/lsp/cache/parse_cache.go
+++ b/gopls/internal/lsp/cache/parse_cache.go
@@ -17,6 +17,7 @@
"time"
"golang.org/x/sync/errgroup"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/memoize"
@@ -133,7 +134,7 @@
type parseCacheEntry struct {
key parseKey
- hash source.Hash
+ hash file.Hash
promise *memoize.Promise // memoize.Promise[*source.ParsedGoFile]
atime uint64 // clock time of last access, for use in LRU sorting
walltime time.Time // actual time of last access, for use in time-based eviction; too coarse for LRU on some systems
@@ -146,7 +147,7 @@
// The resulting slice has an entry for every given file handle, though some
// entries may be nil if there was an error reading the file (in which case the
// resulting error will be non-nil).
-func (c *parseCache) startParse(mode parser.Mode, purgeFuncBodies bool, fhs ...source.FileHandle) ([]*memoize.Promise, error) {
+func (c *parseCache) startParse(mode parser.Mode, purgeFuncBodies bool, fhs ...file.Handle) ([]*memoize.Promise, error) {
c.mu.Lock()
defer c.mu.Unlock()
@@ -180,7 +181,7 @@
}
if e, ok := c.m[key]; ok {
- if e.hash == fh.FileIdentity().Hash { // cache hit
+ if e.hash == fh.Identity().Hash { // cache hit
e.atime = c.clock
e.walltime = walltime
heap.Fix(&c.lru, e.lruIndex)
@@ -236,7 +237,7 @@
// add new entry; entries are gc'ed asynchronously
e := &parseCacheEntry{
key: key,
- hash: fh.FileIdentity().Hash,
+ hash: fh.Identity().Hash,
promise: promise,
atime: c.clock,
walltime: walltime,
@@ -316,7 +317,7 @@
//
// If parseFiles returns an error, it still returns a slice,
// but with a nil entry for each file that could not be parsed.
-func (c *parseCache) parseFiles(ctx context.Context, fset *token.FileSet, mode parser.Mode, purgeFuncBodies bool, fhs ...source.FileHandle) ([]*source.ParsedGoFile, error) {
+func (c *parseCache) parseFiles(ctx context.Context, fset *token.FileSet, mode parser.Mode, purgeFuncBodies bool, fhs ...file.Handle) ([]*source.ParsedGoFile, error) {
pgfs := make([]*source.ParsedGoFile, len(fhs))
// Temporary fall-back for 32-bit systems, where reservedForParsing is too
diff --git a/gopls/internal/lsp/cache/parse_cache_test.go b/gopls/internal/lsp/cache/parse_cache_test.go
index 178a1b5..5693972 100644
--- a/gopls/internal/lsp/cache/parse_cache_test.go
+++ b/gopls/internal/lsp/cache/parse_cache_test.go
@@ -12,6 +12,7 @@
"testing"
"time"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
)
@@ -47,7 +48,7 @@
// Fill up the cache with other files, but don't evict the file above.
cache.gcOnce()
- files := []source.FileHandle{fh}
+ files := []file.Handle{fh}
files = append(files, dummyFileHandles(parseCacheMinFiles-1)...)
pgfs3, err := cache.parseFiles(ctx, fset, source.ParseFull, false, files...)
@@ -114,7 +115,7 @@
parsePadding = 0
danglingSelector := []byte("package p\nfunc _() {\n\tx.\n}")
- files := []source.FileHandle{makeFakeFileHandle("file:///bad", danglingSelector)}
+ files := []file.Handle{makeFakeFileHandle("file:///bad", danglingSelector)}
// Parsing should succeed even though we overflow the padding.
cache := newParseCache(0)
@@ -192,8 +193,8 @@
}
}
-func dummyFileHandles(n int) []source.FileHandle {
- var fhs []source.FileHandle
+func dummyFileHandles(n int) []file.Handle {
+ var fhs []file.Handle
for i := 0; i < n; i++ {
uri := protocol.DocumentURI(fmt.Sprintf("file:///_%d", i))
src := []byte(fmt.Sprintf("package p\nvar _ = %d", i))
@@ -206,15 +207,15 @@
return fakeFileHandle{
uri: uri,
data: src,
- hash: source.HashOf(src),
+ hash: file.HashOf(src),
}
}
type fakeFileHandle struct {
- source.FileHandle
+ file.Handle
uri protocol.DocumentURI
data []byte
- hash source.Hash
+ hash file.Hash
}
func (h fakeFileHandle) URI() protocol.DocumentURI {
@@ -225,8 +226,8 @@
return h.data, nil
}
-func (h fakeFileHandle) FileIdentity() source.FileIdentity {
- return source.FileIdentity{
+func (h fakeFileHandle) Identity() file.Identity {
+ return file.Identity{
URI: h.uri,
Hash: h.hash,
}
diff --git a/gopls/internal/lsp/cache/session.go b/gopls/internal/lsp/cache/session.go
index 3e6f3fc..59561bd 100644
--- a/gopls/internal/lsp/cache/session.go
+++ b/gopls/internal/lsp/cache/session.go
@@ -15,6 +15,7 @@
"sync/atomic"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/lsp/source/typerefs"
@@ -388,7 +389,7 @@
// TODO(rfindley): what happens if this function fails? It must leave us in a
// broken state, which we should surface to the user, probably as a request to
// restart gopls.
-func (s *Session) DidModifyFiles(ctx context.Context, changes []source.FileModification) (map[source.Snapshot][]protocol.DocumentURI, func(), error) {
+func (s *Session) DidModifyFiles(ctx context.Context, changes []file.Modification) (map[source.Snapshot][]protocol.DocumentURI, func(), error) {
s.viewMu.Lock()
defer s.viewMu.Unlock()
@@ -417,8 +418,8 @@
if isGoMod(c.URI) || isGoWork(c.URI) {
// Change, InvalidateMetadata, and UnknownFileAction actions do not cause
// us to re-evaluate views.
- redoViews := (c.Action != source.Change &&
- c.Action != source.UnknownFileAction)
+ redoViews := (c.Action != file.Change &&
+ c.Action != file.UnknownAction)
if redoViews {
checkViews = true
@@ -455,7 +456,7 @@
}
// Collect information about views affected by these changes.
- views := make(map[*View]map[protocol.DocumentURI]source.FileHandle)
+ views := make(map[*View]map[protocol.DocumentURI]file.Handle)
affectedViews := map[protocol.DocumentURI][]*View{}
for _, c := range changes {
// Build the list of affected views.
@@ -488,7 +489,7 @@
// Make sure that the file is added to the view's seenFiles set.
view.markKnown(c.URI)
if _, ok := views[view]; !ok {
- views[view] = make(map[protocol.DocumentURI]source.FileHandle)
+ views[view] = make(map[protocol.DocumentURI]file.Handle)
}
views[view][c.URI] = fh
}
@@ -534,7 +535,7 @@
// ExpandModificationsToDirectories returns the set of changes with the
// directory changes removed and expanded to include all of the files in
// the directory.
-func (s *Session) ExpandModificationsToDirectories(ctx context.Context, changes []source.FileModification) []source.FileModification {
+func (s *Session) ExpandModificationsToDirectories(ctx context.Context, changes []file.Modification) []file.Modification {
var snapshots []*snapshot
s.viewMu.Lock()
for _, v := range s.views {
@@ -552,7 +553,7 @@
//
// There may be other files in the directory, but if we haven't read them yet
// we don't need to invalidate them.
- var result []source.FileModification
+ var result []file.Modification
for _, c := range changes {
expanded := make(map[protocol.DocumentURI]bool)
for _, snapshot := range snapshots {
@@ -564,7 +565,7 @@
result = append(result, c)
} else {
for uri := range expanded {
- result = append(result, source.FileModification{
+ result = append(result, file.Modification{
URI: uri,
Action: c.Action,
LanguageID: "",
@@ -579,7 +580,7 @@
// Precondition: caller holds s.viewMu lock.
// TODO(rfindley): move this to fs_overlay.go.
-func (fs *overlayFS) updateOverlays(ctx context.Context, changes []source.FileModification) error {
+func (fs *overlayFS) updateOverlays(ctx context.Context, changes []file.Modification) error {
fs.mu.Lock()
defer fs.mu.Unlock()
@@ -594,10 +595,10 @@
}
// Determine the file kind on open, otherwise, assume it has been cached.
- var kind source.FileKind
+ var kind file.Kind
switch c.Action {
- case source.Open:
- kind = source.FileKindForLang(c.LanguageID)
+ case file.Open:
+ kind = file.KindForLang(c.LanguageID)
default:
if !ok {
return fmt.Errorf("updateOverlays: modifying unopened overlay %v", c.URI)
@@ -606,7 +607,7 @@
}
// Closing a file just deletes its overlay.
- if c.Action == source.Close {
+ if c.Action == file.Close {
delete(fs.overlays, c.URI)
continue
}
@@ -615,7 +616,7 @@
// overlay. Saves and on-disk file changes don't come with the file's
// content.
text := c.Text
- if text == nil && (c.Action == source.Save || c.OnDisk) {
+ if text == nil && (c.Action == file.Save || c.OnDisk) {
if !ok {
return fmt.Errorf("no known content for overlay for %s", c.Action)
}
@@ -623,15 +624,15 @@
}
// On-disk changes don't come with versions.
version := c.Version
- if c.OnDisk || c.Action == source.Save {
+ if c.OnDisk || c.Action == file.Save {
version = o.version
}
- hash := source.HashOf(text)
+ hash := file.HashOf(text)
var sameContentOnDisk bool
switch c.Action {
- case source.Delete:
+ case file.Delete:
// Do nothing. sameContentOnDisk should be false.
- case source.Save:
+ case file.Save:
// Make sure the version and content (if present) is the same.
if false && o.version != version { // Client no longer sends the version
return fmt.Errorf("updateOverlays: saving %s at version %v, currently at %v", c.URI, c.Version, o.version)
@@ -643,7 +644,7 @@
default:
fh := mustReadFile(ctx, fs.delegate, c.URI)
_, readErr := fh.Content()
- sameContentOnDisk = (readErr == nil && fh.FileIdentity().Hash == hash)
+ sameContentOnDisk = (readErr == nil && fh.Identity().Hash == hash)
}
o = &Overlay{
uri: c.URI,
@@ -663,7 +664,7 @@
return nil
}
-func mustReadFile(ctx context.Context, fs source.FileSource, uri protocol.DocumentURI) source.FileHandle {
+func mustReadFile(ctx context.Context, fs file.Source, uri protocol.DocumentURI) file.Handle {
ctx = xcontext.Detach(ctx)
fh, err := fs.ReadFile(ctx, uri)
if err != nil {
@@ -680,11 +681,11 @@
err error
}
-func (b brokenFile) URI() protocol.DocumentURI { return b.uri }
-func (b brokenFile) FileIdentity() source.FileIdentity { return source.FileIdentity{URI: b.uri} }
-func (b brokenFile) SameContentsOnDisk() bool { return false }
-func (b brokenFile) Version() int32 { return 0 }
-func (b brokenFile) Content() ([]byte, error) { return nil, b.err }
+func (b brokenFile) URI() protocol.DocumentURI { return b.uri }
+func (b brokenFile) Identity() file.Identity { return file.Identity{URI: b.uri} }
+func (b brokenFile) SameContentsOnDisk() bool { return false }
+func (b brokenFile) Version() int32 { return 0 }
+func (b brokenFile) Content() ([]byte, error) { return nil, b.err }
// FileWatchingGlobPatterns returns a new set of glob patterns to
// watch every directory known by the view. For views within a module,
diff --git a/gopls/internal/lsp/cache/snapshot.go b/gopls/internal/lsp/cache/snapshot.go
index f09ee49..976efdc 100644
--- a/gopls/internal/lsp/cache/snapshot.go
+++ b/gopls/internal/lsp/cache/snapshot.go
@@ -30,6 +30,7 @@
"golang.org/x/tools/go/packages"
"golang.org/x/tools/go/types/objectpath"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/immutable"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/filecache"
@@ -275,12 +276,12 @@
return s.view
}
-func (s *snapshot) FileKind(fh source.FileHandle) source.FileKind {
+func (s *snapshot) FileKind(fh file.Handle) file.Kind {
// The kind of an unsaved buffer comes from the
// TextDocumentItem.LanguageID field in the didChange event,
// not from the file name. They may differ.
if o, ok := fh.(*Overlay); ok {
- if o.kind != source.UnknownKind {
+ if o.kind != file.UnknownKind {
return o.kind
}
}
@@ -288,22 +289,22 @@
fext := filepath.Ext(fh.URI().Path())
switch fext {
case ".go":
- return source.Go
+ return file.Go
case ".mod":
- return source.Mod
+ return file.Mod
case ".sum":
- return source.Sum
+ return file.Sum
case ".work":
- return source.Work
+ return file.Work
}
exts := s.Options().TemplateExtensions
for _, ext := range exts {
if fext == ext || fext == "."+ext {
- return source.Tmpl
+ return file.Tmpl
}
}
// and now what? This should never happen, but it does for cgo before go1.15
- return source.Go
+ return file.Go
}
func (s *snapshot) Options() *source.Options {
@@ -327,13 +328,13 @@
return gowork
}
-func (s *snapshot) Templates() map[protocol.DocumentURI]source.FileHandle {
+func (s *snapshot) Templates() map[protocol.DocumentURI]file.Handle {
s.mu.Lock()
defer s.mu.Unlock()
- tmpls := map[protocol.DocumentURI]source.FileHandle{}
- s.files.Range(func(k protocol.DocumentURI, fh source.FileHandle) {
- if s.FileKind(fh) == source.Tmpl {
+ tmpls := map[protocol.DocumentURI]file.Handle{}
+ s.files.Range(func(k protocol.DocumentURI, fh file.Handle) {
+ if s.FileKind(fh) == file.Tmpl {
tmpls[k] = fh
}
})
@@ -1047,7 +1048,7 @@
return nil
}
var files []protocol.DocumentURI
- s.files.Range(func(uri protocol.DocumentURI, _ source.FileHandle) {
+ s.files.Range(func(uri protocol.DocumentURI, _ file.Handle) {
if source.InDir(dir, uri.Path()) {
files = append(files, uri)
}
@@ -1170,7 +1171,7 @@
// containing uri, or a parent of that directory.
//
// The given uri must be a file, not a directory.
-func nearestModFile(ctx context.Context, uri protocol.DocumentURI, fs source.FileSource) (protocol.DocumentURI, error) {
+func nearestModFile(ctx context.Context, uri protocol.DocumentURI, fs file.Source) (protocol.DocumentURI, error) {
dir := filepath.Dir(uri.Path())
mod, err := findRootPattern(ctx, dir, "go.mod", fs)
if err != nil {
@@ -1216,7 +1217,7 @@
}
}
-func (s *snapshot) FindFile(uri protocol.DocumentURI) source.FileHandle {
+func (s *snapshot) FindFile(uri protocol.DocumentURI) file.Handle {
s.view.markKnown(uri)
s.mu.Lock()
@@ -1231,7 +1232,7 @@
//
// ReadFile succeeds even if the file does not exist. A non-nil error return
// indicates some type of internal error, for example if ctx is cancelled.
-func (s *snapshot) ReadFile(ctx context.Context, uri protocol.DocumentURI) (source.FileHandle, error) {
+func (s *snapshot) ReadFile(ctx context.Context, uri protocol.DocumentURI) (file.Handle, error) {
s.mu.Lock()
defer s.mu.Unlock()
@@ -1241,7 +1242,7 @@
// preloadFiles delegates to the view FileSource to read the requested uris in
// parallel, without holding the snapshot lock.
func (s *snapshot) preloadFiles(ctx context.Context, uris []protocol.DocumentURI) {
- files := make([]source.FileHandle, len(uris))
+ files := make([]file.Handle, len(uris))
var wg sync.WaitGroup
iolimit := make(chan struct{}, 20) // I/O concurrency limiting semaphore
for i, uri := range uris {
@@ -1274,11 +1275,11 @@
}
}
-// A lockedSnapshot implements the source.FileSource interface while holding
+// A lockedSnapshot implements the file.Source interface while holding
// the lock for the wrapped snapshot.
type lockedSnapshot struct{ wrapped *snapshot }
-func (s lockedSnapshot) ReadFile(ctx context.Context, uri protocol.DocumentURI) (source.FileHandle, error) {
+func (s lockedSnapshot) ReadFile(ctx context.Context, uri protocol.DocumentURI) (file.Handle, error) {
s.wrapped.view.markKnown(uri)
if fh, ok := s.wrapped.files.Get(uri); ok {
return fh, nil
@@ -1524,7 +1525,7 @@
var files []*Overlay
for _, o := range open {
uri := o.URI()
- if s.IsBuiltin(uri) || s.FileKind(o) != source.Go {
+ if s.IsBuiltin(uri) || s.FileKind(o) != file.Go {
continue
}
if len(meta.ids[uri]) == 0 {
@@ -1625,7 +1626,7 @@
searchOverlays:
for _, o := range s.overlays() {
uri := o.URI()
- if s.IsBuiltin(uri) || s.FileKind(o) != source.Go {
+ if s.IsBuiltin(uri) || s.FileKind(o) != file.Go {
continue
}
md, err := s.MetadataForFile(ctx, uri)
@@ -1889,7 +1890,7 @@
// they exist. Importantly, we don't call ReadFile here: consider the case
// where a file is added on disk; we don't want to read the newly added file
// into the old snapshot, as that will break our change detection below.
- oldFiles := make(map[protocol.DocumentURI]source.FileHandle)
+ oldFiles := make(map[protocol.DocumentURI]file.Handle)
for uri := range changedFiles {
if fh, ok := s.files.Get(uri); ok {
oldFiles[uri] = fh
@@ -1900,14 +1901,14 @@
// the old file wasn't saved, or the on-disk contents changed.
//
// oldFH may be nil.
- changedOnDisk := func(oldFH, newFH source.FileHandle) bool {
+ changedOnDisk := func(oldFH, newFH file.Handle) bool {
if !newFH.SameContentsOnDisk() {
return false
}
if oe, ne := (oldFH != nil && fileExists(oldFH)), fileExists(newFH); !oe || !ne {
return oe != ne
}
- return !oldFH.SameContentsOnDisk() || oldFH.FileIdentity() != newFH.FileIdentity()
+ return !oldFH.SameContentsOnDisk() || oldFH.Identity() != newFH.Identity()
}
if workURI, _ := s.view.GOWORK(); workURI != "" {
@@ -2281,7 +2282,7 @@
// accomplishes this by checking to see if the original and current FileHandles
// are both overlays, and if the current FileHandle is saved while the original
// FileHandle was not saved.
-func fileWasSaved(originalFH, currentFH source.FileHandle) bool {
+func fileWasSaved(originalFH, currentFH file.Handle) bool {
c, ok := currentFH.(*Overlay)
if !ok || c == nil {
return true
@@ -2307,14 +2308,14 @@
// changed).
// - importDeleted means that an import has been deleted, or we can't
// determine if an import was deleted due to errors.
-func metadataChanges(ctx context.Context, lockedSnapshot *snapshot, oldFH, newFH source.FileHandle) (invalidate, pkgFileChanged, importDeleted bool) {
+func metadataChanges(ctx context.Context, lockedSnapshot *snapshot, oldFH, newFH file.Handle) (invalidate, pkgFileChanged, importDeleted bool) {
if oe, ne := oldFH != nil && fileExists(oldFH), fileExists(newFH); !oe || !ne { // existential changes
changed := oe != ne
return changed, changed, !ne // we don't know if an import was deleted
}
// If the file hasn't changed, there's no need to reload.
- if oldFH.FileIdentity() == newFH.FileIdentity() {
+ if oldFH.Identity() == newFH.Identity() {
return false, false, false
}
diff --git a/gopls/internal/lsp/cache/symbols.go b/gopls/internal/lsp/cache/symbols.go
index b16c001..605a186 100644
--- a/gopls/internal/lsp/cache/symbols.go
+++ b/gopls/internal/lsp/cache/symbols.go
@@ -12,6 +12,7 @@
"strings"
"golang.org/x/tools/gopls/internal/astutil"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
)
@@ -34,8 +35,8 @@
if err != nil {
return nil, err
}
- type symbolHandleKey source.Hash
- key := symbolHandleKey(fh.FileIdentity().Hash)
+ type symbolHandleKey file.Hash
+ key := symbolHandleKey(fh.Identity().Hash)
promise, release := s.store.Promise(key, func(ctx context.Context, arg interface{}) interface{} {
symbols, err := symbolizeImpl(ctx, arg.(*snapshot), fh)
return symbolizeResult{symbols, err}
@@ -58,7 +59,7 @@
}
// symbolizeImpl reads and parses a file and extracts symbols from it.
-func symbolizeImpl(ctx context.Context, snapshot *snapshot, fh source.FileHandle) ([]source.Symbol, error) {
+func symbolizeImpl(ctx context.Context, snapshot *snapshot, fh file.Handle) ([]source.Symbol, error) {
pgfs, err := snapshot.view.parseCache.parseFiles(ctx, token.NewFileSet(), source.ParseFull, false, fh)
if err != nil {
return nil, err
diff --git a/gopls/internal/lsp/cache/view.go b/gopls/internal/lsp/cache/view.go
index 0c379a1..1023edc 100644
--- a/gopls/internal/lsp/cache/view.go
+++ b/gopls/internal/lsp/cache/view.go
@@ -23,6 +23,7 @@
"golang.org/x/mod/modfile"
"golang.org/x/mod/semver"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/vulncheck"
@@ -350,8 +351,8 @@
// of the given go.mod file. On success, it is the caller's
// responsibility to call the cleanup function when the file is no
// longer needed.
-func tempModFile(modFh source.FileHandle, gosum []byte) (tmpURI protocol.DocumentURI, cleanup func(), err error) {
- filenameHash := source.Hashf("%s", modFh.URI().Path())
+func tempModFile(modFh file.Handle, gosum []byte) (tmpURI protocol.DocumentURI, cleanup func(), err error) {
+ filenameHash := file.Hashf("%s", modFh.URI().Path())
tmpMod, err := os.CreateTemp("", fmt.Sprintf("go.%s.*.mod", filenameHash))
if err != nil {
return "", nil, err
@@ -557,7 +558,7 @@
}
}
-func (v *View) relevantChange(c source.FileModification) bool {
+func (v *View) relevantChange(c file.Modification) bool {
// If the file is known to the view, the change is relevant.
if v.knownFile(c.URI) {
return true
@@ -888,7 +889,7 @@
return v.snapshot, v.snapshot.Acquire()
}
-func getViewDefinition(ctx context.Context, runner *gocommand.Runner, fs source.FileSource, folder *Folder) (*viewDefinition, error) {
+func getViewDefinition(ctx context.Context, runner *gocommand.Runner, fs file.Source, folder *Folder) (*viewDefinition, error) {
if err := checkPathCase(folder.Dir.Path()); err != nil {
return nil, fmt.Errorf("invalid workspace folder path: %w; check that the casing of the configured workspace folder path agrees with the casing reported by the operating system", err)
}
@@ -953,7 +954,7 @@
// 1. if there is a go.mod file in a parent directory, return it
// 2. else, if there is exactly one nested module, return it
// 3. else, return ""
-func findWorkspaceModFile(ctx context.Context, folderURI protocol.DocumentURI, fs source.FileSource, excludePath func(string) bool) (protocol.DocumentURI, error) {
+func findWorkspaceModFile(ctx context.Context, folderURI protocol.DocumentURI, fs file.Source, excludePath func(string) bool) (protocol.DocumentURI, error) {
folder := folderURI.Path()
match, err := findRootPattern(ctx, folder, "go.mod", fs)
if err != nil {
@@ -992,7 +993,7 @@
//
// The resulting string is either the file path of a matching file with the
// given basename, or "" if none was found.
-func findRootPattern(ctx context.Context, dir, basename string, fs source.FileSource) (string, error) {
+func findRootPattern(ctx context.Context, dir, basename string, fs file.Source) (string, error) {
for dir != "" {
target := filepath.Join(dir, basename)
fh, err := fs.ReadFile(ctx, protocol.URIFromPath(target))
diff --git a/gopls/internal/lsp/cache/workspace.go b/gopls/internal/lsp/cache/workspace.go
index 3787ad1..468fd8e 100644
--- a/gopls/internal/lsp/cache/workspace.go
+++ b/gopls/internal/lsp/cache/workspace.go
@@ -13,8 +13,8 @@
"strings"
"golang.org/x/mod/modfile"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
- "golang.org/x/tools/gopls/internal/lsp/source"
)
// TODO(rfindley): now that experimentalWorkspaceModule is gone, this file can
@@ -22,7 +22,7 @@
// computeWorkspaceModFiles computes the set of workspace mod files based on the
// value of go.mod, go.work, and GO111MODULE.
-func computeWorkspaceModFiles(ctx context.Context, gomod, gowork protocol.DocumentURI, go111module go111module, fs source.FileSource) (map[protocol.DocumentURI]struct{}, error) {
+func computeWorkspaceModFiles(ctx context.Context, gomod, gowork protocol.DocumentURI, go111module go111module, fs file.Source) (map[protocol.DocumentURI]struct{}, error) {
if go111module == off {
return nil, nil
}
@@ -70,7 +70,7 @@
// fileExists reports whether the file has a Content (which may be empty).
// An overlay exists even if it is not reflected in the file system.
-func fileExists(fh source.FileHandle) bool {
+func fileExists(fh file.Handle) bool {
_, err := fh.Content()
return err == nil
}
diff --git a/gopls/internal/lsp/call_hierarchy.go b/gopls/internal/lsp/call_hierarchy.go
index d414b08..3a88520 100644
--- a/gopls/internal/lsp/call_hierarchy.go
+++ b/gopls/internal/lsp/call_hierarchy.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
@@ -16,7 +17,7 @@
ctx, done := event.Start(ctx, "lsp.Server.prepareCallHierarchy")
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.Go)
defer release()
if !ok {
return nil, err
@@ -29,7 +30,7 @@
ctx, done := event.Start(ctx, "lsp.Server.incomingCalls")
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.Item.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.Item.URI, file.Go)
defer release()
if !ok {
return nil, err
@@ -42,7 +43,7 @@
ctx, done := event.Start(ctx, "lsp.Server.outgoingCalls")
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.Item.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.Item.URI, file.Go)
defer release()
if !ok {
return nil, err
diff --git a/gopls/internal/lsp/code_action.go b/gopls/internal/lsp/code_action.go
index 8dfe98f..5efb7a4 100644
--- a/gopls/internal/lsp/code_action.go
+++ b/gopls/internal/lsp/code_action.go
@@ -13,6 +13,7 @@
"golang.org/x/tools/go/ast/inspector"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/analysis/fillstruct"
"golang.org/x/tools/gopls/internal/lsp/analysis/infertypeargs"
"golang.org/x/tools/gopls/internal/lsp/analysis/stubmethods"
@@ -29,7 +30,7 @@
ctx, done := event.Start(ctx, "lsp.Server.codeAction")
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
@@ -76,7 +77,7 @@
}
switch kind {
- case source.Mod:
+ case file.Mod:
var actions []protocol.CodeAction
fixes, err := s.codeActionsMatchingDiagnostics(ctx, fh.URI(), snapshot, params.Context.Diagnostics, want)
@@ -108,7 +109,7 @@
return actions, nil
- case source.Go:
+ case file.Go:
diagnostics := params.Context.Diagnostics
// Don't suggest fixes for generated files, since they are generally
@@ -418,7 +419,7 @@
return actions, nil
}
-func refactorRewrite(ctx context.Context, snapshot source.Snapshot, pkg source.Package, pgf *source.ParsedGoFile, fh source.FileHandle, rng protocol.Range) (_ []protocol.CodeAction, rerr error) {
+func refactorRewrite(ctx context.Context, snapshot source.Snapshot, pkg source.Package, pgf *source.ParsedGoFile, fh file.Handle, rng protocol.Range) (_ []protocol.CodeAction, rerr error) {
// golang/go#61693: code actions were refactored to run outside of the
// analysis framework, but as a result they lost their panic recovery.
//
@@ -574,7 +575,7 @@
}
// refactorInline returns inline actions available at the specified range.
-func refactorInline(ctx context.Context, snapshot source.Snapshot, pkg source.Package, pgf *source.ParsedGoFile, fh source.FileHandle, rng protocol.Range) ([]protocol.CodeAction, error) {
+func refactorInline(ctx context.Context, snapshot source.Snapshot, pkg source.Package, pgf *source.ParsedGoFile, fh file.Handle, rng protocol.Range) ([]protocol.CodeAction, error) {
var commands []protocol.Command
// If range is within call expression, offer inline action.
@@ -602,7 +603,7 @@
return actions, nil
}
-func documentChanges(fh source.FileHandle, edits []protocol.TextEdit) []protocol.DocumentChanges {
+func documentChanges(fh file.Handle, edits []protocol.TextEdit) []protocol.DocumentChanges {
return []protocol.DocumentChanges{
{
TextDocumentEdit: &protocol.TextDocumentEdit{
diff --git a/gopls/internal/lsp/code_lens.go b/gopls/internal/lsp/code_lens.go
index c3fd618..6d8378c 100644
--- a/gopls/internal/lsp/code_lens.go
+++ b/gopls/internal/lsp/code_lens.go
@@ -9,6 +9,7 @@
"fmt"
"sort"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/mod"
"golang.org/x/tools/gopls/internal/lsp/protocol"
@@ -21,16 +22,16 @@
ctx, done := event.Start(ctx, "lsp.Server.codeLens", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
}
var lenses map[command.Command]source.LensFunc
switch snapshot.FileKind(fh) {
- case source.Mod:
+ case file.Mod:
lenses = mod.LensFuncs()
- case source.Go:
+ case file.Go:
lenses = source.LensFuncs()
default:
// Unsupported file kind for a code lens.
diff --git a/gopls/internal/lsp/command.go b/gopls/internal/lsp/command.go
index d9ff59d..53fccee 100644
--- a/gopls/internal/lsp/command.go
+++ b/gopls/internal/lsp/command.go
@@ -22,6 +22,7 @@
"golang.org/x/mod/modfile"
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/cache"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/debug"
@@ -92,7 +93,7 @@
// for details.
type commandDeps struct {
snapshot source.Snapshot // present if cfg.forURI was set
- fh source.FileHandle // present if cfg.forURI was set
+ fh file.Handle // present if cfg.forURI was set
work *progress.WorkDone // present cfg.progress was set
}
@@ -124,7 +125,7 @@
if cfg.forURI != "" {
var ok bool
var release func()
- deps.snapshot, deps.fh, ok, release, err = c.s.beginFileRequest(ctx, cfg.forURI, source.UnknownKind)
+ deps.snapshot, deps.fh, ok, release, err = c.s.beginFileRequest(ctx, cfg.forURI, file.UnknownKind)
defer release()
if !ok {
if err != nil {
@@ -316,7 +317,7 @@
progress: "Updating go.sum",
}, func(ctx context.Context, deps commandDeps) error {
for _, uri := range args.URIs {
- snapshot, fh, ok, release, err := c.s.beginFileRequest(ctx, uri, source.UnknownKind)
+ snapshot, fh, ok, release, err := c.s.beginFileRequest(ctx, uri, file.UnknownKind)
defer release()
if !ok {
return err
@@ -338,7 +339,7 @@
progress: "Running go mod tidy",
}, func(ctx context.Context, deps commandDeps) error {
for _, uri := range args.URIs {
- snapshot, fh, ok, release, err := c.s.beginFileRequest(ctx, uri, source.UnknownKind)
+ snapshot, fh, ok, release, err := c.s.beginFileRequest(ctx, uri, file.UnknownKind)
defer release()
if !ok {
return err
@@ -382,7 +383,7 @@
requireSave: true, // if go.mod isn't saved it could cause a problem
forURI: args.URI,
}, func(ctx context.Context, deps commandDeps) error {
- snapshot, fh, ok, release, err := c.s.beginFileRequest(ctx, args.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := c.s.beginFileRequest(ctx, args.URI, file.UnknownKind)
defer release()
if !ok {
return err
diff --git a/gopls/internal/lsp/completion.go b/gopls/internal/lsp/completion.go
index 558a67a..2c121a9 100644
--- a/gopls/internal/lsp/completion.go
+++ b/gopls/internal/lsp/completion.go
@@ -9,6 +9,7 @@
"fmt"
"strings"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/lsp/source/completion"
@@ -28,7 +29,7 @@
ctx, done := event.Start(ctx, "lsp.Server.completion", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
@@ -36,17 +37,17 @@
var candidates []completion.CompletionItem
var surrounding *completion.Selection
switch snapshot.FileKind(fh) {
- case source.Go:
+ case file.Go:
candidates, surrounding, err = completion.Completion(ctx, snapshot, fh, params.Position, params.Context)
- case source.Mod:
+ case file.Mod:
candidates, surrounding = nil, nil
- case source.Work:
+ case file.Work:
cl, err := work.Completion(ctx, snapshot, fh, params.Position)
if err != nil {
break
}
return cl, nil
- case source.Tmpl:
+ case file.Tmpl:
var cl *protocol.CompletionList
cl, err = template.Completion(ctx, snapshot, fh, params.Position, params.Context)
if err != nil {
diff --git a/gopls/internal/lsp/debug/serve.go b/gopls/internal/lsp/debug/serve.go
index f57b833..9609e0c 100644
--- a/gopls/internal/lsp/debug/serve.go
+++ b/gopls/internal/lsp/debug/serve.go
@@ -322,7 +322,7 @@
}
for _, o := range s.Overlays() {
// TODO(adonovan): understand and document this comparison.
- if o.FileIdentity().Hash.String() == identifier {
+ if o.Identity().Hash.String() == identifier {
return o
}
}
@@ -836,7 +836,7 @@
{{$session := .}}
<ul>{{range .Overlays}}
<li>
-<a href="/file/{{$session.ID}}/{{.FileIdentity.Hash}}">{{.FileIdentity.URI}}</a>
+<a href="/file/{{$session.ID}}/{{.Identity.Hash}}">{{.Identity.URI}}</a>
</li>{{end}}</ul>
{{end}}
`))
@@ -850,11 +850,11 @@
`))
var FileTmpl = template.Must(template.Must(BaseTemplate.Clone()).Parse(`
-{{define "title"}}Overlay {{.FileIdentity.Hash}}{{end}}
+{{define "title"}}Overlay {{.Identity.Hash}}{{end}}
{{define "body"}}
{{with .}}
URI: <b>{{.URI}}</b><br>
- Identifier: <b>{{.FileIdentity.Hash}}</b><br>
+ Identifier: <b>{{.Identity.Hash}}</b><br>
Version: <b>{{.Version}}</b><br>
Kind: <b>{{.Kind}}</b><br>
{{end}}
diff --git a/gopls/internal/lsp/definition.go b/gopls/internal/lsp/definition.go
index 5eb5062..bdbf45a 100644
--- a/gopls/internal/lsp/definition.go
+++ b/gopls/internal/lsp/definition.go
@@ -8,6 +8,7 @@
"context"
"fmt"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/lsp/template"
@@ -26,15 +27,15 @@
defer done()
// TODO(rfindley): definition requests should be multiplexed across all views.
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
}
switch kind := snapshot.FileKind(fh); kind {
- case source.Tmpl:
+ case file.Tmpl:
return template.Definition(snapshot, fh, params.Position)
- case source.Go:
+ case file.Go:
return source.Definition(ctx, snapshot, fh, params.Position)
default:
return nil, fmt.Errorf("can't find definitions for file type %s", kind)
@@ -46,13 +47,13 @@
defer done()
// TODO(rfindley): type definition requests should be multiplexed across all views.
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.Go)
defer release()
if !ok {
return nil, err
}
switch kind := snapshot.FileKind(fh); kind {
- case source.Go:
+ case file.Go:
return source.TypeDefinition(ctx, snapshot, fh, params.Position)
default:
return nil, fmt.Errorf("can't find type definitions for file type %s", kind)
diff --git a/gopls/internal/lsp/folding_range.go b/gopls/internal/lsp/folding_range.go
index 302463f..db0ec0b 100644
--- a/gopls/internal/lsp/folding_range.go
+++ b/gopls/internal/lsp/folding_range.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
@@ -17,7 +18,7 @@
ctx, done := event.Start(ctx, "lsp.Server.foldingRange", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.Go)
defer release()
if !ok {
return nil, err
diff --git a/gopls/internal/lsp/format.go b/gopls/internal/lsp/format.go
index 5fd37ca..efb24fd 100644
--- a/gopls/internal/lsp/format.go
+++ b/gopls/internal/lsp/format.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/mod"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -19,17 +20,17 @@
ctx, done := event.Start(ctx, "lsp.Server.formatting", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
}
switch snapshot.FileKind(fh) {
- case source.Mod:
+ case file.Mod:
return mod.Format(ctx, snapshot, fh)
- case source.Go:
+ case file.Go:
return source.Format(ctx, snapshot, fh)
- case source.Work:
+ case file.Work:
return work.Format(ctx, snapshot, fh)
}
return nil, nil
diff --git a/gopls/internal/lsp/general.go b/gopls/internal/lsp/general.go
index 4ba8fe5..ad9be90 100644
--- a/gopls/internal/lsp/general.go
+++ b/gopls/internal/lsp/general.go
@@ -18,6 +18,7 @@
"sync"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/goversion"
"golang.org/x/tools/gopls/internal/lsp/debug"
"golang.org/x/tools/gopls/internal/lsp/protocol"
@@ -548,7 +549,7 @@
// We don't want to return errors for benign conditions like wrong file type,
// so callers should do if !ok { return err } rather than if err != nil.
// The returned cleanup function is non-nil even in case of false/error result.
-func (s *server) beginFileRequest(ctx context.Context, pURI protocol.DocumentURI, expectKind source.FileKind) (source.Snapshot, source.FileHandle, bool, func(), error) {
+func (s *server) beginFileRequest(ctx context.Context, pURI protocol.DocumentURI, expectKind file.Kind) (source.Snapshot, file.Handle, bool, func(), error) {
uri := pURI
if !uri.IsFile() {
// Not a file URI. Stop processing the request, but don't return an error.
@@ -567,7 +568,7 @@
release()
return nil, nil, false, func() {}, err
}
- if expectKind != source.UnknownKind && snapshot.FileKind(fh) != expectKind {
+ if expectKind != file.UnknownKind && snapshot.FileKind(fh) != expectKind {
// Wrong kind of file. Nothing to do.
release()
return nil, nil, false, func() {}, nil
diff --git a/gopls/internal/lsp/highlight.go b/gopls/internal/lsp/highlight.go
index d058578..2a00f3b 100644
--- a/gopls/internal/lsp/highlight.go
+++ b/gopls/internal/lsp/highlight.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/lsp/template"
@@ -18,13 +19,13 @@
ctx, done := event.Start(ctx, "lsp.Server.documentHighlight", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.Go)
defer release()
if !ok {
return nil, err
}
- if snapshot.FileKind(fh) == source.Tmpl {
+ if snapshot.FileKind(fh) == file.Tmpl {
return template.Highlight(ctx, snapshot, fh, params.Position)
}
diff --git a/gopls/internal/lsp/hover.go b/gopls/internal/lsp/hover.go
index 72811d7..598fa63 100644
--- a/gopls/internal/lsp/hover.go
+++ b/gopls/internal/lsp/hover.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/mod"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -26,19 +27,19 @@
ctx, done := event.Start(ctx, "lsp.Server.hover", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
}
switch snapshot.FileKind(fh) {
- case source.Mod:
+ case file.Mod:
return mod.Hover(ctx, snapshot, fh, params.Position)
- case source.Go:
+ case file.Go:
return source.Hover(ctx, snapshot, fh, params.Position)
- case source.Tmpl:
+ case file.Tmpl:
return template.Hover(ctx, snapshot, fh, params.Position)
- case source.Work:
+ case file.Work:
return work.Hover(ctx, snapshot, fh, params.Position)
}
return nil, nil
diff --git a/gopls/internal/lsp/implementation.go b/gopls/internal/lsp/implementation.go
index f3e9bbe..4771f79 100644
--- a/gopls/internal/lsp/implementation.go
+++ b/gopls/internal/lsp/implementation.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/telemetry"
@@ -23,7 +24,7 @@
ctx, done := event.Start(ctx, "lsp.Server.implementation", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.Go)
defer release()
if !ok {
return nil, err
diff --git a/gopls/internal/lsp/inlay_hint.go b/gopls/internal/lsp/inlay_hint.go
index 2496b88..3c7ba14 100644
--- a/gopls/internal/lsp/inlay_hint.go
+++ b/gopls/internal/lsp/inlay_hint.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/mod"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -18,15 +19,15 @@
ctx, done := event.Start(ctx, "lsp.Server.inlayHint", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
}
switch snapshot.FileKind(fh) {
- case source.Mod:
+ case file.Mod:
return mod.InlayHint(ctx, snapshot, fh, params.Range)
- case source.Go:
+ case file.Go:
return source.InlayHint(ctx, snapshot, fh, params.Range)
}
return nil, nil
diff --git a/gopls/internal/lsp/link.go b/gopls/internal/lsp/link.go
index 095c66a..cbc11e9 100644
--- a/gopls/internal/lsp/link.go
+++ b/gopls/internal/lsp/link.go
@@ -16,6 +16,7 @@
"sync"
"golang.org/x/mod/modfile"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -27,15 +28,15 @@
ctx, done := event.Start(ctx, "lsp.Server.documentLink")
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
}
switch snapshot.FileKind(fh) {
- case source.Mod:
+ case file.Mod:
links, err = modLinks(ctx, snapshot, fh)
- case source.Go:
+ case file.Go:
links, err = goLinks(ctx, snapshot, fh)
}
// Don't return errors for document links.
@@ -46,7 +47,7 @@
return links, nil
}
-func modLinks(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]protocol.DocumentLink, error) {
+func modLinks(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]protocol.DocumentLink, error) {
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil {
return nil, err
@@ -102,7 +103,7 @@
}
// goLinks returns the set of hyperlink annotations for the specified Go file.
-func goLinks(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]protocol.DocumentLink, error) {
+func goLinks(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]protocol.DocumentLink, error) {
pgf, err := snapshot.ParseGo(ctx, fh, source.ParseFull)
if err != nil {
diff --git a/gopls/internal/lsp/mod/code_lens.go b/gopls/internal/lsp/mod/code_lens.go
index 9a2a623..e53d586 100644
--- a/gopls/internal/lsp/mod/code_lens.go
+++ b/gopls/internal/lsp/mod/code_lens.go
@@ -11,6 +11,7 @@
"path/filepath"
"golang.org/x/mod/modfile"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -26,7 +27,7 @@
}
}
-func upgradeLenses(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]protocol.CodeLens, error) {
+func upgradeLenses(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]protocol.CodeLens, error) {
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil || pm.File == nil {
return nil, err
@@ -87,7 +88,7 @@
}...), nil
}
-func tidyLens(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]protocol.CodeLens, error) {
+func tidyLens(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]protocol.CodeLens, error) {
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil || pm.File == nil {
return nil, err
@@ -107,7 +108,7 @@
}}, nil
}
-func vendorLens(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]protocol.CodeLens, error) {
+func vendorLens(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]protocol.CodeLens, error) {
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil || pm.File == nil {
return nil, err
@@ -135,7 +136,7 @@
return []protocol.CodeLens{{Range: rng, Command: &cmd}}, nil
}
-func moduleStmtRange(fh source.FileHandle, pm *source.ParsedModule) (protocol.Range, error) {
+func moduleStmtRange(fh file.Handle, pm *source.ParsedModule) (protocol.Range, error) {
if pm.File == nil || pm.File.Module == nil || pm.File.Module.Syntax == nil {
return protocol.Range{}, fmt.Errorf("no module statement in %s", fh.URI())
}
@@ -145,7 +146,7 @@
// firstRequireRange returns the range for the first "require" in the given
// go.mod file. This is either a require block or an individual require line.
-func firstRequireRange(fh source.FileHandle, pm *source.ParsedModule) (protocol.Range, error) {
+func firstRequireRange(fh file.Handle, pm *source.ParsedModule) (protocol.Range, error) {
if len(pm.File.Require) == 0 {
return protocol.Range{}, fmt.Errorf("no requires in the file %s", fh.URI())
}
@@ -164,7 +165,7 @@
return pm.Mapper.OffsetRange(start.Byte, end.Byte)
}
-func vulncheckLenses(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]protocol.CodeLens, error) {
+func vulncheckLenses(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]protocol.CodeLens, error) {
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil || pm.File == nil {
return nil, err
diff --git a/gopls/internal/lsp/mod/diagnostics.go b/gopls/internal/lsp/mod/diagnostics.go
index 1f2d7fc..29220d5 100644
--- a/gopls/internal/lsp/mod/diagnostics.go
+++ b/gopls/internal/lsp/mod/diagnostics.go
@@ -17,6 +17,7 @@
"golang.org/x/mod/modfile"
"golang.org/x/mod/semver"
"golang.org/x/sync/errgroup"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -58,7 +59,7 @@
return collectDiagnostics(ctx, snapshot, ModVulnerabilityDiagnostics)
}
-func collectDiagnostics(ctx context.Context, snapshot source.Snapshot, diagFn func(context.Context, source.Snapshot, source.FileHandle) ([]*source.Diagnostic, error)) (map[protocol.DocumentURI][]*source.Diagnostic, error) {
+func collectDiagnostics(ctx context.Context, snapshot source.Snapshot, diagFn func(context.Context, source.Snapshot, file.Handle) ([]*source.Diagnostic, error)) (map[protocol.DocumentURI][]*source.Diagnostic, error) {
g, ctx := errgroup.WithContext(ctx)
cpulimit := runtime.GOMAXPROCS(0)
g.SetLimit(cpulimit)
@@ -93,7 +94,7 @@
}
// ModParseDiagnostics reports diagnostics from parsing the mod file.
-func ModParseDiagnostics(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) (diagnostics []*source.Diagnostic, err error) {
+func ModParseDiagnostics(ctx context.Context, snapshot source.Snapshot, fh file.Handle) (diagnostics []*source.Diagnostic, err error) {
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil {
if pm == nil || len(pm.ParseErrors) == 0 {
@@ -105,7 +106,7 @@
}
// ModTidyDiagnostics reports diagnostics from running go mod tidy.
-func ModTidyDiagnostics(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) (diagnostics []*source.Diagnostic, err error) {
+func ModTidyDiagnostics(ctx context.Context, snapshot source.Snapshot, fh file.Handle) (diagnostics []*source.Diagnostic, err error) {
pm, err := snapshot.ParseMod(ctx, fh) // memoized
if err != nil {
return nil, nil // errors reported by ModDiagnostics above
@@ -128,7 +129,7 @@
// ModUpgradeDiagnostics adds upgrade quick fixes for individual modules if the upgrades
// are recorded in the view.
-func ModUpgradeDiagnostics(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) (upgradeDiagnostics []*source.Diagnostic, err error) {
+func ModUpgradeDiagnostics(ctx context.Context, snapshot source.Snapshot, fh file.Handle) (upgradeDiagnostics []*source.Diagnostic, err error) {
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil {
// Don't return an error if there are parse error diagnostics to be shown, but also do not
@@ -176,7 +177,7 @@
// ModVulnerabilityDiagnostics adds diagnostics for vulnerabilities in individual modules
// if the vulnerability is recorded in the view.
-func ModVulnerabilityDiagnostics(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) (vulnDiagnostics []*source.Diagnostic, err error) {
+func ModVulnerabilityDiagnostics(ctx context.Context, snapshot source.Snapshot, fh file.Handle) (vulnDiagnostics []*source.Diagnostic, err error) {
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil {
// Don't return an error if there are parse error diagnostics to be shown, but also do not
@@ -495,7 +496,7 @@
return fmt.Sprintf("https://pkg.go.dev/vuln/%s", vulnID)
}
-func getUpgradeCodeAction(fh source.FileHandle, req *modfile.Require, version string) (protocol.Command, error) {
+func getUpgradeCodeAction(fh file.Handle, req *modfile.Require, version string) (protocol.Command, error) {
cmd, err := command.NewUpgradeDependencyCommand(upgradeTitle(version), command.DependencyArgs{
URI: fh.URI(),
AddRequire: false,
diff --git a/gopls/internal/lsp/mod/format.go b/gopls/internal/lsp/mod/format.go
index daa12da..b04baa2 100644
--- a/gopls/internal/lsp/mod/format.go
+++ b/gopls/internal/lsp/mod/format.go
@@ -7,12 +7,13 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
)
-func Format(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]protocol.TextEdit, error) {
+func Format(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]protocol.TextEdit, error) {
ctx, done := event.Start(ctx, "mod.Format")
defer done()
diff --git a/gopls/internal/lsp/mod/hover.go b/gopls/internal/lsp/mod/hover.go
index fc1705b..9f1d621 100644
--- a/gopls/internal/lsp/mod/hover.go
+++ b/gopls/internal/lsp/mod/hover.go
@@ -13,6 +13,7 @@
"golang.org/x/mod/modfile"
"golang.org/x/mod/semver"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/vulncheck"
@@ -21,7 +22,7 @@
"golang.org/x/tools/internal/event"
)
-func Hover(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, position protocol.Position) (*protocol.Hover, error) {
+func Hover(ctx context.Context, snapshot source.Snapshot, fh file.Handle, position protocol.Position) (*protocol.Hover, error) {
var found bool
for _, uri := range snapshot.ModFiles() {
if fh.URI() == uri {
@@ -55,7 +56,7 @@
return hoverOnRequireStatement(ctx, pm, offset, snapshot, fh)
}
-func hoverOnRequireStatement(ctx context.Context, pm *source.ParsedModule, offset int, snapshot source.Snapshot, fh source.FileHandle) (*protocol.Hover, error) {
+func hoverOnRequireStatement(ctx context.Context, pm *source.ParsedModule, offset int, snapshot source.Snapshot, fh file.Handle) (*protocol.Hover, error) {
// Confirm that the cursor is at the position of a require statement.
var req *modfile.Require
var startOffset, endOffset int
@@ -126,7 +127,7 @@
}, nil
}
-func hoverOnModuleStatement(ctx context.Context, pm *source.ParsedModule, offset int, snapshot source.Snapshot, fh source.FileHandle) (*protocol.Hover, bool) {
+func hoverOnModuleStatement(ctx context.Context, pm *source.ParsedModule, offset int, snapshot source.Snapshot, fh file.Handle) (*protocol.Hover, bool) {
module := pm.File.Module
if module == nil {
return nil, false // no module stmt
diff --git a/gopls/internal/lsp/mod/inlayhint.go b/gopls/internal/lsp/mod/inlayhint.go
index f522365..2fda62f 100644
--- a/gopls/internal/lsp/mod/inlayhint.go
+++ b/gopls/internal/lsp/mod/inlayhint.go
@@ -8,11 +8,12 @@
"fmt"
"golang.org/x/mod/modfile"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
)
-func InlayHint(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, rng protocol.Range) ([]protocol.InlayHint, error) {
+func InlayHint(ctx context.Context, snapshot source.Snapshot, fh file.Handle, rng protocol.Range) ([]protocol.InlayHint, error) {
// Inlay hints are enabled if the client supports them.
pm, err := snapshot.ParseMod(ctx, fh)
if err != nil {
diff --git a/gopls/internal/lsp/references.go b/gopls/internal/lsp/references.go
index d132da1..03e749b 100644
--- a/gopls/internal/lsp/references.go
+++ b/gopls/internal/lsp/references.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/lsp/template"
@@ -24,12 +25,12 @@
ctx, done := event.Start(ctx, "lsp.Server.references", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
}
- if snapshot.FileKind(fh) == source.Tmpl {
+ if snapshot.FileKind(fh) == file.Tmpl {
return template.References(ctx, snapshot, fh, params)
}
return source.References(ctx, snapshot, fh, params.Position, params.Context.IncludeDeclaration)
diff --git a/gopls/internal/lsp/rename.go b/gopls/internal/lsp/rename.go
index c693507..41473a5 100644
--- a/gopls/internal/lsp/rename.go
+++ b/gopls/internal/lsp/rename.go
@@ -8,6 +8,7 @@
"context"
"path/filepath"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
@@ -18,7 +19,7 @@
ctx, done := event.Start(ctx, "lsp.Server.rename", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.Go)
defer release()
if !ok {
return nil, err
@@ -66,7 +67,7 @@
ctx, done := event.Start(ctx, "lsp.Server.prepareRename", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.Go)
defer release()
if !ok {
return nil, err
diff --git a/gopls/internal/lsp/selection_range.go b/gopls/internal/lsp/selection_range.go
index a0011d1..08651dc 100644
--- a/gopls/internal/lsp/selection_range.go
+++ b/gopls/internal/lsp/selection_range.go
@@ -8,6 +8,7 @@
"context"
"golang.org/x/tools/go/ast/astutil"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
@@ -28,7 +29,7 @@
ctx, done := event.Start(ctx, "lsp.Server.selectionRange")
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
diff --git a/gopls/internal/lsp/semantic.go b/gopls/internal/lsp/semantic.go
index 198c305..ff8ccc0 100644
--- a/gopls/internal/lsp/semantic.go
+++ b/gopls/internal/lsp/semantic.go
@@ -18,6 +18,7 @@
"strings"
"time"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -50,7 +51,7 @@
ctx, done := event.Start(ctx, "lsp.Server.semanticTokens", tag.URI.Of(td.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, td.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, td.URI, file.UnknownKind)
defer release()
if !ok {
return nil, err
@@ -62,7 +63,7 @@
}
kind := snapshot.FileKind(fh)
- if kind == source.Tmpl {
+ if kind == file.Tmpl {
// this is a little cumbersome to avoid both exporting 'encoded' and its methods
// and to avoid import cycles
e := &encoded{
@@ -80,7 +81,7 @@
}
return template.SemanticTokens(ctx, snapshot, fh.URI(), add, data)
}
- if kind != source.Go {
+ if kind != file.Go {
return nil, nil
}
pkg, pgf, err := source.NarrowestPackageForFile(ctx, snapshot, fh.URI())
diff --git a/gopls/internal/lsp/server.go b/gopls/internal/lsp/server.go
index 8a6fd18..9b7304a 100644
--- a/gopls/internal/lsp/server.go
+++ b/gopls/internal/lsp/server.go
@@ -18,6 +18,7 @@
"os"
"sync"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/cache"
"golang.org/x/tools/gopls/internal/lsp/progress"
"golang.org/x/tools/gopls/internal/lsp/protocol"
@@ -143,8 +144,8 @@
// TODO(adonovan): opt: parallelize FileDiagnostics(URI...), either
// by calling it in multiple goroutines or, better, by making
// the relevant APIs accept a set of URIs/packages.
- for _, file := range paramMap["files"].([]interface{}) {
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, protocol.DocumentURI(file.(string)), source.UnknownKind)
+ for _, f := range paramMap["files"].([]interface{}) {
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, protocol.DocumentURI(f.(string)), file.UnknownKind)
defer release()
if !ok {
return nil, err
@@ -180,7 +181,7 @@
// efficient to compute the set of packages and TypeCheck and
// Analyze them all at once. Or instead support textDocument/diagnostic
// (golang/go#60122).
-func (s *server) diagnoseFile(ctx context.Context, snapshot source.Snapshot, uri protocol.DocumentURI) (source.FileHandle, []*source.Diagnostic, error) {
+func (s *server) diagnoseFile(ctx context.Context, snapshot source.Snapshot, uri protocol.DocumentURI) (file.Handle, []*source.Diagnostic, error) {
fh, err := snapshot.ReadFile(ctx, uri)
if err != nil {
return nil, nil, err
diff --git a/gopls/internal/lsp/signature_help.go b/gopls/internal/lsp/signature_help.go
index 4fc4e88..7b699b7 100644
--- a/gopls/internal/lsp/signature_help.go
+++ b/gopls/internal/lsp/signature_help.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
@@ -17,7 +18,7 @@
ctx, done := event.Start(ctx, "lsp.Server.signatureHelp", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.Go)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.Go)
defer release()
if !ok {
return nil, err
diff --git a/gopls/internal/lsp/source/add_import.go b/gopls/internal/lsp/source/add_import.go
index cd8ec7a..8930e8f 100644
--- a/gopls/internal/lsp/source/add_import.go
+++ b/gopls/internal/lsp/source/add_import.go
@@ -7,12 +7,13 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/internal/imports"
)
// AddImport adds a single import statement to the given file
-func AddImport(ctx context.Context, snapshot Snapshot, fh FileHandle, importPath string) ([]protocol.TextEdit, error) {
+func AddImport(ctx context.Context, snapshot Snapshot, fh file.Handle, importPath string) ([]protocol.TextEdit, error) {
pgf, err := snapshot.ParseGo(ctx, fh, ParseFull)
if err != nil {
return nil, err
diff --git a/gopls/internal/lsp/source/call_hierarchy.go b/gopls/internal/lsp/source/call_hierarchy.go
index cdaa2c6..606ae30 100644
--- a/gopls/internal/lsp/source/call_hierarchy.go
+++ b/gopls/internal/lsp/source/call_hierarchy.go
@@ -15,6 +15,7 @@
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/internal/event"
@@ -22,7 +23,7 @@
)
// PrepareCallHierarchy returns an array of CallHierarchyItem for a file and the position within the file.
-func PrepareCallHierarchy(ctx context.Context, snapshot Snapshot, fh FileHandle, pp protocol.Position) ([]protocol.CallHierarchyItem, error) {
+func PrepareCallHierarchy(ctx context.Context, snapshot Snapshot, fh file.Handle, pp protocol.Position) ([]protocol.CallHierarchyItem, error) {
ctx, done := event.Start(ctx, "source.PrepareCallHierarchy")
defer done()
@@ -63,7 +64,7 @@
}
// IncomingCalls returns an array of CallHierarchyIncomingCall for a file and the position within the file.
-func IncomingCalls(ctx context.Context, snapshot Snapshot, fh FileHandle, pos protocol.Position) ([]protocol.CallHierarchyIncomingCall, error) {
+func IncomingCalls(ctx context.Context, snapshot Snapshot, fh file.Handle, pos protocol.Position) ([]protocol.CallHierarchyIncomingCall, error) {
ctx, done := event.Start(ctx, "source.IncomingCalls")
defer done()
@@ -177,7 +178,7 @@
}
// OutgoingCalls returns an array of CallHierarchyOutgoingCall for a file and the position within the file.
-func OutgoingCalls(ctx context.Context, snapshot Snapshot, fh FileHandle, pp protocol.Position) ([]protocol.CallHierarchyOutgoingCall, error) {
+func OutgoingCalls(ctx context.Context, snapshot Snapshot, fh file.Handle, pp protocol.Position) ([]protocol.CallHierarchyOutgoingCall, error) {
ctx, done := event.Start(ctx, "source.OutgoingCalls")
defer done()
diff --git a/gopls/internal/lsp/source/change_quote.go b/gopls/internal/lsp/source/change_quote.go
index a4dc132..6bb7f37 100644
--- a/gopls/internal/lsp/source/change_quote.go
+++ b/gopls/internal/lsp/source/change_quote.go
@@ -12,6 +12,7 @@
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/internal/diff"
@@ -23,7 +24,7 @@
// Only the following conditions are true, the action in result is valid
// - [start, end) is enclosed by a string literal
// - if the string is interpreted string, need check whether the convert is allowed
-func ConvertStringLiteral(pgf *ParsedGoFile, fh FileHandle, rng protocol.Range) (protocol.CodeAction, bool) {
+func ConvertStringLiteral(pgf *ParsedGoFile, fh file.Handle, rng protocol.Range) (protocol.CodeAction, bool) {
startPos, endPos, err := pgf.RangePos(rng)
if err != nil {
bug.Reportf("(file=%v).RangePos(%v) failed: %v", pgf.URI, rng, err)
diff --git a/gopls/internal/lsp/source/change_signature.go b/gopls/internal/lsp/source/change_signature.go
index 1864092..dcd1185 100644
--- a/gopls/internal/lsp/source/change_signature.go
+++ b/gopls/internal/lsp/source/change_signature.go
@@ -17,6 +17,7 @@
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/imports"
@@ -37,7 +38,7 @@
// - Improve the extra newlines in output.
// - Stream type checking via ForEachPackage.
// - Avoid unnecessary additional type checking.
-func RemoveUnusedParameter(ctx context.Context, fh FileHandle, rng protocol.Range, snapshot Snapshot) ([]protocol.DocumentChanges, error) {
+func RemoveUnusedParameter(ctx context.Context, fh file.Handle, rng protocol.Range, snapshot Snapshot) ([]protocol.DocumentChanges, error) {
pkg, pgf, err := NarrowestPackageForFile(ctx, snapshot, fh.URI())
if err != nil {
return nil, err
diff --git a/gopls/internal/lsp/source/code_lens.go b/gopls/internal/lsp/source/code_lens.go
index 7fb3559..28495f0 100644
--- a/gopls/internal/lsp/source/code_lens.go
+++ b/gopls/internal/lsp/source/code_lens.go
@@ -13,11 +13,12 @@
"regexp"
"strings"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/command"
"golang.org/x/tools/gopls/internal/lsp/protocol"
)
-type LensFunc func(context.Context, Snapshot, FileHandle) ([]protocol.CodeLens, error)
+type LensFunc func(context.Context, Snapshot, file.Handle) ([]protocol.CodeLens, error)
// LensFuncs returns the supported lensFuncs for Go files.
func LensFuncs() map[command.Command]LensFunc {
@@ -34,7 +35,7 @@
benchmarkRe = regexp.MustCompile(`^Benchmark([^a-z]|$)`)
)
-func runTestCodeLens(ctx context.Context, snapshot Snapshot, fh FileHandle) ([]protocol.CodeLens, error) {
+func runTestCodeLens(ctx context.Context, snapshot Snapshot, fh file.Handle) ([]protocol.CodeLens, error) {
var codeLens []protocol.CodeLens
pkg, pgf, err := NarrowestPackageForFile(ctx, snapshot, fh.URI())
@@ -165,7 +166,7 @@
return namedObj.Id() == paramID
}
-func goGenerateCodeLens(ctx context.Context, snapshot Snapshot, fh FileHandle) ([]protocol.CodeLens, error) {
+func goGenerateCodeLens(ctx context.Context, snapshot Snapshot, fh file.Handle) ([]protocol.CodeLens, error) {
pgf, err := snapshot.ParseGo(ctx, fh, ParseFull)
if err != nil {
return nil, err
@@ -199,7 +200,7 @@
return nil, nil
}
-func regenerateCgoLens(ctx context.Context, snapshot Snapshot, fh FileHandle) ([]protocol.CodeLens, error) {
+func regenerateCgoLens(ctx context.Context, snapshot Snapshot, fh file.Handle) ([]protocol.CodeLens, error) {
pgf, err := snapshot.ParseGo(ctx, fh, ParseFull)
if err != nil {
return nil, err
@@ -225,7 +226,7 @@
return []protocol.CodeLens{{Range: rng, Command: &cmd}}, nil
}
-func toggleDetailsCodeLens(ctx context.Context, snapshot Snapshot, fh FileHandle) ([]protocol.CodeLens, error) {
+func toggleDetailsCodeLens(ctx context.Context, snapshot Snapshot, fh file.Handle) ([]protocol.CodeLens, error) {
pgf, err := snapshot.ParseGo(ctx, fh, ParseFull)
if err != nil {
return nil, err
diff --git a/gopls/internal/lsp/source/completion/completion.go b/gopls/internal/lsp/source/completion/completion.go
index 42c369f..f0cd6d0 100644
--- a/gopls/internal/lsp/source/completion/completion.go
+++ b/gopls/internal/lsp/source/completion/completion.go
@@ -28,6 +28,7 @@
"golang.org/x/sync/errgroup"
"golang.org/x/tools/go/ast/astutil"
goplsastutil "golang.org/x/tools/gopls/internal/astutil"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/gopls/internal/lsp/snippet"
@@ -177,7 +178,7 @@
completionContext completionContext
// fh is a handle to the file associated with this completion request.
- fh source.FileHandle
+ fh file.Handle
// filename is the name of the file associated with this completion request.
filename string
@@ -442,7 +443,7 @@
// The selection is computed based on the preceding identifier and can be used by
// the client to score the quality of the completion. For instance, some clients
// may tolerate imperfect matches as valid completion results, since users may make typos.
-func Completion(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, protoPos protocol.Position, protoContext protocol.CompletionContext) ([]CompletionItem, *Selection, error) {
+func Completion(ctx context.Context, snapshot source.Snapshot, fh file.Handle, protoPos protocol.Position, protoContext protocol.CompletionContext) ([]CompletionItem, *Selection, error) {
ctx, done := event.Start(ctx, "completion.Completion")
defer done()
diff --git a/gopls/internal/lsp/source/completion/package.go b/gopls/internal/lsp/source/completion/package.go
index 7c69c8f..d4aacf4 100644
--- a/gopls/internal/lsp/source/completion/package.go
+++ b/gopls/internal/lsp/source/completion/package.go
@@ -18,6 +18,7 @@
"strings"
"unicode"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/gopls/internal/lsp/source"
@@ -26,7 +27,7 @@
// packageClauseCompletions offers completions for a package declaration when
// one is not present in the given file.
-func packageClauseCompletions(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, position protocol.Position) ([]CompletionItem, *Selection, error) {
+func packageClauseCompletions(ctx context.Context, snapshot source.Snapshot, fh file.Handle, position protocol.Position) ([]CompletionItem, *Selection, error) {
// We know that the AST for this file will be empty due to the missing
// package declaration, but parse it anyway to get a mapper.
// TODO(adonovan): opt: there's no need to parse just to get a mapper.
diff --git a/gopls/internal/lsp/source/definition.go b/gopls/internal/lsp/source/definition.go
index 158b3b1..7ed2860 100644
--- a/gopls/internal/lsp/source/definition.go
+++ b/gopls/internal/lsp/source/definition.go
@@ -13,12 +13,13 @@
"go/types"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/internal/event"
)
// Definition handles the textDocument/definition request for Go files.
-func Definition(ctx context.Context, snapshot Snapshot, fh FileHandle, position protocol.Position) ([]protocol.Location, error) {
+func Definition(ctx context.Context, snapshot Snapshot, fh file.Handle, position protocol.Position) ([]protocol.Location, error) {
ctx, done := event.Start(ctx, "source.Definition")
defer done()
@@ -276,7 +277,7 @@
// TODO(rfindley): avoid the duplicate column mapping here, by associating a
// column mapper with each file handle.
-func mapPosition(ctx context.Context, fset *token.FileSet, s FileSource, start, end token.Pos) (protocol.Location, error) {
+func mapPosition(ctx context.Context, fset *token.FileSet, s file.Source, start, end token.Pos) (protocol.Location, error) {
file := fset.File(start)
uri := protocol.URIFromPath(file.Name())
fh, err := s.ReadFile(ctx, uri)
diff --git a/gopls/internal/lsp/source/fix.go b/gopls/internal/lsp/source/fix.go
index 53ed3a3..314403c 100644
--- a/gopls/internal/lsp/source/fix.go
+++ b/gopls/internal/lsp/source/fix.go
@@ -13,6 +13,7 @@
"golang.org/x/tools/go/analysis"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/analysis/embeddirective"
"golang.org/x/tools/gopls/internal/lsp/analysis/fillstruct"
"golang.org/x/tools/gopls/internal/lsp/analysis/undeclaredname"
@@ -29,7 +30,7 @@
// TODO(rfindley): the signature of suggestedFixFunc should probably accept
// (context.Context, Snapshot, protocol.Diagnostic). No reason for us to
// encode as a (URI, Range) pair when we have the protocol type.
- suggestedFixFunc func(context.Context, Snapshot, FileHandle, protocol.Range) ([]protocol.TextDocumentEdit, error)
+ suggestedFixFunc func(context.Context, Snapshot, file.Handle, protocol.Range) ([]protocol.TextDocumentEdit, error)
suggestedFixer struct {
// fixesDiagnostic reports if a diagnostic from the analyzer can be fixed
// by Fix. If nil then all diagnostics from the analyzer are assumed to be
@@ -86,7 +87,7 @@
// singleFile calls analyzers that expect inputs for a single file.
func singleFile(sf singleFileFixFunc) suggestedFixFunc {
- return func(ctx context.Context, snapshot Snapshot, fh FileHandle, rng protocol.Range) ([]protocol.TextDocumentEdit, error) {
+ return func(ctx context.Context, snapshot Snapshot, fh file.Handle, rng protocol.Range) ([]protocol.TextDocumentEdit, error) {
pkg, pgf, err := NarrowestPackageForFile(ctx, snapshot, fh.URI())
if err != nil {
return nil, err
@@ -133,7 +134,7 @@
// ApplyFix applies the command's suggested fix to the given file and
// range, returning the resulting edits.
-func ApplyFix(ctx context.Context, fix string, snapshot Snapshot, fh FileHandle, rng protocol.Range) ([]protocol.TextDocumentEdit, error) {
+func ApplyFix(ctx context.Context, fix string, snapshot Snapshot, fh file.Handle, rng protocol.Range) ([]protocol.TextDocumentEdit, error) {
fixer, ok := suggestedFixes[fix]
if !ok {
return nil, fmt.Errorf("no suggested fix function for %s", fix)
@@ -198,7 +199,7 @@
}
// addEmbedImport adds a missing embed "embed" import with blank name.
-func addEmbedImport(ctx context.Context, snapshot Snapshot, fh FileHandle, _ protocol.Range) ([]protocol.TextDocumentEdit, error) {
+func addEmbedImport(ctx context.Context, snapshot Snapshot, fh file.Handle, _ protocol.Range) ([]protocol.TextDocumentEdit, error) {
pkg, pgf, err := NarrowestPackageForFile(ctx, snapshot, fh.URI())
if err != nil {
return nil, fmt.Errorf("narrow pkg: %w", err)
diff --git a/gopls/internal/lsp/source/folding_range.go b/gopls/internal/lsp/source/folding_range.go
index 9f63c77..b6f7faa 100644
--- a/gopls/internal/lsp/source/folding_range.go
+++ b/gopls/internal/lsp/source/folding_range.go
@@ -12,6 +12,7 @@
"strings"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
)
@@ -23,7 +24,7 @@
}
// FoldingRange gets all of the folding range for f.
-func FoldingRange(ctx context.Context, snapshot Snapshot, fh FileHandle, lineFoldingOnly bool) (ranges []*FoldingRangeInfo, err error) {
+func FoldingRange(ctx context.Context, snapshot Snapshot, fh file.Handle, lineFoldingOnly bool) (ranges []*FoldingRangeInfo, err error) {
// TODO(suzmue): consider limiting the number of folding ranges returned, and
// implement a way to prioritize folding ranges in that case.
pgf, err := snapshot.ParseGo(ctx, fh, ParseFull)
diff --git a/gopls/internal/lsp/source/format.go b/gopls/internal/lsp/source/format.go
index 3646a24..9f3597c 100644
--- a/gopls/internal/lsp/source/format.go
+++ b/gopls/internal/lsp/source/format.go
@@ -16,6 +16,7 @@
"strings"
"text/scanner"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/internal/diff"
@@ -25,7 +26,7 @@
)
// Format formats a file with a given range.
-func Format(ctx context.Context, snapshot Snapshot, fh FileHandle) ([]protocol.TextEdit, error) {
+func Format(ctx context.Context, snapshot Snapshot, fh file.Handle) ([]protocol.TextEdit, error) {
ctx, done := event.Start(ctx, "source.Format")
defer done()
@@ -88,7 +89,7 @@
return computeTextEdits(ctx, snapshot, pgf, formatted)
}
-func formatSource(ctx context.Context, fh FileHandle) ([]byte, error) {
+func formatSource(ctx context.Context, fh file.Handle) ([]byte, error) {
_, done := event.Start(ctx, "source.formatSource")
defer done()
diff --git a/gopls/internal/lsp/source/highlight.go b/gopls/internal/lsp/source/highlight.go
index adfc659..05cdc41 100644
--- a/gopls/internal/lsp/source/highlight.go
+++ b/gopls/internal/lsp/source/highlight.go
@@ -12,11 +12,12 @@
"go/types"
"golang.org/x/tools/go/ast/astutil"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/internal/event"
)
-func Highlight(ctx context.Context, snapshot Snapshot, fh FileHandle, position protocol.Position) ([]protocol.Range, error) {
+func Highlight(ctx context.Context, snapshot Snapshot, fh file.Handle, position protocol.Position) ([]protocol.Range, error) {
ctx, done := event.Start(ctx, "source.Highlight")
defer done()
diff --git a/gopls/internal/lsp/source/hover.go b/gopls/internal/lsp/source/hover.go
index 4c037e3..5e38868 100644
--- a/gopls/internal/lsp/source/hover.go
+++ b/gopls/internal/lsp/source/hover.go
@@ -25,6 +25,7 @@
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/go/types/typeutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/internal/event"
@@ -61,7 +62,7 @@
}
// Hover implements the "textDocument/hover" RPC for Go files.
-func Hover(ctx context.Context, snapshot Snapshot, fh FileHandle, position protocol.Position) (*protocol.Hover, error) {
+func Hover(ctx context.Context, snapshot Snapshot, fh file.Handle, position protocol.Position) (*protocol.Hover, error) {
ctx, done := event.Start(ctx, "source.Hover")
defer done()
@@ -88,7 +89,7 @@
// hover computes hover information at the given position. If we do not support
// hovering at the position, it returns _, nil, nil: an error is only returned
// if the position is valid but we fail to compute hover information.
-func hover(ctx context.Context, snapshot Snapshot, fh FileHandle, pp protocol.Position) (protocol.Range, *HoverJSON, error) {
+func hover(ctx context.Context, snapshot Snapshot, fh file.Handle, pp protocol.Position) (protocol.Range, *HoverJSON, error) {
pkg, pgf, err := NarrowestPackageForFile(ctx, snapshot, fh.URI())
if err != nil {
return protocol.Range{}, nil, err
@@ -634,7 +635,7 @@
// hoverEmbed computes hover information for a filepath.Match pattern.
// Assumes that the pattern is relative to the location of fh.
-func hoverEmbed(fh FileHandle, rng protocol.Range, pattern string) (protocol.Range, *HoverJSON, error) {
+func hoverEmbed(fh file.Handle, rng protocol.Range, pattern string) (protocol.Range, *HoverJSON, error) {
s := &strings.Builder{}
dir := filepath.Dir(fh.URI().Path())
diff --git a/gopls/internal/lsp/source/implementation.go b/gopls/internal/lsp/source/implementation.go
index 339daac..69de9ea 100644
--- a/gopls/internal/lsp/source/implementation.go
+++ b/gopls/internal/lsp/source/implementation.go
@@ -18,6 +18,7 @@
"golang.org/x/sync/errgroup"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/gopls/internal/lsp/source/methodsets"
@@ -45,7 +46,7 @@
//
// If the position denotes a method, the computation is applied to its
// receiver type and then its corresponding methods are returned.
-func Implementation(ctx context.Context, snapshot Snapshot, f FileHandle, pp protocol.Position) ([]protocol.Location, error) {
+func Implementation(ctx context.Context, snapshot Snapshot, f file.Handle, pp protocol.Position) ([]protocol.Location, error) {
ctx, done := event.Start(ctx, "source.Implementation")
defer done()
@@ -69,7 +70,7 @@
return locs, nil
}
-func implementations(ctx context.Context, snapshot Snapshot, fh FileHandle, pp protocol.Position) ([]protocol.Location, error) {
+func implementations(ctx context.Context, snapshot Snapshot, fh file.Handle, pp protocol.Position) ([]protocol.Location, error) {
obj, pkg, err := implementsObj(ctx, snapshot, fh.URI(), pp)
if err != nil {
return nil, err
diff --git a/gopls/internal/lsp/source/inlay_hint.go b/gopls/internal/lsp/source/inlay_hint.go
index 9a77d16..d82b8e1 100644
--- a/gopls/internal/lsp/source/inlay_hint.go
+++ b/gopls/internal/lsp/source/inlay_hint.go
@@ -13,6 +13,7 @@
"go/types"
"strings"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/internal/event"
"golang.org/x/tools/internal/typeparams"
@@ -78,7 +79,7 @@
},
}
-func InlayHint(ctx context.Context, snapshot Snapshot, fh FileHandle, pRng protocol.Range) ([]protocol.InlayHint, error) {
+func InlayHint(ctx context.Context, snapshot Snapshot, fh file.Handle, pRng protocol.Range) ([]protocol.InlayHint, error) {
ctx, done := event.Start(ctx, "source.InlayHint")
defer done()
diff --git a/gopls/internal/lsp/source/inline.go b/gopls/internal/lsp/source/inline.go
index 5b74367..5619b23 100644
--- a/gopls/internal/lsp/source/inline.go
+++ b/gopls/internal/lsp/source/inline.go
@@ -17,6 +17,7 @@
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/go/types/typeutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/internal/diff"
@@ -57,7 +58,7 @@
return call, fn, nil
}
-func inlineCall(ctx context.Context, snapshot Snapshot, fh FileHandle, rng protocol.Range) (_ []protocol.TextDocumentEdit, err error) {
+func inlineCall(ctx context.Context, snapshot Snapshot, fh file.Handle, rng protocol.Range) (_ []protocol.TextDocumentEdit, err error) {
// Find enclosing static call.
callerPkg, callerPGF, err := NarrowestPackageForFile(ctx, snapshot, fh.URI())
if err != nil {
diff --git a/gopls/internal/lsp/source/known_packages.go b/gopls/internal/lsp/source/known_packages.go
index 6e4e198..8f41746 100644
--- a/gopls/internal/lsp/source/known_packages.go
+++ b/gopls/internal/lsp/source/known_packages.go
@@ -13,6 +13,7 @@
"sync"
"time"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/internal/event"
"golang.org/x/tools/internal/imports"
)
@@ -23,7 +24,7 @@
// all dot-free paths (standard packages) appear before dotful ones.
//
// It is part of the gopls.list_known_packages command.
-func KnownPackagePaths(ctx context.Context, snapshot Snapshot, fh FileHandle) ([]PackagePath, error) {
+func KnownPackagePaths(ctx context.Context, snapshot Snapshot, fh file.Handle) ([]PackagePath, error) {
// This algorithm is expressed in terms of Metadata, not Packages,
// so it doesn't cause or wait for type checking.
diff --git a/gopls/internal/lsp/source/options.go b/gopls/internal/lsp/source/options.go
index f2682f1..dfd7da9 100644
--- a/gopls/internal/lsp/source/options.go
+++ b/gopls/internal/lsp/source/options.go
@@ -53,6 +53,7 @@
"golang.org/x/tools/go/analysis/passes/unsafeptr"
"golang.org/x/tools/go/analysis/passes/unusedresult"
"golang.org/x/tools/go/analysis/passes/unusedwrite"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/analysis/deprecated"
"golang.org/x/tools/gopls/internal/lsp/analysis/embeddirective"
"golang.org/x/tools/gopls/internal/lsp/analysis/fillreturns"
@@ -100,8 +101,8 @@
HierarchicalDocumentSymbolSupport: true,
},
ServerOptions: ServerOptions{
- SupportedCodeActions: map[FileKind]map[protocol.CodeActionKind]bool{
- Go: {
+ SupportedCodeActions: map[file.Kind]map[protocol.CodeActionKind]bool{
+ file.Go: {
protocol.SourceFixAll: true,
protocol.SourceOrganizeImports: true,
protocol.QuickFix: true,
@@ -109,13 +110,13 @@
protocol.RefactorInline: true,
protocol.RefactorExtract: true,
},
- Mod: {
+ file.Mod: {
protocol.SourceOrganizeImports: true,
protocol.QuickFix: true,
},
- Work: {},
- Sum: {},
- Tmpl: {},
+ file.Work: {},
+ file.Sum: {},
+ file.Tmpl: {},
},
SupportedCommands: commands,
},
@@ -252,7 +253,7 @@
// ServerOptions holds LSP-specific configuration that is provided by the
// server.
type ServerOptions struct {
- SupportedCodeActions map[FileKind]map[protocol.CodeActionKind]bool
+ SupportedCodeActions map[file.Kind]map[protocol.CodeActionKind]bool
SupportedCommands []string
}
diff --git a/gopls/internal/lsp/source/references.go b/gopls/internal/lsp/source/references.go
index 295bce1..8030ef3 100644
--- a/gopls/internal/lsp/source/references.go
+++ b/gopls/internal/lsp/source/references.go
@@ -26,6 +26,7 @@
"golang.org/x/sync/errgroup"
"golang.org/x/tools/go/types/objectpath"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/gopls/internal/lsp/source/methodsets"
@@ -35,7 +36,7 @@
// References returns a list of all references (sorted with
// definitions before uses) to the object denoted by the identifier at
// the given file/position, searching the entire workspace.
-func References(ctx context.Context, snapshot Snapshot, fh FileHandle, pp protocol.Position, includeDeclaration bool) ([]protocol.Location, error) {
+func References(ctx context.Context, snapshot Snapshot, fh file.Handle, pp protocol.Position, includeDeclaration bool) ([]protocol.Location, error) {
references, err := references(ctx, snapshot, fh, pp, includeDeclaration)
if err != nil {
return nil, err
@@ -58,7 +59,7 @@
// references returns a list of all references (sorted with
// definitions before uses) to the object denoted by the identifier at
// the given file/position, searching the entire workspace.
-func references(ctx context.Context, snapshot Snapshot, f FileHandle, pp protocol.Position, includeDeclaration bool) ([]reference, error) {
+func references(ctx context.Context, snapshot Snapshot, f file.Handle, pp protocol.Position, includeDeclaration bool) ([]reference, error) {
ctx, done := event.Start(ctx, "source.references")
defer done()
diff --git a/gopls/internal/lsp/source/rename.go b/gopls/internal/lsp/source/rename.go
index 4075436..936ef6a 100644
--- a/gopls/internal/lsp/source/rename.go
+++ b/gopls/internal/lsp/source/rename.go
@@ -60,6 +60,7 @@
"golang.org/x/tools/go/types/objectpath"
"golang.org/x/tools/go/types/typeutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
"golang.org/x/tools/internal/diff"
@@ -94,7 +95,7 @@
// The returned usererr is intended to be displayed to the user to explain why
// the prepare fails. Probably we could eliminate the redundancy in returning
// two errors, but for now this is done defensively.
-func PrepareRename(ctx context.Context, snapshot Snapshot, f FileHandle, pp protocol.Position) (_ *PrepareItem, usererr, err error) {
+func PrepareRename(ctx context.Context, snapshot Snapshot, f file.Handle, pp protocol.Position) (_ *PrepareItem, usererr, err error) {
ctx, done := event.Start(ctx, "source.PrepareRename")
defer done()
@@ -212,7 +213,7 @@
// Rename returns a map of TextEdits for each file modified when renaming a
// given identifier within a package and a boolean value of true for renaming
// package and false otherwise.
-func Rename(ctx context.Context, snapshot Snapshot, f FileHandle, pp protocol.Position, newName string) (map[protocol.DocumentURI][]protocol.TextEdit, bool, error) {
+func Rename(ctx context.Context, snapshot Snapshot, f file.Handle, pp protocol.Position, newName string) (map[protocol.DocumentURI][]protocol.TextEdit, bool, error) {
ctx, done := event.Start(ctx, "source.Rename")
defer done()
@@ -286,7 +287,7 @@
}
// renameOrdinary renames an ordinary (non-package) name throughout the workspace.
-func renameOrdinary(ctx context.Context, snapshot Snapshot, f FileHandle, pp protocol.Position, newName string) (map[protocol.DocumentURI][]diff.Edit, error) {
+func renameOrdinary(ctx context.Context, snapshot Snapshot, f file.Handle, pp protocol.Position, newName string) (map[protocol.DocumentURI][]diff.Edit, error) {
// Type-check the referring package and locate the object(s).
//
// Unlike NarrowestPackageForFile, this operation prefers the
@@ -637,7 +638,7 @@
}
// renamePackageName renames package declarations, imports, and go.mod files.
-func renamePackageName(ctx context.Context, s Snapshot, f FileHandle, newName PackageName) (map[protocol.DocumentURI][]diff.Edit, error) {
+func renamePackageName(ctx context.Context, s Snapshot, f file.Handle, newName PackageName) (map[protocol.DocumentURI][]diff.Edit, error) {
// Rename the package decl and all imports.
renamingEdits, err := renamePackage(ctx, s, f, newName)
if err != nil {
@@ -740,7 +741,7 @@
// It updates package clauses and import paths for the renamed package as well
// as any other packages affected by the directory renaming among all packages
// known to the snapshot.
-func renamePackage(ctx context.Context, s Snapshot, f FileHandle, newName PackageName) (map[protocol.DocumentURI][]diff.Edit, error) {
+func renamePackage(ctx context.Context, s Snapshot, f file.Handle, newName PackageName) (map[protocol.DocumentURI][]diff.Edit, error) {
if strings.HasSuffix(string(newName), "_test") {
return nil, fmt.Errorf("cannot rename to _test package")
}
@@ -1245,7 +1246,7 @@
// whether the position ppos lies within it.
//
// Note: also used by references.
-func parsePackageNameDecl(ctx context.Context, snapshot Snapshot, fh FileHandle, ppos protocol.Position) (*ParsedGoFile, bool, error) {
+func parsePackageNameDecl(ctx context.Context, snapshot Snapshot, fh file.Handle, ppos protocol.Position) (*ParsedGoFile, bool, error) {
pgf, err := snapshot.ParseGo(ctx, fh, ParseHeader)
if err != nil {
return nil, false, err
diff --git a/gopls/internal/lsp/source/signature_help.go b/gopls/internal/lsp/source/signature_help.go
index 3d1514a..0c58f0a 100644
--- a/gopls/internal/lsp/source/signature_help.go
+++ b/gopls/internal/lsp/source/signature_help.go
@@ -14,11 +14,12 @@
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/internal/event"
)
-func SignatureHelp(ctx context.Context, snapshot Snapshot, fh FileHandle, position protocol.Position) (*protocol.SignatureInformation, int, error) {
+func SignatureHelp(ctx context.Context, snapshot Snapshot, fh file.Handle, position protocol.Position) (*protocol.SignatureInformation, int, error) {
ctx, done := event.Start(ctx, "source.SignatureHelp")
defer done()
diff --git a/gopls/internal/lsp/source/stub.go b/gopls/internal/lsp/source/stub.go
index 64cec26..d93712c 100644
--- a/gopls/internal/lsp/source/stub.go
+++ b/gopls/internal/lsp/source/stub.go
@@ -19,6 +19,7 @@
"golang.org/x/tools/go/analysis"
"golang.org/x/tools/go/ast/astutil"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/analysis/stubmethods"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
@@ -30,7 +31,7 @@
// stubSuggestedFixFunc returns a suggested fix to declare the missing
// methods of the concrete type that is assigned to an interface type
// at the cursor position.
-func stubSuggestedFixFunc(ctx context.Context, snapshot Snapshot, fh FileHandle, rng protocol.Range) ([]protocol.TextDocumentEdit, error) {
+func stubSuggestedFixFunc(ctx context.Context, snapshot Snapshot, fh file.Handle, rng protocol.Range) ([]protocol.TextDocumentEdit, error) {
pkg, pgf, err := NarrowestPackageForFile(ctx, snapshot, fh.URI())
if err != nil {
return nil, fmt.Errorf("GetTypedFile: %w", err)
diff --git a/gopls/internal/lsp/source/symbols.go b/gopls/internal/lsp/source/symbols.go
index a5c015e..8369043 100644
--- a/gopls/internal/lsp/source/symbols.go
+++ b/gopls/internal/lsp/source/symbols.go
@@ -11,11 +11,12 @@
"go/token"
"go/types"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/internal/event"
)
-func DocumentSymbols(ctx context.Context, snapshot Snapshot, fh FileHandle) ([]protocol.DocumentSymbol, error) {
+func DocumentSymbols(ctx context.Context, snapshot Snapshot, fh file.Handle) ([]protocol.DocumentSymbol, error) {
ctx, done := event.Start(ctx, "source.DocumentSymbols")
defer done()
diff --git a/gopls/internal/lsp/source/type_definition.go b/gopls/internal/lsp/source/type_definition.go
index 6c26b16..2a09c59 100644
--- a/gopls/internal/lsp/source/type_definition.go
+++ b/gopls/internal/lsp/source/type_definition.go
@@ -10,12 +10,13 @@
"go/token"
"golang.org/x/tools/gopls/internal/bug"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/internal/event"
)
// TypeDefinition handles the textDocument/typeDefinition request for Go files.
-func TypeDefinition(ctx context.Context, snapshot Snapshot, fh FileHandle, position protocol.Position) ([]protocol.Location, error) {
+func TypeDefinition(ctx context.Context, snapshot Snapshot, fh file.Handle, position protocol.Position) ([]protocol.Location, error) {
ctx, done := event.Start(ctx, "source.TypeDefinition")
defer done()
diff --git a/gopls/internal/lsp/source/util.go b/gopls/internal/lsp/source/util.go
index 23510e9..8c8f5f3 100644
--- a/gopls/internal/lsp/source/util.go
+++ b/gopls/internal/lsp/source/util.go
@@ -81,25 +81,6 @@
// https://golang.org/s/generatedcode
var generatedRx = regexp.MustCompile(`// .*DO NOT EDIT\.?`)
-// FileKindForLang returns the file kind associated with the given language ID,
-// or UnknownKind if the language ID is not recognized.
-func FileKindForLang(langID string) FileKind {
- switch langID {
- case "go":
- return Go
- case "go.mod":
- return Mod
- case "go.sum":
- return Sum
- case "tmpl", "gotmpl":
- return Tmpl
- case "go.work":
- return Work
- default:
- return UnknownKind
- }
-}
-
// nodeAtPos returns the index and the node whose position is contained inside
// the node list.
func nodeAtPos(nodes []ast.Node, pos token.Pos) (ast.Node, int) {
diff --git a/gopls/internal/lsp/source/view.go b/gopls/internal/lsp/source/view.go
index fef6064..8620c42 100644
--- a/gopls/internal/lsp/source/view.go
+++ b/gopls/internal/lsp/source/view.go
@@ -7,7 +7,6 @@
import (
"bytes"
"context"
- "crypto/sha256"
"encoding/json"
"errors"
"fmt"
@@ -22,6 +21,7 @@
"golang.org/x/tools/go/analysis"
"golang.org/x/tools/go/packages"
"golang.org/x/tools/go/types/objectpath"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/progress"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/safetoken"
@@ -64,7 +64,7 @@
// language different from the file name heuristic, e.g. that
// an .html file actually contains Go "html/template" syntax,
// or even that a .go file contains Python.
- FileKind(FileHandle) FileKind
+ FileKind(file.Handle) file.Kind
// Options returns the options associated with this snapshot.
Options() *Options
@@ -79,12 +79,12 @@
// A Snapshot is a caching implementation of FileSource whose
// ReadFile method returns consistent information about the existence
// and content of each file throughout its lifetime.
- FileSource
+ file.Source
// FindFile returns the FileHandle for the given URI, if it is already
// in the given snapshot.
// TODO(adonovan): delete this operation; use ReadFile instead.
- FindFile(uri protocol.DocumentURI) FileHandle
+ FindFile(uri protocol.DocumentURI) file.Handle
// AwaitInitialized waits until the snapshot's view is initialized.
AwaitInitialized(ctx context.Context)
@@ -97,12 +97,12 @@
IgnoredFile(uri protocol.DocumentURI) bool
// Templates returns the .tmpl files
- Templates() map[protocol.DocumentURI]FileHandle
+ Templates() map[protocol.DocumentURI]file.Handle
// ParseGo returns the parsed AST for the file.
// If the file is not available, returns nil and an error.
// Position information is added to FileSet().
- ParseGo(ctx context.Context, fh FileHandle, mode parser.Mode) (*ParsedGoFile, error)
+ ParseGo(ctx context.Context, fh file.Handle, mode parser.Mode) (*ParsedGoFile, error)
// Analyze runs the specified analyzers on the given packages at this snapshot.
//
@@ -135,11 +135,11 @@
ModFiles() []protocol.DocumentURI
// ParseMod is used to parse go.mod files.
- ParseMod(ctx context.Context, fh FileHandle) (*ParsedModule, error)
+ ParseMod(ctx context.Context, fh file.Handle) (*ParsedModule, error)
// ModWhy returns the results of `go mod why` for the module specified by
// the given go.mod file.
- ModWhy(ctx context.Context, fh FileHandle) (map[string]string, error)
+ ModWhy(ctx context.Context, fh file.Handle) (map[string]string, error)
// ModTidy returns the results of `go mod tidy` for the module specified by
// the given go.mod file.
@@ -156,7 +156,7 @@
WorkFile() protocol.DocumentURI
// ParseWork is used to parse go.work files.
- ParseWork(ctx context.Context, fh FileHandle) (*ParsedWorkFile, error)
+ ParseWork(ctx context.Context, fh file.Handle) (*ParsedWorkFile, error)
// BuiltinFile returns information about the special builtin package.
BuiltinFile(ctx context.Context) (*ParsedGoFile, error)
@@ -432,21 +432,11 @@
// By far the most common of these is a change to file state, but a query of
// module upgrade information or vulnerabilities also affects gopls' behavior.
type StateChange struct {
- Files map[protocol.DocumentURI]FileHandle
+ Files map[protocol.DocumentURI]file.Handle
ModuleUpgrades map[protocol.DocumentURI]map[string]string
Vulns map[protocol.DocumentURI]*vulncheck.Result
}
-// A FileSource maps URIs to FileHandles.
-type FileSource interface {
- // ReadFile returns the FileHandle for a given URI, either by
- // reading the content of the file or by obtaining it from a cache.
- //
- // Invariant: ReadFile must only return an error in the case of context
- // cancellation. If ctx.Err() is nil, the resulting error must also be nil.
- ReadFile(ctx context.Context, uri protocol.DocumentURI) (FileHandle, error)
-}
-
// A MetadataSource maps package IDs to metadata.
//
// TODO(rfindley): replace this with a concrete metadata graph, once it is
@@ -713,60 +703,12 @@
*pmetas = res
}
-var ErrViewExists = errors.New("view already exists for session")
-
-// FileModification represents a modification to a file.
-type FileModification struct {
- URI protocol.DocumentURI
- Action FileAction
-
- // OnDisk is true if a watched file is changed on disk.
- // If true, Version will be -1 and Text will be nil.
- OnDisk bool
-
- // Version will be -1 and Text will be nil when they are not supplied,
- // specifically on textDocument/didClose and for on-disk changes.
- Version int32
- Text []byte
-
- // LanguageID is only sent from the language client on textDocument/didOpen.
- LanguageID string
-}
-
-type FileAction int
-
-const (
- UnknownFileAction = FileAction(iota)
- Open
- Change
- Close
- Save
- Create
- Delete
+var (
+ ErrViewExists = errors.New("view already exists for session")
+ ErrTmpModfileUnsupported = errors.New("-modfile is unsupported for this Go version")
+ ErrNoModOnDisk = errors.New("go.mod file is not on disk")
)
-func (a FileAction) String() string {
- switch a {
- case Open:
- return "Open"
- case Change:
- return "Change"
- case Close:
- return "Close"
- case Save:
- return "Save"
- case Create:
- return "Create"
- case Delete:
- return "Delete"
- default:
- return "Unknown"
- }
-}
-
-var ErrTmpModfileUnsupported = errors.New("-modfile is unsupported for this Go version")
-var ErrNoModOnDisk = errors.New("go.mod file is not on disk")
-
func IsNonFatalGoModError(err error) bool {
return err == ErrTmpModfileUnsupported || err == ErrNoModOnDisk
}
@@ -784,115 +726,6 @@
ParseFull = parser.AllErrors | parser.ParseComments | SkipObjectResolution
)
-// A FileHandle represents the URI, content, hash, and optional
-// version of a file tracked by the LSP session.
-//
-// File content may be provided by the file system (for Saved files)
-// or from an overlay, for open files with unsaved edits.
-// A FileHandle may record an attempt to read a non-existent file,
-// in which case Content returns an error.
-type FileHandle interface {
- // URI is the URI for this file handle.
- // TODO(rfindley): this is not actually well-defined. In some cases, there
- // may be more than one URI that resolve to the same FileHandle. Which one is
- // this?
- URI() protocol.DocumentURI
- // FileIdentity returns a FileIdentity for the file, even if there was an
- // error reading it.
- FileIdentity() FileIdentity
- // SameContentsOnDisk reports whether the file has the same content on disk:
- // it is false for files open on an editor with unsaved edits.
- SameContentsOnDisk() bool
- // Version returns the file version, as defined by the LSP client.
- // For on-disk file handles, Version returns 0.
- Version() int32
- // Content returns the contents of a file.
- // If the file is not available, returns a nil slice and an error.
- Content() ([]byte, error)
-}
-
-// A Hash is a cryptographic digest of the contents of a file.
-// (Although at 32B it is larger than a 16B string header, it is smaller
-// and has better locality than the string header + 64B of hex digits.)
-type Hash [sha256.Size]byte
-
-// HashOf returns the hash of some data.
-func HashOf(data []byte) Hash {
- return Hash(sha256.Sum256(data))
-}
-
-// Hashf returns the hash of a printf-formatted string.
-func Hashf(format string, args ...interface{}) Hash {
- // Although this looks alloc-heavy, it is faster than using
- // Fprintf on sha256.New() because the allocations don't escape.
- return HashOf([]byte(fmt.Sprintf(format, args...)))
-}
-
-// String returns the digest as a string of hex digits.
-func (h Hash) String() string {
- return fmt.Sprintf("%64x", [sha256.Size]byte(h))
-}
-
-// Less returns true if the given hash is less than the other.
-func (h Hash) Less(other Hash) bool {
- return bytes.Compare(h[:], other[:]) < 0
-}
-
-// XORWith updates *h to *h XOR h2.
-func (h *Hash) XORWith(h2 Hash) {
- // Small enough that we don't need crypto/subtle.XORBytes.
- for i := range h {
- h[i] ^= h2[i]
- }
-}
-
-// FileIdentity uniquely identifies a file at a version from a FileSystem.
-type FileIdentity struct {
- URI protocol.DocumentURI
- Hash Hash // digest of file contents
-}
-
-func (id FileIdentity) String() string {
- return fmt.Sprintf("%s%s", id.URI, id.Hash)
-}
-
-// FileKind describes the kind of the file in question.
-// It can be one of Go,mod, Sum, or Tmpl.
-type FileKind int
-
-const (
- // UnknownKind is a file type we don't know about.
- UnknownKind = FileKind(iota)
-
- // Go is a normal go source file.
- Go
- // Mod is a go.mod file.
- Mod
- // Sum is a go.sum file.
- Sum
- // Tmpl is a template file.
- Tmpl
- // Work is a go.work file.
- Work
-)
-
-func (k FileKind) String() string {
- switch k {
- case Go:
- return "go"
- case Mod:
- return "go.mod"
- case Sum:
- return "go.sum"
- case Tmpl:
- return "tmpl"
- case Work:
- return "go.work"
- default:
- return fmt.Sprintf("internal error: unknown file kind %d", k)
- }
-}
-
// Analyzer represents a go/analysis analyzer with some boolean properties
// that let the user know how to use the analyzer.
type Analyzer struct {
diff --git a/gopls/internal/lsp/symbols.go b/gopls/internal/lsp/symbols.go
index 3fe2824..e220a2e 100644
--- a/gopls/internal/lsp/symbols.go
+++ b/gopls/internal/lsp/symbols.go
@@ -7,6 +7,7 @@
import (
"context"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/gopls/internal/lsp/template"
@@ -18,16 +19,16 @@
ctx, done := event.Start(ctx, "lsp.Server.documentSymbol", tag.URI.Of(params.TextDocument.URI))
defer done()
- snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, source.UnknownKind)
+ snapshot, fh, ok, release, err := s.beginFileRequest(ctx, params.TextDocument.URI, file.UnknownKind)
defer release()
if !ok {
return []interface{}{}, err
}
var docSymbols []protocol.DocumentSymbol
switch snapshot.FileKind(fh) {
- case source.Tmpl:
+ case file.Tmpl:
docSymbols, err = template.DocumentSymbols(snapshot, fh)
- case source.Go:
+ case file.Go:
docSymbols, err = source.DocumentSymbols(ctx, snapshot, fh)
default:
return []interface{}{}, nil
diff --git a/gopls/internal/lsp/template/completion.go b/gopls/internal/lsp/template/completion.go
index fbb2744..7be1b43 100644
--- a/gopls/internal/lsp/template/completion.go
+++ b/gopls/internal/lsp/template/completion.go
@@ -12,6 +12,7 @@
"go/token"
"strings"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
)
@@ -25,7 +26,7 @@
syms map[string]symbol
}
-func Completion(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, pos protocol.Position, context protocol.CompletionContext) (*protocol.CompletionList, error) {
+func Completion(ctx context.Context, snapshot source.Snapshot, fh file.Handle, pos protocol.Position, context protocol.CompletionContext) (*protocol.CompletionList, error) {
all := New(snapshot.Templates())
var start int // the beginning of the Token (completed or not)
syms := make(map[string]symbol)
@@ -43,7 +44,7 @@
}
if p == nil {
// this cannot happen unless the search missed a template file
- return nil, fmt.Errorf("%s not found", fh.FileIdentity().URI.Path())
+ return nil, fmt.Errorf("%s not found", fh.Identity().URI.Path())
}
c := completer{
p: p,
diff --git a/gopls/internal/lsp/template/highlight.go b/gopls/internal/lsp/template/highlight.go
index 47069b1..3d65403 100644
--- a/gopls/internal/lsp/template/highlight.go
+++ b/gopls/internal/lsp/template/highlight.go
@@ -9,11 +9,12 @@
"fmt"
"regexp"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
)
-func Highlight(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, loc protocol.Position) ([]protocol.DocumentHighlight, error) {
+func Highlight(ctx context.Context, snapshot source.Snapshot, fh file.Handle, loc protocol.Position) ([]protocol.DocumentHighlight, error) {
buf, err := fh.Content()
if err != nil {
return nil, err
diff --git a/gopls/internal/lsp/template/implementations.go b/gopls/internal/lsp/template/implementations.go
index 7f081de..14c62c1 100644
--- a/gopls/internal/lsp/template/implementations.go
+++ b/gopls/internal/lsp/template/implementations.go
@@ -11,6 +11,7 @@
"strconv"
"time"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
)
@@ -21,7 +22,7 @@
// Diagnose returns parse errors. There is only one.
// The errors are not always helpful. For instance { {end}}
// will likely point to the end of the file.
-func Diagnose(f source.FileHandle) []*source.Diagnostic {
+func Diagnose(f file.Handle) []*source.Diagnostic {
// no need for skipTemplate check, as Diagnose is called on the
// snapshot's template files
buf, err := f.Content()
@@ -72,7 +73,7 @@
// does not understand scoping (if any) in templates. This code is
// for definitions, type definitions, and implementations.
// Results only for variables and templates.
-func Definition(snapshot source.Snapshot, fh source.FileHandle, loc protocol.Position) ([]protocol.Location, error) {
+func Definition(snapshot source.Snapshot, fh file.Handle, loc protocol.Position) ([]protocol.Location, error) {
x, _, err := symAtPosition(fh, loc)
if err != nil {
return nil, err
@@ -92,7 +93,7 @@
return ans, nil
}
-func Hover(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, position protocol.Position) (*protocol.Hover, error) {
+func Hover(ctx context.Context, snapshot source.Snapshot, fh file.Handle, position protocol.Position) (*protocol.Hover, error) {
sym, p, err := symAtPosition(fh, position)
if sym == nil || err != nil {
return nil, err
@@ -123,7 +124,7 @@
return &ans, nil
}
-func References(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, params *protocol.ReferenceParams) ([]protocol.Location, error) {
+func References(ctx context.Context, snapshot source.Snapshot, fh file.Handle, params *protocol.ReferenceParams) ([]protocol.Location, error) {
sym, _, err := symAtPosition(fh, params.Position)
if sym == nil || err != nil || sym.name == "" {
return nil, err
diff --git a/gopls/internal/lsp/template/parse.go b/gopls/internal/lsp/template/parse.go
index d7c6f75..ab09bce 100644
--- a/gopls/internal/lsp/template/parse.go
+++ b/gopls/internal/lsp/template/parse.go
@@ -24,8 +24,8 @@
"text/template/parse"
"unicode/utf8"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
- "golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
)
@@ -69,7 +69,7 @@
// New returns the Parses of the snapshot's tmpl files
// (maybe cache these, but then avoiding import cycles needs code rearrangements)
-func New(tmpls map[protocol.DocumentURI]source.FileHandle) *All {
+func New(tmpls map[protocol.DocumentURI]file.Handle) *All {
all := make(map[protocol.DocumentURI]*Parsed)
for k, v := range tmpls {
buf, err := v.Content()
@@ -376,7 +376,7 @@
return pos
}
-func symAtPosition(fh source.FileHandle, loc protocol.Position) (*symbol, *Parsed, error) {
+func symAtPosition(fh file.Handle, loc protocol.Position) (*symbol, *Parsed, error) {
buf, err := fh.Content()
if err != nil {
return nil, nil, err
diff --git a/gopls/internal/lsp/template/symbols.go b/gopls/internal/lsp/template/symbols.go
index 356705f..bc2e278 100644
--- a/gopls/internal/lsp/template/symbols.go
+++ b/gopls/internal/lsp/template/symbols.go
@@ -11,6 +11,7 @@
"text/template/parse"
"unicode/utf8"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
@@ -193,7 +194,7 @@
// DocumentSymbols returns a hierarchy of the symbols defined in a template file.
// (The hierarchy is flat. SymbolInformation might be better.)
-func DocumentSymbols(snapshot source.Snapshot, fh source.FileHandle) ([]protocol.DocumentSymbol, error) {
+func DocumentSymbols(snapshot source.Snapshot, fh file.Handle) ([]protocol.DocumentSymbol, error) {
buf, err := fh.Content()
if err != nil {
return nil, err
diff --git a/gopls/internal/lsp/text_synchronization.go b/gopls/internal/lsp/text_synchronization.go
index 28c3a81..3523c62 100644
--- a/gopls/internal/lsp/text_synchronization.go
+++ b/gopls/internal/lsp/text_synchronization.go
@@ -12,6 +12,7 @@
"path/filepath"
"sync"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
@@ -109,9 +110,9 @@
return err
}
}
- return s.didModifyFiles(ctx, []source.FileModification{{
+ return s.didModifyFiles(ctx, []file.Modification{{
URI: uri,
- Action: source.Open,
+ Action: file.Open,
Version: params.TextDocument.Version,
Text: []byte(params.TextDocument.Text),
LanguageID: params.TextDocument.LanguageID,
@@ -131,13 +132,13 @@
if err != nil {
return err
}
- c := source.FileModification{
+ c := file.Modification{
URI: uri,
- Action: source.Change,
+ Action: file.Change,
Version: params.TextDocument.Version,
Text: text,
}
- if err := s.didModifyFiles(ctx, []source.FileModification{c}, FromDidChange); err != nil {
+ if err := s.didModifyFiles(ctx, []file.Modification{c}, FromDidChange); err != nil {
return err
}
return s.warnAboutModifyingGeneratedFiles(ctx, uri)
@@ -185,14 +186,14 @@
ctx, done := event.Start(ctx, "lsp.Server.didChangeWatchedFiles")
defer done()
- var modifications []source.FileModification
+ var modifications []file.Modification
for _, change := range params.Changes {
uri := change.URI
if !uri.IsFile() {
continue
}
action := changeTypeToFileAction(change.Type)
- modifications = append(modifications, source.FileModification{
+ modifications = append(modifications, file.Modification{
URI: uri,
Action: action,
OnDisk: true,
@@ -209,14 +210,14 @@
if !uri.IsFile() {
return nil
}
- c := source.FileModification{
+ c := file.Modification{
URI: uri,
- Action: source.Save,
+ Action: file.Save,
}
if params.Text != nil {
c.Text = []byte(*params.Text)
}
- return s.didModifyFiles(ctx, []source.FileModification{c}, FromDidSave)
+ return s.didModifyFiles(ctx, []file.Modification{c}, FromDidSave)
}
func (s *server) didClose(ctx context.Context, params *protocol.DidCloseTextDocumentParams) error {
@@ -227,17 +228,17 @@
if !uri.IsFile() {
return nil
}
- return s.didModifyFiles(ctx, []source.FileModification{
+ return s.didModifyFiles(ctx, []file.Modification{
{
URI: uri,
- Action: source.Close,
+ Action: file.Close,
Version: -1,
Text: nil,
},
}, FromDidClose)
}
-func (s *server) didModifyFiles(ctx context.Context, modifications []source.FileModification, cause ModificationSource) error {
+func (s *server) didModifyFiles(ctx context.Context, modifications []file.Modification, cause ModificationSource) error {
// wg guards two conditions:
// 1. didModifyFiles is complete
// 2. the goroutine diagnosing changes on behalf of didModifyFiles is
@@ -277,7 +278,7 @@
// Build a lookup map for file modifications, so that we can later join
// with the snapshot file associations.
- modMap := make(map[protocol.DocumentURI]source.FileModification)
+ modMap := make(map[protocol.DocumentURI]file.Modification)
for _, mod := range modifications {
modMap[mod.URI] = mod
}
@@ -292,7 +293,7 @@
for snapshot, uris := range snapshots {
for _, uri := range uris {
mod := modMap[uri]
- if snapshot.Options().ChattyDiagnostics || mod.Action == source.Open || mod.Action == source.Close {
+ if snapshot.Options().ChattyDiagnostics || mod.Action == file.Open || mod.Action == file.Close {
s.mustPublishDiagnostics(uri)
}
}
@@ -364,14 +365,14 @@
return content, nil
}
-func changeTypeToFileAction(ct protocol.FileChangeType) source.FileAction {
+func changeTypeToFileAction(ct protocol.FileChangeType) file.Action {
switch ct {
case protocol.Changed:
- return source.Change
+ return file.Change
case protocol.Created:
- return source.Create
+ return file.Create
case protocol.Deleted:
- return source.Delete
+ return file.Delete
}
- return source.UnknownFileAction
+ return file.UnknownAction
}
diff --git a/gopls/internal/lsp/work/completion.go b/gopls/internal/lsp/work/completion.go
index d4de255..e450287 100644
--- a/gopls/internal/lsp/work/completion.go
+++ b/gopls/internal/lsp/work/completion.go
@@ -13,12 +13,13 @@
"sort"
"strings"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
)
-func Completion(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, position protocol.Position) (*protocol.CompletionList, error) {
+func Completion(ctx context.Context, snapshot source.Snapshot, fh file.Handle, position protocol.Position) (*protocol.CompletionList, error) {
ctx, done := event.Start(ctx, "work.Completion")
defer done()
diff --git a/gopls/internal/lsp/work/diagnostics.go b/gopls/internal/lsp/work/diagnostics.go
index e0f9b4d..57b5eb7 100644
--- a/gopls/internal/lsp/work/diagnostics.go
+++ b/gopls/internal/lsp/work/diagnostics.go
@@ -11,6 +11,7 @@
"path/filepath"
"golang.org/x/mod/modfile"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
@@ -45,7 +46,7 @@
return reports, nil
}
-func DiagnosticsForWork(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]*source.Diagnostic, error) {
+func DiagnosticsForWork(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]*source.Diagnostic, error) {
pw, err := snapshot.ParseWork(ctx, fh)
if err != nil {
if pw == nil || len(pw.ParseErrors) == 0 {
diff --git a/gopls/internal/lsp/work/format.go b/gopls/internal/lsp/work/format.go
index 70cbe59..4fc6dd7 100644
--- a/gopls/internal/lsp/work/format.go
+++ b/gopls/internal/lsp/work/format.go
@@ -8,12 +8,13 @@
"context"
"golang.org/x/mod/modfile"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
)
-func Format(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle) ([]protocol.TextEdit, error) {
+func Format(ctx context.Context, snapshot source.Snapshot, fh file.Handle) ([]protocol.TextEdit, error) {
ctx, done := event.Start(ctx, "work.Format")
defer done()
diff --git a/gopls/internal/lsp/work/hover.go b/gopls/internal/lsp/work/hover.go
index d777acd..0e0f040 100644
--- a/gopls/internal/lsp/work/hover.go
+++ b/gopls/internal/lsp/work/hover.go
@@ -10,12 +10,13 @@
"fmt"
"golang.org/x/mod/modfile"
+ "golang.org/x/tools/gopls/internal/file"
"golang.org/x/tools/gopls/internal/lsp/protocol"
"golang.org/x/tools/gopls/internal/lsp/source"
"golang.org/x/tools/internal/event"
)
-func Hover(ctx context.Context, snapshot source.Snapshot, fh source.FileHandle, position protocol.Position) (*protocol.Hover, error) {
+func Hover(ctx context.Context, snapshot source.Snapshot, fh file.Handle, position protocol.Position) (*protocol.Hover, error) {
// We only provide hover information for the view's go.work file.
if fh.URI() != snapshot.WorkFile() {
return nil, nil