internal/lsp: in semantic tokens, better distinguish between types and variables
If A is a type, then in
type B {
A
} it is a type, but in
type C {
A int
}
it is a variable (and similarly in function types). The old code got this wrong.
Fixes: golang/go#46068
Change-Id: Ib7320914de81d2b7377214f53f99f4fea25e00fb
Reviewed-on: https://go-review.googlesource.com/c/tools/+/318749
Run-TryBot: Peter Weinberger <pjw@google.com>
gopls-CI: kokoro <noreply+kokoro@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Trust: Peter Weinberger <pjw@google.com>
Reviewed-by: Robert Findley <rfindley@google.com>
diff --git a/internal/lsp/semantic.go b/internal/lsp/semantic.go
index b7746bf..8ef30ff 100644
--- a/internal/lsp/semantic.go
+++ b/internal/lsp/semantic.go
@@ -511,9 +511,14 @@
// (type A func(b uint64)) (err error)
// b and err should not be tokType, but tokVaraible
// and in GenDecl/TpeSpec/StructType/FieldList/Field/Ident
- // (type A struct{b uint64})
+ // (type A struct{b uint64}
+ // but on type B struct{C}), C is a type, but is not being defined.
fldm := e.stack[len(e.stack)-2]
- if _, ok := fldm.(*ast.Field); ok {
+ if fld, ok := fldm.(*ast.Field); ok {
+ // if len(fld.names) == 0 this is a tokType, being used
+ if len(fld.Names) == 0 {
+ return tokType, nil
+ }
return tokVariable, mods
}
return tokType, mods
diff --git a/internal/lsp/testdata/semantic/README.md b/internal/lsp/testdata/semantic/README.md
new file mode 100644
index 0000000..00ec19a
--- /dev/null
+++ b/internal/lsp/testdata/semantic/README.md
@@ -0,0 +1,2 @@
+The golden files are the output of `gopls semtok <src-file>`, with `-- semantic --`
+inserted as the first line (the spaces are mandatory) and an extra newline at the end.
diff --git a/internal/lsp/testdata/semantic/b.go b/internal/lsp/testdata/semantic/b.go
index e633f4e..a536f97 100644
--- a/internal/lsp/testdata/semantic/b.go
+++ b/internal/lsp/testdata/semantic/b.go
@@ -23,3 +23,12 @@
multiline */ /*
multiline
*/
+type AA int
+type BB struct {
+ AA
+}
+type CC struct {
+ AA int
+}
+type D func(aa AA) (BB error)
+type E func(AA) BB
diff --git a/internal/lsp/testdata/semantic/b.go.golden b/internal/lsp/testdata/semantic/b.go.golden
index 48be5ea..863a68c 100644
--- a/internal/lsp/testdata/semantic/b.go.golden
+++ b/internal/lsp/testdata/semantic/b.go.golden
@@ -24,4 +24,13 @@
/*⇒12,comment,[]*/multiline */ /*⇒2,comment,[]*//*
/*⇒9,comment,[]*/multiline
/*⇒2,comment,[]*/*/
+/*⇒4,keyword,[]*/type /*⇒2,type,[definition]*/AA /*⇒3,type,[defaultLibrary]*/int
+/*⇒4,keyword,[]*/type /*⇒2,type,[definition]*/BB /*⇒6,keyword,[]*/struct {
+ /*⇒2,type,[]*/AA
+}
+/*⇒4,keyword,[]*/type /*⇒2,type,[definition]*/CC /*⇒6,keyword,[]*/struct {
+ /*⇒2,variable,[definition]*/AA /*⇒3,type,[defaultLibrary]*/int
+}
+/*⇒4,keyword,[]*/type /*⇒1,type,[definition]*/D /*⇒4,keyword,[]*/func(/*⇒2,variable,[definition]*/aa /*⇒2,type,[]*/AA) (/*⇒2,variable,[definition]*/BB /*⇒5,type,[]*/error)
+/*⇒4,keyword,[]*/type /*⇒1,type,[definition]*/E /*⇒4,keyword,[]*/func(/*⇒2,type,[]*/AA) /*⇒2,type,[]*/BB