From 01f11fbbcd7483bad79f1320ffa80cb7818aa573 Mon Sep 17 00:00:00 2001 From: Nuruddin Ashr Date: Wed, 8 Jan 2025 10:05:19 +0700 Subject: [PATCH] Handle untyped nil --- opaque/opaque.go | 15 +++++++++++++-- opaque/testdata/src/a/a.go | 9 +++++++++ opaque/testdata/src/a/a.go.golden | 9 +++++++++ 3 files changed, 31 insertions(+), 2 deletions(-) diff --git a/opaque/opaque.go b/opaque/opaque.go index 59e4063..500249d 100644 --- a/opaque/opaque.go +++ b/opaque/opaque.go @@ -157,12 +157,15 @@ func (r *runner) run(pass *analysis.Pass) (interface{}, error) { } typ := pass.TypesInfo.TypeOf(res) + isNilStmt := isUntypedNil(typ) if r.debug { - fmt.Printf(" Ident type: %v %v interface=%t\n", typ, reflect.TypeOf(typ), types.IsInterface(typ)) + fmt.Printf(" Ident type: %v %v interface=%t, untypedNil=%t\n", typ, reflect.TypeOf(typ), types.IsInterface(typ), isNilStmt) } - retStmtTypes[i][typ] = struct{}{} + if !isNilStmt { + retStmtTypes[i][typ] = struct{}{} + } case *ast.UnaryExpr: if r.debug { fmt.Printf(" UnaryExpr X: %v \n", res.X) @@ -302,6 +305,14 @@ func (r *runner) run(pass *analysis.Pass) (interface{}, error) { return nil, nil } +func isUntypedNil(typ types.Type) bool { + if b, ok := typ.(*types.Basic); ok { + return b.Kind() == types.UntypedNil + } + + return false +} + func positionStr(idx int) string { switch idx { case 0: diff --git a/opaque/testdata/src/a/a.go b/opaque/testdata/src/a/a.go index 8180f12..52cb352 100644 --- a/opaque/testdata/src/a/a.go +++ b/opaque/testdata/src/a/a.go @@ -1,5 +1,7 @@ package app +import "errors" + type Server interface { Serve() error } @@ -24,6 +26,13 @@ func NewServer3(addr string) Server { // want "NewServer3 function return Server return &server{addr: addr} } +func NewServer4(addr string) (Server, error) { // want "NewServer4 function return Server interface at the 1st result, abstract a single concrete implementation of \\*server" + if addr == "" { + return nil, errors.New("addr cannot be nil") + } + return &server{addr: addr}, nil +} + func newServer(addr string) *server { return &server{addr: addr} } diff --git a/opaque/testdata/src/a/a.go.golden b/opaque/testdata/src/a/a.go.golden index 92949db..532e99c 100644 --- a/opaque/testdata/src/a/a.go.golden +++ b/opaque/testdata/src/a/a.go.golden @@ -1,5 +1,7 @@ package app +import "errors" + type Server interface { Serve() error } @@ -24,6 +26,13 @@ func NewServer3(addr string) *server { // want "NewServer3 function return Serve return &server{addr: addr} } +func NewServer4(addr string) (*server, error) { // want "NewServer4 function return Server interface at the 1st result, abstract a single concrete implementation of \\*server" + if addr == "" { + return nil, errors.New("addr cannot be nil") + } + return &server{addr: addr}, nil +} + func newServer(addr string) *server { return &server{addr: addr} }