Skip to content

Commit

Permalink
Merge pull request #72 from jmattheis/panic-interface-type
Browse files Browse the repository at this point in the history
  • Loading branch information
jmattheis committed Apr 9, 2023
2 parents a118b69 + e69a1d5 commit 555ca5a
Show file tree
Hide file tree
Showing 7 changed files with 203 additions and 2 deletions.
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ use reflection.
1. Run `goverter`:

```bash
$ go run github.com/jmattheis/goverter/cmd/[email protected].2 ./
$ go run github.com/jmattheis/goverter/cmd/[email protected].3 ./
```

See [Installation](https://goverter.jmattheis.de/#/install) for more information.
Expand Down
4 changes: 3 additions & 1 deletion runner_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,9 @@ func TestScenario(t *testing.T) {
require.Equal(t, scenario.Success, string(body))
require.NoError(t, compile(genFile), "generated converter doesn't build")
})
clearDir(execDir)
if os.Getenv("SKIP_CLEAN") != "true" {
clearDir(execDir)
}
}
}

Expand Down
55 changes: 55 additions & 0 deletions scenario/interface_complex.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
input:
input.go: |
package structs
import "io"
// goverter:converter
// goverter:extend ConvertInterface
type Converter interface {
Convert(source map[string]interface {
io.Reader
Test() bool
}) map[string]interface {
io.Writer
Test() bool
}
}
func ConvertInterface(x interface {
io.Reader
Test() bool
}) interface {
io.Writer
Test() bool
} {
return nil
}
success: |
// Code generated by github.com/jmattheis/goverter, DO NOT EDIT.
package generated
import (
execution "github.com/jmattheis/goverter/execution"
"io"
)
type ConverterImpl struct{}
func (c *ConverterImpl) Convert(source map[string]interface {
io.Reader
Test() bool
}) map[string]interface {
io.Writer
Test() bool
} {
mapStringUnknown := make(map[string]interface {
io.Writer
Test() bool
}, len(source))
for key, value := range source {
mapStringUnknown[key] = execution.ConvertInterface(value)
}
return mapStringUnknown
}
40 changes: 40 additions & 0 deletions scenario/interface_embed.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
input:
input.go: |
package structs
import "io"
// goverter:converter
// goverter:extend ConvertInterface
type Converter interface {
Convert(source map[string]interface{ io.Reader }) map[string]interface{ io.Writer }
}
func ConvertInterface(x interface{io.Reader}) interface{io.Writer} {
return nil
}
success: |
// Code generated by github.com/jmattheis/goverter, DO NOT EDIT.
package generated
import (
execution "github.com/jmattheis/goverter/execution"
"io"
)
type ConverterImpl struct{}
func (c *ConverterImpl) Convert(source map[string]interface {
io.Reader
}) map[string]interface {
io.Writer
} {
mapStringUnknown := make(map[string]interface {
io.Writer
}, len(source))
for key, value := range source {
mapStringUnknown[key] = execution.ConvertInterface(value)
}
return mapStringUnknown
}
29 changes: 29 additions & 0 deletions scenario/interface_empty.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
input:
input.go: |
package structs
// goverter:converter
// goverter:extend ConvertInterface
type Converter interface {
Convert(source map[string]interface{}) map[string]interface{}
}
func ConvertInterface(x interface{}) interface{} {
return nil
}
success: |
// Code generated by github.com/jmattheis/goverter, DO NOT EDIT.
package generated
import execution "github.com/jmattheis/goverter/execution"
type ConverterImpl struct{}
func (c *ConverterImpl) Convert(source map[string]interface{}) map[string]interface{} {
mapStringUnknown := make(map[string]interface{}, len(source))
for key, value := range source {
mapStringUnknown[key] = execution.ConvertInterface(value)
}
return mapStringUnknown
}
39 changes: 39 additions & 0 deletions scenario/interface_methods.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
input:
input.go: |
package structs
// goverter:converter
// goverter:extend ConvertInterface
type Converter interface {
Convert(source map[string]interface {
Test(x bool) (l string, err error)
}) map[string]interface{ Test2() }
}
func ConvertInterface(x interface {
Test(x bool) (l string, err error)
}) interface{ Test2() } {
return nil
}
success: |
// Code generated by github.com/jmattheis/goverter, DO NOT EDIT.
package generated
import execution "github.com/jmattheis/goverter/execution"
type ConverterImpl struct{}
func (c *ConverterImpl) Convert(source map[string]interface {
Test(bool) (string, error)
}) map[string]interface {
Test2()
} {
mapStringUnknown := make(map[string]interface {
Test2()
}, len(source))
for key, value := range source {
mapStringUnknown[key] = execution.ConvertInterface(value)
}
return mapStringUnknown
}
36 changes: 36 additions & 0 deletions xtype/type.go
Original file line number Diff line number Diff line change
Expand Up @@ -264,10 +264,46 @@ func toCode(t types.Type) *jen.Statement {
return toCodeBasic(cast.Kind())
case *types.Struct:
return toCodeStruct(cast)
case *types.Interface:
return toCodeInterface(cast)
}
panic("unsupported type " + t.String())
}

func toCodeInterface(t *types.Interface) *jen.Statement {
content := []jen.Code{}
for i := 0; i < t.NumEmbeddeds(); i++ {
content = append(content, toCode(t.EmbeddedType(i)))
}

for i := 0; i < t.NumExplicitMethods(); i++ {
method := t.ExplicitMethod(i)
content = append(content, toCodeFunc(method))
}

return jen.Interface(content...)
}

func toCodeFunc(t *types.Func) *jen.Statement {
sig := t.Type().(*types.Signature)
return toCodeSignature(t.Name(), sig)
}

func toCodeSignature(name string, t *types.Signature) *jen.Statement {
jenParams := []jen.Code{}
params := t.Params()
for i := 0; i < params.Len(); i++ {
jenParams = append(jenParams, toCode(params.At(i).Type()))
}

jenResults := []jen.Code{}
results := t.Results()
for i := 0; i < results.Len(); i++ {
jenResults = append(jenResults, toCode(results.At(i).Type()))
}
return jen.Id(name).Params(jenParams...).Params(jenResults...)
}

func toCodeNamed(t *types.Named) *jen.Statement {
var name *jen.Statement
if t.Obj().Pkg() == nil {
Expand Down

0 comments on commit 555ca5a

Please sign in to comment.