managedfields: Create NewFakeFieldManager

And simplify how a lot of the fakes are created. Notably, the converter
was never really used to do anything so this is simplified.
This commit is contained in:
Antoine Pelisse 2023-03-28 16:55:47 -07:00
parent 45853e20ae
commit 559d12fcce
3 changed files with 48 additions and 42 deletions

View File

@ -33,7 +33,7 @@ func TestNoUpdateBeforeFirstApply(t *testing.T) {
f := internaltesting.NewTestFieldManagerImpl(fakeTypeConverter, schema.FromAPIVersionAndKind("v1", "Pod"), "", func(m internal.Manager) internal.Manager { f := internaltesting.NewTestFieldManagerImpl(fakeTypeConverter, schema.FromAPIVersionAndKind("v1", "Pod"), "", func(m internal.Manager) internal.Manager {
return internal.NewSkipNonAppliedManager( return internal.NewSkipNonAppliedManager(
m, m,
internaltesting.NewFakeObjectCreater(), &internaltesting.FakeObjectCreater{},
schema.FromAPIVersionAndKind("v1", "Pod"), schema.FromAPIVersionAndKind("v1", "Pod"),
) )
}) })
@ -73,7 +73,7 @@ func TestUpdateBeforeFirstApply(t *testing.T) {
f := internaltesting.NewTestFieldManagerImpl(fakeTypeConverter, schema.FromAPIVersionAndKind("v1", "Pod"), "", func(m internal.Manager) internal.Manager { f := internaltesting.NewTestFieldManagerImpl(fakeTypeConverter, schema.FromAPIVersionAndKind("v1", "Pod"), "", func(m internal.Manager) internal.Manager {
return internal.NewSkipNonAppliedManager( return internal.NewSkipNonAppliedManager(
m, m,
internaltesting.NewFakeObjectCreater(), &internaltesting.FakeObjectCreater{},
schema.FromAPIVersionAndKind("v1", "Pod"), schema.FromAPIVersionAndKind("v1", "Pod"),
) )
}) })

View File

@ -27,62 +27,42 @@ import (
"k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/apimachinery/pkg/util/managedfields" "k8s.io/apimachinery/pkg/util/managedfields"
"k8s.io/apimachinery/pkg/util/managedfields/internal" "k8s.io/apimachinery/pkg/util/managedfields/internal"
"sigs.k8s.io/structured-merge-diff/v4/fieldpath"
"sigs.k8s.io/structured-merge-diff/v4/merge"
"sigs.k8s.io/structured-merge-diff/v4/typed"
) )
// NewFakeObjectCreater implements ObjectCreater, it can create empty // FakeObjectCreater implements ObjectCreater, it can create empty
// objects (unstructured) of the given GVK. // objects (unstructured) of the given GVK.
func NewFakeObjectCreater() runtime.ObjectCreater { type FakeObjectCreater struct{}
return &fakeObjectCreater{}
}
type fakeObjectCreater struct{} func (f *FakeObjectCreater) New(gvk schema.GroupVersionKind) (runtime.Object, error) {
func (f *fakeObjectCreater) New(gvk schema.GroupVersionKind) (runtime.Object, error) {
u := unstructured.Unstructured{Object: map[string]interface{}{}} u := unstructured.Unstructured{Object: map[string]interface{}{}}
u.SetAPIVersion(gvk.GroupVersion().String()) u.SetAPIVersion(gvk.GroupVersion().String())
u.SetKind(gvk.Kind) u.SetKind(gvk.Kind)
return &u, nil return &u, nil
} }
type fakeObjectConvertor struct { // FakeObjectConvertor implements runtime.ObjectConvertor but it
converter merge.Converter // actually does nothing but return its input.
apiVersion fieldpath.APIVersion type FakeObjectConvertor struct{}
}
//nolint:staticcheck,ineffassign // SA4009 backwards compatibility //nolint:staticcheck,ineffassign // SA4009 backwards compatibility
func (c *fakeObjectConvertor) Convert(in, out, context interface{}) error { func (c *FakeObjectConvertor) Convert(in, out, context interface{}) error {
if typedValue, ok := in.(*typed.TypedValue); ok { out = in
var err error
out, err = c.converter.Convert(typedValue, c.apiVersion)
return err
}
return nil return nil
} }
func (c *fakeObjectConvertor) ConvertToVersion(in runtime.Object, _ runtime.GroupVersioner) (runtime.Object, error) { func (c *FakeObjectConvertor) ConvertToVersion(in runtime.Object, _ runtime.GroupVersioner) (runtime.Object, error) {
return in, nil return in, nil
} }
func (c *fakeObjectConvertor) ConvertFieldLabel(_ schema.GroupVersionKind, _, _ string) (string, string, error) { func (c *FakeObjectConvertor) ConvertFieldLabel(_ schema.GroupVersionKind, _, _ string) (string, string, error) {
return "", "", errors.New("not implemented") return "", "", errors.New("not implemented")
} }
type fakeObjectDefaulter struct{} // FakeObjectDefaulter implements runtime.Defaulter, but it actually
// does nothing.
type FakeObjectDefaulter struct{}
func (d *fakeObjectDefaulter) Default(in runtime.Object) {} func (d *FakeObjectDefaulter) Default(in runtime.Object) {}
type sameVersionConverter struct{}
func (sameVersionConverter) Convert(object *typed.TypedValue, version fieldpath.APIVersion) (*typed.TypedValue, error) {
return object, nil
}
func (sameVersionConverter) IsMissingVersionError(error) bool {
return false
}
type TestFieldManagerImpl struct { type TestFieldManagerImpl struct {
fieldManager *internal.FieldManager fieldManager *internal.FieldManager
@ -139,12 +119,10 @@ func (f *TestFieldManagerImpl) ManagedFields() []metav1.ManagedFieldsEntry {
// NewTestFieldManager creates a new manager for the given GVK. // NewTestFieldManager creates a new manager for the given GVK.
func NewTestFieldManagerImpl(typeConverter managedfields.TypeConverter, gvk schema.GroupVersionKind, subresource string, chainFieldManager func(internal.Manager) internal.Manager) *TestFieldManagerImpl { func NewTestFieldManagerImpl(typeConverter managedfields.TypeConverter, gvk schema.GroupVersionKind, subresource string, chainFieldManager func(internal.Manager) internal.Manager) *TestFieldManagerImpl {
apiVersion := fieldpath.APIVersion(gvk.GroupVersion().String())
objectConverter := &fakeObjectConvertor{sameVersionConverter{}, apiVersion}
f, err := internal.NewStructuredMergeManager( f, err := internal.NewStructuredMergeManager(
typeConverter, typeConverter,
objectConverter, &FakeObjectConvertor{},
&fakeObjectDefaulter{}, &FakeObjectDefaulter{},
gvk.GroupVersion(), gvk.GroupVersion(),
gvk.GroupVersion(), gvk.GroupVersion(),
nil, nil,
@ -166,8 +144,8 @@ func NewTestFieldManagerImpl(typeConverter managedfields.TypeConverter, gvk sche
internal.NewManagedFieldsUpdater( internal.NewManagedFieldsUpdater(
internal.NewStripMetaManager(f), internal.NewStripMetaManager(f),
), gvk.GroupVersion(), subresource, ), gvk.GroupVersion(), subresource,
), NewFakeObjectCreater(), gvk, internal.DefaultTrackOnCreateProbability, ), &FakeObjectCreater{}, gvk, internal.DefaultTrackOnCreateProbability,
), typeConverter, objectConverter, gvk.GroupVersion(), ), typeConverter, &FakeObjectConvertor{}, gvk.GroupVersion(),
), ),
) )
if chainFieldManager != nil { if chainFieldManager != nil {

View File

@ -63,4 +63,32 @@ func NewTestFieldManager(typeConverter managedfields.TypeConverter, gvk schema.G
// for the given gvk, on the given sub-resource. // for the given gvk, on the given sub-resource.
func NewTestFieldManagerSubresource(typeConverter managedfields.TypeConverter, gvk schema.GroupVersionKind, subresource string) TestFieldManager { func NewTestFieldManagerSubresource(typeConverter managedfields.TypeConverter, gvk schema.GroupVersionKind, subresource string) TestFieldManager {
return testing.NewTestFieldManagerImpl(typeConverter, gvk, subresource, nil) return testing.NewTestFieldManagerImpl(typeConverter, gvk, subresource, nil)
}
// NewFakeFieldManager creates an actual FieldManager but that doesn't
// perform any conversion. This is just a convenience for tests to
// create an actual manager that they can use but in very restricted
// ways.
//
// This is different from the TestFieldManager because it's not meant to
// assert values, or hold the state, this acts like a normal
// FieldManager.
//
// Also, this only operates on the main-resource, and sub-resource can't
// be configured.
func NewFakeFieldManager(typeConverter managedfields.TypeConverter, gvk schema.GroupVersionKind) *managedfields.FieldManager {
ffm, err := managedfields.NewDefaultFieldManager(
typeConverter,
&testing.FakeObjectConvertor{},
&testing.FakeObjectDefaulter{},
&testing.FakeObjectCreater{},
gvk,
gvk.GroupVersion(),
"",
nil)
if err != nil {
panic(err)
}
return ffm
} }