Skip to content

Commit 862d013

Browse files
committed
support subpackages
1 parent d6502dd commit 862d013

File tree

2 files changed

+113
-11
lines changed

2 files changed

+113
-11
lines changed

cmd/godoc-mcp-server/packageInfo.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ import (
1212

1313
func getPackageInfoTool() (tool mcp.Tool, handler server.ToolHandlerFunc) {
1414
return mcp.NewTool("getPackageInfo",
15-
mcp.WithDescription("provide a golang package name,get package consts,types,functions,variables from pkg.go.dev"),
15+
mcp.WithDescription("provide a golang package name,get package consts,types,functions,variables, subpackages from pkg.go.dev"),
1616
mcp.WithString("packageName",
1717
mcp.Required(),
1818
mcp.Description("package name for search")),

pkg/godoc/package.go

Lines changed: 112 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
package godoc
22

33
import (
4+
"fmt"
45
"strings"
56

67
"github.com/PuerkitoBio/goquery"
@@ -9,11 +10,12 @@ import (
910
)
1011

1112
type PackageDocument struct {
12-
Overview string
13-
Consts []ConstBlock
14-
Variables []VariableBlock
15-
Functions []FunctionBlock
16-
Types []TypeBlock
13+
Overview string
14+
Consts []ConstBlock
15+
Variables []VariableBlock
16+
Functions []FunctionBlock
17+
Types []TypeBlock
18+
SubPackages []*SubPackage
1719
}
1820

1921
type ConstBlock struct {
@@ -49,6 +51,11 @@ type TypeMethod struct {
4951
Comment string
5052
}
5153

54+
type SubPackage struct {
55+
Name string
56+
Comment string
57+
}
58+
5259
func GetPackageDocument(pkgName string) (*PackageDocument, error) {
5360
resp, err := client().
5461
R().
@@ -88,13 +95,18 @@ func extractDocResult(html string) (*PackageDocument, error) {
8895
if err != nil {
8996
return nil, err
9097
}
98+
subPackages, err := extractSubPackages(doc)
99+
if err != nil {
100+
return nil, err
101+
}
91102

92103
return &PackageDocument{
93-
Overview: overview,
94-
Consts: consts,
95-
Variables: variables,
96-
Functions: fns,
97-
Types: types,
104+
Overview: overview,
105+
Consts: consts,
106+
Variables: variables,
107+
Functions: fns,
108+
Types: types,
109+
SubPackages: subPackages,
98110
}, nil
99111
}
100112

@@ -269,3 +281,93 @@ func extractDocTypeMethods(s *goquery.Selection) ([]TypeMethod, error) {
269281
})
270282
return methods, nil
271283
}
284+
285+
func extractSubPackages(doc *goquery.Document) ([]*SubPackage, error) {
286+
var subPackages []*SubPackage
287+
var err error
288+
289+
doc.Find("table[data-test-id='UnitDirectories-table']").
290+
Find("tbody").
291+
Children().
292+
Each(func(i int, s *goquery.Selection) {
293+
294+
v, hasSubPackage := s.Attr("data-aria-controls")
295+
fmt.Println(v, hasSubPackage, goquery.NodeName(s))
296+
297+
if hasSubPackage {
298+
// 目录要处理自己和子包
299+
dir, _err := extractSubPackageAsDir(s)
300+
if _err != nil {
301+
err = multierr.Append(err, _err)
302+
return
303+
}
304+
if dir != nil {
305+
subPackages = append(subPackages, dir)
306+
}
307+
308+
} else {
309+
subPackage, _err := extractSubPackage(s)
310+
if _err != nil {
311+
err = multierr.Append(err, _err)
312+
return
313+
}
314+
if subPackage != nil {
315+
subPackages = append(subPackages, subPackage)
316+
}
317+
}
318+
})
319+
if err != nil {
320+
return nil, err
321+
}
322+
323+
return subPackages, nil
324+
}
325+
326+
func extractSubPackage(s *goquery.Selection) (*SubPackage, error) {
327+
// Name
328+
// 有 id 优先用id
329+
// 没有 id 用 a 标签的文本
330+
name := s.AttrOr("data-id", "")
331+
if name == "" {
332+
name = s.Find("a").Text()
333+
} else {
334+
name = strings.TrimSpace(name)
335+
name = strings.ReplaceAll(name, "-", "/")
336+
}
337+
if name == "" {
338+
return nil, nil
339+
}
340+
// comment
341+
comment := s.Find("td.UnitDirectories-desktopSynopsis").Text()
342+
comment = strings.TrimSpace(comment)
343+
if comment == "" {
344+
return nil, nil
345+
}
346+
347+
return &SubPackage{
348+
Name: name,
349+
Comment: comment,
350+
}, nil
351+
}
352+
353+
func extractSubPackageAsDir(s *goquery.Selection) (*SubPackage, error) {
354+
355+
// pathCell name
356+
name := s.Find("div.UnitDirectories-pathCell").Find("span").Text()
357+
name = strings.TrimSpace(name)
358+
if name == "" {
359+
name = s.Find("a").Text()
360+
name = strings.TrimSpace(name)
361+
if name == "" {
362+
return nil, nil
363+
}
364+
}
365+
// comment
366+
comment := s.Find("td.UnitDirectories-desktopSynopsis").Text()
367+
comment = strings.TrimSpace(comment)
368+
369+
return &SubPackage{
370+
Name: name,
371+
Comment: comment,
372+
}, nil
373+
}

0 commit comments

Comments
 (0)