Codebase list golint / c48b90c
Flag names of type time.Duration that have unit suffixes. This catches people writing code such as var timeoutSecs = 5 * time.Second David Symonds 9 years ago
2 changed file(s) with 66 addition(s) and 0 deletion(s). Raw diff Collapse all Expand all
181181 f.lintMake()
182182 f.lintErrorReturn()
183183 f.lintUnexportedReturn()
184 f.lintTimeNames()
184185 }
185186
186187 type link string
259260 return nil
260261 }
261262 return p.typesInfo.TypeOf(expr)
263 }
264
265 func (p *pkg) isNamedType(typ types.Type, importPath, name string) bool {
266 n, ok := typ.(*types.Named)
267 if !ok {
268 return false
269 }
270 tn := n.Obj()
271 return tn != nil && tn.Pkg() != nil && tn.Pkg().Path() == importPath && tn.Name() == name
262272 }
263273
264274 // scopeOf returns the tightest scope encompassing id.
12591269 return true
12601270 }
12611271
1272 // timeSuffixes is a list of name suffixes that imply a time unit.
1273 // This is not an exhaustive list.
1274 var timeSuffixes = []string{
1275 "Sec", "Secs", "Seconds",
1276 "Msec", "Msecs",
1277 "Milli", "Millis", "Milliseconds",
1278 "Usec", "Usecs", "Microseconds",
1279 "MS", "Ms",
1280 }
1281
1282 func (f *file) lintTimeNames() {
1283 f.walk(func(node ast.Node) bool {
1284 v, ok := node.(*ast.ValueSpec)
1285 if !ok {
1286 return true
1287 }
1288 for _, name := range v.Names {
1289 origTyp := f.pkg.typeOf(name)
1290 // Look for time.Duration or *time.Duration;
1291 // the latter is common when using flag.Duration.
1292 typ := origTyp
1293 if pt, ok := typ.(*types.Pointer); ok {
1294 typ = pt.Elem()
1295 }
1296 if !f.pkg.isNamedType(typ, "time", "Duration") {
1297 continue
1298 }
1299 suffix := ""
1300 for _, suf := range timeSuffixes {
1301 if strings.HasSuffix(name.Name, suf) {
1302 suffix = suf
1303 break
1304 }
1305 }
1306 if suffix == "" {
1307 continue
1308 }
1309 f.errorf(v, 0.9, category("time"), "var %s is of type %v; don't use unit-specific suffix %q", name.Name, origTyp, suffix)
1310 }
1311 return true
1312 })
1313 }
1314
12621315 func receiverType(fn *ast.FuncDecl) string {
12631316 switch e := fn.Recv.List[0].Type.(type) {
12641317 case *ast.Ident:
0 // Test of time suffixes.
1
2 // Package foo ...
3 package foo
4
5 import (
6 "flag"
7 "time"
8 )
9
10 var rpcTimeoutMsec = flag.Duration("rpc_timeout", 100*time.Millisecond, "some flag") // MATCH /Msec.*\*time.Duration/
11
12 var timeoutSecs = 5 * time.Second // MATCH /Secs.*time.Duration/