cmd/cloner, cmd/viewer, util/codegen: add support for aliases of cloneable types

We have several checked type assertions to *types.Named in both cmd/cloner and cmd/viewer.
As Go 1.23 updates the go/types package to produce Alias type nodes for type aliases,
these type assertions no longer work as expected unless the new behavior is disabled
with gotypesalias=0.

In this PR, we add codegen.NamedTypeOf(t types.Type), which functions like t.(*types.Named)
but also unrolls type aliases. We then use it in place of type assertions in the cmd/cloner and
cmd/viewer packages where appropriate.

We also update type switches to include *types.Alias alongside *types.Named in relevant cases,
remove *types.Struct cases when switching on types.Type.Underlying and update the tests
with more cases where type aliases can be used.

Updates #13224
Updates #12912

Signed-off-by: Nick Khyl <nickk@tailscale.com>
This commit is contained in:
Nick Khyl
2024-08-22 17:59:45 -05:00
committed by Nick Khyl
parent a9dc6e07ad
commit 03acab2639
6 changed files with 154 additions and 18 deletions

View File

@@ -724,11 +724,60 @@ func (v *StructWithTypeAliasFieldsView) UnmarshalJSON(b []byte) error {
func (v StructWithTypeAliasFieldsView) WithPtr() StructWithPtrsView { return v.ж.WithPtr.View() }
func (v StructWithTypeAliasFieldsView) WithoutPtr() StructWithoutPtrsAlias { return v.ж.WithoutPtr }
func (v StructWithTypeAliasFieldsView) WithPtrByPtr() StructWithPtrsAliasView {
return v.ж.WithPtrByPtr.View()
}
func (v StructWithTypeAliasFieldsView) WithoutPtrByPtr() *StructWithoutPtrsAlias {
if v.ж.WithoutPtrByPtr == nil {
return nil
}
x := *v.ж.WithoutPtrByPtr
return &x
}
func (v StructWithTypeAliasFieldsView) SliceWithPtrs() views.SliceView[*StructWithPtrsAlias, StructWithPtrsAliasView] {
return views.SliceOfViews[*StructWithPtrsAlias, StructWithPtrsAliasView](v.ж.SliceWithPtrs)
}
func (v StructWithTypeAliasFieldsView) SliceWithoutPtrs() views.SliceView[*StructWithoutPtrsAlias, StructWithoutPtrsAliasView] {
return views.SliceOfViews[*StructWithoutPtrsAlias, StructWithoutPtrsAliasView](v.ж.SliceWithoutPtrs)
}
func (v StructWithTypeAliasFieldsView) MapWithPtrs() views.MapFn[string, *StructWithPtrsAlias, StructWithPtrsAliasView] {
return views.MapFnOf(v.ж.MapWithPtrs, func(t *StructWithPtrsAlias) StructWithPtrsAliasView {
return t.View()
})
}
func (v StructWithTypeAliasFieldsView) MapWithoutPtrs() views.MapFn[string, *StructWithoutPtrsAlias, StructWithoutPtrsAliasView] {
return views.MapFnOf(v.ж.MapWithoutPtrs, func(t *StructWithoutPtrsAlias) StructWithoutPtrsAliasView {
return t.View()
})
}
func (v StructWithTypeAliasFieldsView) MapOfSlicesWithPtrs() views.MapFn[string, []*StructWithPtrsAlias, views.SliceView[*StructWithPtrsAlias, StructWithPtrsAliasView]] {
return views.MapFnOf(v.ж.MapOfSlicesWithPtrs, func(t []*StructWithPtrsAlias) views.SliceView[*StructWithPtrsAlias, StructWithPtrsAliasView] {
return views.SliceOfViews[*StructWithPtrsAlias, StructWithPtrsAliasView](t)
})
}
func (v StructWithTypeAliasFieldsView) MapOfSlicesWithoutPtrs() views.MapFn[string, []*StructWithoutPtrsAlias, views.SliceView[*StructWithoutPtrsAlias, StructWithoutPtrsAliasView]] {
return views.MapFnOf(v.ж.MapOfSlicesWithoutPtrs, func(t []*StructWithoutPtrsAlias) views.SliceView[*StructWithoutPtrsAlias, StructWithoutPtrsAliasView] {
return views.SliceOfViews[*StructWithoutPtrsAlias, StructWithoutPtrsAliasView](t)
})
}
// A compilation failure here means this code must be regenerated, with the command at the top of this file.
var _StructWithTypeAliasFieldsViewNeedsRegeneration = StructWithTypeAliasFields(struct {
WithPtr StructWithPtrsAlias
WithoutPtr StructWithoutPtrsAlias
WithPtr StructWithPtrsAlias
WithoutPtr StructWithoutPtrsAlias
WithPtrByPtr *StructWithPtrsAlias
WithoutPtrByPtr *StructWithoutPtrsAlias
SliceWithPtrs []*StructWithPtrsAlias
SliceWithoutPtrs []*StructWithoutPtrsAlias
MapWithPtrs map[string]*StructWithPtrsAlias
MapWithoutPtrs map[string]*StructWithoutPtrsAlias
MapOfSlicesWithPtrs map[string][]*StructWithPtrsAlias
MapOfSlicesWithoutPtrs map[string][]*StructWithoutPtrsAlias
}{})
// View returns a readonly view of GenericTypeAliasStruct.