From 6bbf83c794180bd9e76d77132ef767bc1993a5d8 Mon Sep 17 00:00:00 2001 From: Myzel394 <50424412+Myzel394@users.noreply.github.com> Date: Sun, 18 Aug 2024 18:47:17 +0200 Subject: [PATCH] feat(wireguard): Add hover support --- handlers/wireguard/hover.go | 95 +++++++++++++++++++++++ handlers/wireguard/text-document-hover.go | 38 +++++++++ handlers/wireguard/wg-parser.go | 10 +++ root-handler/text-document-hover.go | 3 + 4 files changed, 146 insertions(+) create mode 100644 handlers/wireguard/hover.go create mode 100644 handlers/wireguard/text-document-hover.go diff --git a/handlers/wireguard/hover.go b/handlers/wireguard/hover.go new file mode 100644 index 0000000..5e3d3da --- /dev/null +++ b/handlers/wireguard/hover.go @@ -0,0 +1,95 @@ +package wireguard + +import ( + docvalues "config-lsp/doc-values" + "fmt" + "strings" +) + +func (p wireguardProperty) getHoverInfo(cursor uint32, section *wireguardSection) []string { + if cursor <= p.Key.Location.End { + options, found := optionsHeaderMap[*section.Name] + + if !found { + return []string{} + } + + option, found := options[p.Key.Name] + + if !found { + return []string{} + } + + return strings.Split(option.Documentation, "\n") + } + + options, found := optionsHeaderMap[*section.Name] + + if !found { + return []string{} + } + + if option, found := options[p.Key.Name]; found { + return option.GetTypeDescription() + } + + return []string{} +} + +func (p wireguardParser) getHeaderInfo(line uint32, cursor uint32) []string { + section := p.getSectionByLine(line) + + if section == nil { + return []string{} + } + + sectionInfo := section.getHeaderInfo() + + property, _ := section.findProperty(line) + + if property == nil { + return sectionInfo + } + + propertyInfo := property.getHoverInfo(cursor, section) + + if len(propertyInfo) == 0 { + return sectionInfo + } + + contents := append(sectionInfo, []string{ + "", + fmt.Sprintf("### %s", property.Key.Name), + }...) + contents = append(contents, propertyInfo...) + + return contents +} + +func (p wireguardSection) getHeaderInfo() []string { + if p.Name == nil { + return []string{} + } + + contents := []string{ + fmt.Sprintf("## [%s]", *p.Name), + "", + } + + var option *docvalues.EnumString = nil + + switch *p.Name { + case "Interface": + option = &headerInterfaceEnum + case "Peer": + option = &headerPeerEnum + } + + if option == nil { + return contents + } + + contents = append(contents, strings.Split(option.Documentation, "\n")...) + + return contents +} diff --git a/handlers/wireguard/text-document-hover.go b/handlers/wireguard/text-document-hover.go new file mode 100644 index 0000000..82d92d9 --- /dev/null +++ b/handlers/wireguard/text-document-hover.go @@ -0,0 +1,38 @@ +package wireguard + +import ( + "strings" + + "github.com/tliron/glsp" + protocol "github.com/tliron/glsp/protocol_3_16" +) + +func TextDocumentHover( + context *glsp.Context, + params *protocol.HoverParams, +) (*protocol.Hover, error) { + // cursor := params.Position.Character + + parser := documentParserMap[params.TextDocument.URI] + + switch parser.getTypeByLine(params.Position.Line) { + case LineTypeComment: + return nil, nil + case LineTypeEmpty: + return nil, nil + case LineTypeHeader: + fallthrough + case LineTypeProperty: + documentation := parser.getHeaderInfo(params.Position.Line, params.Position.Character) + + hover := protocol.Hover{ + Contents: protocol.MarkupContent{ + Kind: protocol.MarkupKindMarkdown, + Value: strings.Join(documentation, "\n"), + }, + } + return &hover, nil + } + + return nil, nil +} diff --git a/handlers/wireguard/wg-parser.go b/handlers/wireguard/wg-parser.go index 1969aa7..9c60ba4 100644 --- a/handlers/wireguard/wg-parser.go +++ b/handlers/wireguard/wg-parser.go @@ -33,6 +33,16 @@ type wireguardParser struct { LineIndexes map[uint32]wireguardLineIndex } +func (p *wireguardParser) getSectionByLine(line uint32) *wireguardSection { + for _, section := range p.Sections { + if section.StartLine <= line && section.EndLine >= line { + return section + } + } + + return nil +} + // Search for a property by name // Returns (line number, property) func (p *wireguardParser) fetchPropertyByName(name string) (*uint32, *wireguardProperty) { diff --git a/root-handler/text-document-hover.go b/root-handler/text-document-hover.go index d61e7aa..28ec43f 100644 --- a/root-handler/text-document-hover.go +++ b/root-handler/text-document-hover.go @@ -2,6 +2,7 @@ package roothandler import ( "config-lsp/handlers/fstab" + "config-lsp/handlers/wireguard" "github.com/tliron/glsp" protocol "github.com/tliron/glsp/protocol_3_16" @@ -15,6 +16,8 @@ func TextDocumentHover(context *glsp.Context, params *protocol.HoverParams) (*pr return fstab.TextDocumentHover(context, params) case LanguageSSHDConfig: return nil, nil + case LanguageWireguard: + return wireguard.TextDocumentHover(context, params) } panic("root-handler/TextDocumentHover: unexpected language" + language)