Skip to content

Commit 391cb0c

Browse files
authored
LSP fix type completion for same package (#4118)
1 parent 9ac413f commit 391cb0c

File tree

1 file changed

+23
-22
lines changed

1 file changed

+23
-22
lines changed

private/buf/buflsp/completion.go

Lines changed: 23 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -272,6 +272,7 @@ func completionItemsForKeyword(ctx context.Context, file *file, declPath []ast.D
272272
),
273273
typeReferencesToCompletionItems(
274274
file,
275+
findTypeFullName(file, parentDef),
275276
tokenSpan,
276277
offset,
277278
),
@@ -386,6 +387,7 @@ func completionItemsForField(ctx context.Context, file *file, declPath []ast.Dec
386387
),
387388
typeReferencesToCompletionItems(
388389
file,
390+
findTypeFullName(file, parentDef),
389391
tokenSpan,
390392
offset,
391393
),
@@ -601,14 +603,12 @@ func keywordToCompletionItem(
601603
// typeReferencesToCompletionItems returns completion items for user-defined types (messages, enums, etc).
602604
func typeReferencesToCompletionItems(
603605
current *file,
606+
parentFullName ir.FullName,
604607
span report.Span,
605608
offset int,
606609
) iter.Seq[protocol.CompletionItem] {
607610
fileSymbolTypesIter := func(yield func(*file, *symbol) bool) {
608611
for _, imported := range current.workspace.PathToFile() {
609-
if imported == current {
610-
continue
611-
}
612612
for _, symbol := range imported.referenceableSymbols {
613613
if !yield(imported, symbol) {
614614
return
@@ -619,22 +619,17 @@ func typeReferencesToCompletionItems(
619619
return func(yield func(protocol.CompletionItem) bool) {
620620
editRange := reportSpanToProtocolRange(span)
621621
prefix, suffix := splitSpan(span, offset)
622-
for file, symbol := range fileSymbolTypesIter {
622+
for _, symbol := range fileSymbolTypesIter {
623623
if !symbol.ir.Kind().IsType() {
624624
continue
625625
}
626-
var (
627-
label string
628-
kind protocol.CompletionItemKind
629-
)
630-
if file.ir.Package() == current.ir.Package() {
631-
label = symbol.ir.FullName().Name()
632-
} else {
633-
label = string(symbol.ir.FullName())
634-
}
626+
label := strings.TrimPrefix(string(symbol.ir.FullName()), string(parentFullName))
627+
label = strings.TrimPrefix(label, string(current.ir.Package()))
628+
label = strings.TrimPrefix(label, ".")
635629
if !strings.HasPrefix(label, prefix) || !strings.HasSuffix(label, suffix) {
636630
continue
637631
}
632+
var kind protocol.CompletionItemKind
638633
switch symbol.ir.Kind() {
639634
case ir.SymbolKindMessage:
640635
kind = protocol.CompletionItemKindStruct
@@ -813,17 +808,23 @@ func isNewlineOrEndOfSpan(span report.Span, offset int) bool {
813808

814809
// isProto2 returns true if the file has a syntax declaration of proto2.
815810
func isProto2(file *file) bool {
816-
body := file.ir.AST().DeclBody
817-
for decl := range seq.Values(body.Decls()) {
818-
if decl.IsZero() {
819-
continue
820-
}
821-
if kind := decl.Kind(); kind == ast.DeclKindSyntax {
822-
declSyntax := decl.AsSyntax()
823-
return declSyntax.IsSyntax() && declSyntax.Value().Span().Text() == "proto2"
811+
return file.ir.Syntax() == syntax.Proto2
812+
}
813+
814+
// findTypeFullName simply loops through and finds the type definition name.
815+
func findTypeFullName(file *file, declDef ast.DeclDef) ir.FullName {
816+
declDefSpan := declDef.Span()
817+
if declDefSpan.IsZero() {
818+
return ""
819+
}
820+
for irType := range seq.Values(file.ir.AllTypes()) {
821+
typeSpan := irType.AST().Span()
822+
if typeSpan.Start == declDefSpan.Start && typeSpan.End == declDefSpan.End {
823+
file.lsp.logger.Debug("completion: found parent type", slog.String("parent", string(irType.FullName())))
824+
return irType.FullName()
824825
}
825826
}
826-
return false
827+
return ""
827828
}
828829

829830
// resolveCompletionItem resolves additional details for a completion item.

0 commit comments

Comments
 (0)