Skip to content

Commit 3302613

Browse files
committed
fix: anonymous/inaccessible structs for commentstart
1 parent 13b7bbd commit 3302613

File tree

3 files changed

+76
-14
lines changed

3 files changed

+76
-14
lines changed

pkg/analysis/commentstart/analyzer.go

+32-14
Original file line numberDiff line numberDiff line change
@@ -42,43 +42,59 @@ func run(pass *analysis.Pass) (interface{}, error) {
4242

4343
// Filter to structs so that we can iterate over fields in a struct.
4444
nodeFilter := []ast.Node{
45-
(*ast.StructType)(nil),
45+
(*ast.Field)(nil),
4646
}
4747

48-
inspect.Preorder(nodeFilter, func(n ast.Node) {
49-
sTyp, ok := n.(*ast.StructType)
48+
inspect.WithStack(nodeFilter, func(n ast.Node, push bool, stack []ast.Node) (proceed bool) {
49+
if !push {
50+
return false
51+
}
52+
53+
if len(stack) < 2 {
54+
return true
55+
}
56+
57+
// The 0th node in the stack is the *ast.File.
58+
// The 1st node in the stack is the *ast.GenDecl.
59+
decl, ok := stack[1].(*ast.GenDecl)
5060
if !ok {
51-
return
61+
return false
5262
}
5363

54-
if sTyp.Fields == nil {
55-
return
64+
if decl.Tok != token.TYPE {
65+
return false
5666
}
5767

58-
for _, field := range sTyp.Fields.List {
59-
checkField(pass, field, jsonTags)
68+
field, ok := n.(*ast.Field)
69+
if !ok {
70+
return true
6071
}
72+
73+
return checkField(pass, field, jsonTags)
6174
})
6275

6376
return nil, nil //nolint:nilnil
6477
}
6578

66-
func checkField(pass *analysis.Pass, field *ast.Field, jsonTags extractjsontags.StructFieldTags) {
79+
func checkField(pass *analysis.Pass, field *ast.Field, jsonTags extractjsontags.StructFieldTags) (proceed bool) {
6780
if field == nil || len(field.Names) == 0 {
68-
return
81+
return false
6982
}
7083

71-
fieldName := field.Names[0].Name
72-
7384
tagInfo := jsonTags.FieldTags(field)
85+
if tagInfo.Ignored {
86+
return false
87+
}
7488

7589
if tagInfo.Name == "" {
76-
return
90+
return true
7791
}
7892

93+
fieldName := field.Names[0].Name
94+
7995
if field.Doc == nil {
8096
pass.Reportf(field.Pos(), "field %s is missing godoc comment", fieldName)
81-
return
97+
return true
8298
}
8399

84100
firstLine := field.Doc.List[0]
@@ -105,4 +121,6 @@ func checkField(pass *analysis.Pass, field *ast.Field, jsonTags extractjsontags.
105121
pass.Reportf(field.Doc.List[0].Pos(), "godoc for field %s should start with '%s ...'", fieldName, tagInfo.Name)
106122
}
107123
}
124+
125+
return true
108126
}

pkg/analysis/commentstart/testdata/src/a/a.go

+22
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,18 @@ type CommentStartTestStruct struct {
88
Ignored string `json:"-"`
99
Hyphen string `json:"-,"` // want "field Hyphen is missing godoc comment"
1010

11+
AnonymousStruct struct { // want "field AnonymousStruct is missing godoc comment"
12+
NoComment string `json:"noComment"` // want "field NoComment is missing godoc comment"
13+
} `json:"anonymousStruct"`
14+
15+
AnonymousStructInlineJSONTag struct {
16+
NoComment string `json:"noComment"` // want "field NoComment is missing godoc comment"
17+
} `json:",inline"`
18+
19+
IgnoredAnonymousStruct struct {
20+
NoComment string `json:"noComment"`
21+
} `json:"-"`
22+
1123
// IncorrectStartComment is a field with an incorrect start to the comment. // want "godoc for field IncorrectStartComment should start with 'incorrectStartComment ...'"
1224
IncorrectStartComment string `json:"incorrectStartComment"`
1325

@@ -34,3 +46,13 @@ type CommentStartTestStruct struct {
3446

3547
// DoNothing is used to check that the analyser doesn't report on methods.
3648
func (CommentStartTestStruct) DoNothing() {}
49+
50+
type unexportedStruct struct {
51+
NoComment string `json:"noComment"` // want "field NoComment is missing godoc comment"
52+
}
53+
54+
func FunctionWithStructs() {
55+
type InaccessibleStruct struct {
56+
NoComment string `json:"noComment"`
57+
}
58+
}

pkg/analysis/commentstart/testdata/src/a/a.go.golden

+22
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,18 @@ type CommentStartTestStruct struct {
88
Ignored string `json:"-"`
99
Hyphen string `json:"-,"` // want "field Hyphen is missing godoc comment"
1010

11+
AnonymousStruct struct { // want "field AnonymousStruct is missing godoc comment"
12+
NoComment string `json:"noComment"` // want "field NoComment is missing godoc comment"
13+
} `json:"anonymousStruct"`
14+
15+
AnonymousStructInlineJSONTag struct {
16+
NoComment string `json:"noComment"` // want "field NoComment is missing godoc comment"
17+
} `json:",inline"`
18+
19+
IgnoredAnonymousStruct struct {
20+
NoComment string `json:"noComment"`
21+
} `json:"-"`
22+
1123
// incorrectStartComment is a field with an incorrect start to the comment. // want "godoc for field IncorrectStartComment should start with 'incorrectStartComment ...'"
1224
IncorrectStartComment string `json:"incorrectStartComment"`
1325

@@ -34,3 +46,13 @@ type CommentStartTestStruct struct {
3446

3547
// DoNothing is used to check that the analyser doesn't report on methods.
3648
func (CommentStartTestStruct) DoNothing() {}
49+
50+
type unexportedStruct struct {
51+
NoComment string `json:"noComment"` // want "field NoComment is missing godoc comment"
52+
}
53+
54+
func FunctionWithStructs() {
55+
type InaccessibleStruct struct {
56+
NoComment string `json:"noComment"`
57+
}
58+
}

0 commit comments

Comments
 (0)