google / wire

Compile-time Dependency Injection for Go
Apache License 2.0
13.12k stars 623 forks source link

Panic bug: build code with more than 1 generic type parameters #417

Open LittleKey opened 1 month ago

LittleKey commented 1 month ago

Describe the bug

got panic error when build code with more than 1 generic type parameters

panic: unhandled AST node: *ast.IndexListExpr [recovered]
        panic: unhandled AST node: *ast.IndexListExpr

goroutine 1 [running]:
golang.org/x/tools/go/ast/astutil.Apply.func1()
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:46 +0xb8
panic({0x1049cdd40?, 0x140001a75a0?})
        /Users/littlekey/.local/share/mise/installs/go/1.22.8/src/runtime/panic.go:770 +0x124
github.com/google/wire/internal/wire.copyAST.func1(0x1400035a360?)
        /Users/littlekey/go/pkg/mod/github.com/google/wire@v0.6.0/internal/wire/copyast.go:392 +0x24a8
golang.org/x/tools/go/ast/astutil.(*application).apply(0x1400035a360, {0x104a20720?, 0x1400018f788?}, {0x1049ad5e8?, 0x1049ca820?}, 0x0?, {0x104a20540?, 0x14000352680?})
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:452 +0x157c
golang.org/x/tools/go/ast/astutil.(*application).apply(0x1400035a360, {0x104a20428?, 0x140003526c0?}, {0x104947882?, 0x5?}, 0x1047b83d0?, {0x104a20720?, 0x1400018f788?})
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:272 +0x1de8
golang.org/x/tools/go/ast/astutil.(*application).apply(0x1400035a360, {0x104a207c0?, 0x1400034c960?}, {0x1049478a2?, 0x0?}, 0x1400018f980?, {0x104a20428?, 0x140003526c0?})
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:220 +0x1974
golang.org/x/tools/go/ast/astutil.(*application).applyList(0x1400035a360, {0x104a207c0, 0x1400034c960}, {0x1049478a2, 0x4})
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:482 +0x78
golang.org/x/tools/go/ast/astutil.(*application).apply(0x1400035a360, {0x104a20450?, 0x140003580c0?}, {0x104948376?, 0xa?}, 0x1?, {0x104a207c0?, 0x1400034c960?})
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:225 +0xd08
golang.org/x/tools/go/ast/astutil.(*application).apply(0x1400035a360, {0x104a201f8?, 0x1400034c9c0?}, {0x104947882?, 0x0?}, 0x5?, {0x104a20450?, 0x140003580c0?})
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:298 +0x6f0
golang.org/x/tools/go/ast/astutil.(*application).apply(0x1400035a360, {0x104a20b50?, 0x140001a7590?}, {0x10494789e?, 0x10?}, 0x104b99420?, {0x104a201f8?, 0x1400034c9c0?})
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:426 +0x109c
golang.org/x/tools/go/ast/astutil.Apply({0x104a201f8, 0x1400034c9c0}, 0x0, 0x140001a7580)
        /Users/littlekey/go/pkg/mod/golang.org/x/tools@v0.17.0/go/ast/astutil/rewrite.go:51 +0x10c
github.com/google/wire/internal/wire.copyAST({0x104a201f8, 0x1400034c9c0})
        /Users/littlekey/go/pkg/mod/github.com/google/wire@v0.6.0/internal/wire/copyast.go:36 +0x7c
github.com/google/wire/internal/wire.(*gen).rewritePkgRefs(0x14000344e10, 0x140001c1a40, {0x104a201f8, 0x1400034c9c0})
        /Users/littlekey/go/pkg/mod/github.com/google/wire@v0.6.0/internal/wire/wire.go:400 +0x58
github.com/google/wire/internal/wire.(*gen).writeAST(0x14000344e10, 0x1049e4660?, {0x104a201f8?, 0x1400034c9c0?})
        /Users/littlekey/go/pkg/mod/github.com/google/wire@v0.6.0/internal/wire/wire.go:515 +0x28
github.com/google/wire/internal/wire.copyNonInjectorDecls(0x14000344e10, {0x140001804d0, 0x1, 0x10494957d?}, 0x140001c1a40)
        /Users/littlekey/go/pkg/mod/github.com/google/wire@v0.6.0/internal/wire/wire.go:227 +0x26c
github.com/google/wire/internal/wire.Generate({0x104a21a10?, 0x104bfee40?}, {0x14000018104?, 0x140000ac9c0?}, {0x140000b0b08?, 0x65?, 0x40?}, {0x140000e7ba0?, 0x140000e7a88?, 0x10471cc20?}, ...)
        /Users/littlekey/go/pkg/mod/github.com/google/wire@v0.6.0/internal/wire/wire.go:106 +0x310
main.(*genCmd).Execute(0x140000a27b0, {0x104a21a10, 0x104bfee40}, 0x140000cc8c0, {0x140000e7cd8?, 0x1049428d8?, 0x10?})
        /Users/littlekey/go/pkg/mod/github.com/google/wire@v0.6.0/cmd/wire/main.go:139 +0x214
github.com/google/subcommands.(*Commander).Execute(0x140000ce000, {0x104a21a10, 0x104bfee40}, {0x0, 0x0, 0x0})
        /Users/littlekey/go/pkg/mod/github.com/google/subcommands@v1.2.0/subcommands.go:209 +0x324
github.com/google/subcommands.Execute(...)
        /Users/littlekey/go/pkg/mod/github.com/google/subcommands@v1.2.0/subcommands.go:492
main.main()
        /Users/littlekey/go/pkg/mod/github.com/google/wire@v0.6.0/cmd/wire/main.go:73 +0x1124

To Reproduce

//go:build wireinject
// +build wireinject

package main

import (
    "github.com/google/wire"
)

type Empty[T, T2 any] struct{}

func ProvideEmpty() *Empty[int, int] {
    return &Empty[int, int]{}
}

func InitializeEmpty() *Empty[int, int] {
    wire.Build(ProvideEmpty)
    return nil
}

wire gen with above code: wire gen

Expected behavior

do not panic and generate code as well

Version

latest: v0.6.0

Additional context

Work well when use only 1 generic type parameter, like below:

//go:build wireinject
// +build wireinject

package main

import (
    "github.com/google/wire"
)

type Empty[T any] struct{}

func ProvideEmpty() *Empty[int] {
    return &Empty[int]{}
}

func InitializeEmpty() *Empty[int] {
    wire.Build(ProvideEmpty)
    return nil
}
LittleKey commented 1 month ago

Fixed by myself(casual): for everyone who has same problem before official fixed it

 internal/wire/copyast.go | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/internal/wire/copyast.go b/internal/wire/copyast.go
index 179d1c6..9ec63d7 100644
--- a/internal/wire/copyast.go
+++ b/internal/wire/copyast.go
@@ -263,6 +263,13 @@ func copyAST(original ast.Node) ast.Node {
                                Index:  exprFromMap(m, node.Index),
                                Rbrack: node.Rbrack,
                        }
+               case *ast.IndexListExpr:
+                       m[node] = &ast.IndexListExpr{
+                               X:       exprFromMap(m, node.X),
+                               Lbrack:  node.Lbrack,
+                               Indices: copyExprList(m, node.Indices),
+                               Rbrack:  node.Rbrack,
+                       }
                case *ast.InterfaceType:
                        m[node] = &ast.InterfaceType{
                                Interface:  node.Interface,
burik666 commented 1 month ago

Make a pull request, please.

LittleKey commented 1 month ago

Already has a fixed PR, but has been reverted. @burik666

Related:

  1. https://github.com/google/wire/pull/360
  2. https://github.com/google/wire/pull/365
LittleKey commented 1 month ago

Related: https://github.com/google/wire/pull/385