|
|
|
@ -57,8 +57,18 @@ func (d *DualWriterMode1) Create(ctx context.Context, original runtime.Object, c |
|
|
|
|
|
|
|
|
|
|
|
createdCopy := created.DeepCopyObject() |
|
|
|
createdCopy := created.DeepCopyObject() |
|
|
|
|
|
|
|
|
|
|
|
go func(createdCopy runtime.Object) { |
|
|
|
//nolint:errcheck
|
|
|
|
ctx, cancel := context.WithTimeoutCause(ctx, time.Second*10, errors.New("storage create timeout")) |
|
|
|
go d.createOnUnifiedStorage(ctx, original, createValidation, createdCopy, options) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return created, err |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) createOnUnifiedStorage(ctx context.Context, original runtime.Object, createValidation rest.ValidateObjectFunc, createdCopy runtime.Object, options *metav1.CreateOptions) error { |
|
|
|
|
|
|
|
var method = "create" |
|
|
|
|
|
|
|
log := d.Log.WithValues("method", method) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Ignores cancellation signals from parent context. Will automatically be canceled after 10 seconds.
|
|
|
|
|
|
|
|
ctx, cancel := context.WithTimeoutCause(context.WithoutCancel(ctx), time.Second*10, errors.New("storage create timeout")) |
|
|
|
defer cancel() |
|
|
|
defer cancel() |
|
|
|
|
|
|
|
|
|
|
|
if err := enrichLegacyObject(original, createdCopy); err != nil { |
|
|
|
if err := enrichLegacyObject(original, createdCopy); err != nil { |
|
|
|
@ -68,7 +78,7 @@ func (d *DualWriterMode1) Create(ctx context.Context, original runtime.Object, c |
|
|
|
startStorage := time.Now() |
|
|
|
startStorage := time.Now() |
|
|
|
storageObj, errObjectSt := d.Storage.Create(ctx, createdCopy, createValidation, options) |
|
|
|
storageObj, errObjectSt := d.Storage.Create(ctx, createdCopy, createValidation, options) |
|
|
|
d.recordStorageDuration(errObjectSt != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
d.recordStorageDuration(errObjectSt != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
if err != nil { |
|
|
|
if errObjectSt != nil { |
|
|
|
cancel() |
|
|
|
cancel() |
|
|
|
} |
|
|
|
} |
|
|
|
areEqual := Compare(storageObj, createdCopy) |
|
|
|
areEqual := Compare(storageObj, createdCopy) |
|
|
|
@ -76,9 +86,8 @@ func (d *DualWriterMode1) Create(ctx context.Context, original runtime.Object, c |
|
|
|
if !areEqual { |
|
|
|
if !areEqual { |
|
|
|
log.Info("object from legacy and storage are not equal") |
|
|
|
log.Info("object from legacy and storage are not equal") |
|
|
|
} |
|
|
|
} |
|
|
|
}(createdCopy) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return created, err |
|
|
|
return errObjectSt |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
// Get overrides the behavior of the generic DualWriter and reads only from LegacyStorage.
|
|
|
|
// Get overrides the behavior of the generic DualWriter and reads only from LegacyStorage.
|
|
|
|
@ -94,9 +103,19 @@ func (d *DualWriterMode1) Get(ctx context.Context, name string, options *metav1. |
|
|
|
} |
|
|
|
} |
|
|
|
d.recordLegacyDuration(errLegacy != nil, mode1Str, d.resource, method, startLegacy) |
|
|
|
d.recordLegacyDuration(errLegacy != nil, mode1Str, d.resource, method, startLegacy) |
|
|
|
|
|
|
|
|
|
|
|
go func(res runtime.Object) { |
|
|
|
//nolint:errcheck
|
|
|
|
|
|
|
|
go d.getFromUnifiedStorage(ctx, res, name, options) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, errLegacy |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) getFromUnifiedStorage(ctx context.Context, res runtime.Object, name string, options *metav1.GetOptions) error { |
|
|
|
|
|
|
|
var method = "get" |
|
|
|
|
|
|
|
log := d.Log.WithValues("method", method, "name", name) |
|
|
|
|
|
|
|
|
|
|
|
startStorage := time.Now() |
|
|
|
startStorage := time.Now() |
|
|
|
ctx, cancel := context.WithTimeoutCause(ctx, time.Second*10, errors.New("storage get timeout")) |
|
|
|
// Ignores cancellation signals from parent context. Will automatically be canceled after 10 seconds.
|
|
|
|
|
|
|
|
ctx, cancel := context.WithTimeoutCause(context.WithoutCancel(ctx), time.Second*10, errors.New("storage get timeout")) |
|
|
|
defer cancel() |
|
|
|
defer cancel() |
|
|
|
storageObj, err := d.Storage.Get(ctx, name, options) |
|
|
|
storageObj, err := d.Storage.Get(ctx, name, options) |
|
|
|
d.recordStorageDuration(err != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
d.recordStorageDuration(err != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
@ -110,9 +129,8 @@ func (d *DualWriterMode1) Get(ctx context.Context, name string, options *metav1. |
|
|
|
if !areEqual { |
|
|
|
if !areEqual { |
|
|
|
log.WithValues("name", name).Info("object from legacy and storage are not equal") |
|
|
|
log.WithValues("name", name).Info("object from legacy and storage are not equal") |
|
|
|
} |
|
|
|
} |
|
|
|
}(res) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, errLegacy |
|
|
|
return err |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
// List overrides the behavior of the generic DualWriter and reads only from LegacyStorage.
|
|
|
|
// List overrides the behavior of the generic DualWriter and reads only from LegacyStorage.
|
|
|
|
@ -128,13 +146,24 @@ func (d *DualWriterMode1) List(ctx context.Context, options *metainternalversion |
|
|
|
} |
|
|
|
} |
|
|
|
d.recordLegacyDuration(errLegacy != nil, mode1Str, d.resource, method, startLegacy) |
|
|
|
d.recordLegacyDuration(errLegacy != nil, mode1Str, d.resource, method, startLegacy) |
|
|
|
|
|
|
|
|
|
|
|
go func(res runtime.Object) { |
|
|
|
//nolint:errcheck
|
|
|
|
|
|
|
|
go d.listFromUnifiedStorage(ctx, options, res) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, errLegacy |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) listFromUnifiedStorage(ctx context.Context, options *metainternalversion.ListOptions, res runtime.Object) error { |
|
|
|
|
|
|
|
var method = "list" |
|
|
|
|
|
|
|
log := d.Log.WithValues("resourceVersion", options.ResourceVersion, "method", method) |
|
|
|
|
|
|
|
|
|
|
|
startStorage := time.Now() |
|
|
|
startStorage := time.Now() |
|
|
|
ctx, cancel := context.WithTimeoutCause(ctx, time.Second*10, errors.New("storage list timeout")) |
|
|
|
// Ignores cancellation signals from parent context. Will automatically be canceled after 10 seconds.
|
|
|
|
|
|
|
|
ctx, cancel := context.WithTimeoutCause(context.WithoutCancel(ctx), time.Second*10, errors.New("storage list timeout")) |
|
|
|
defer cancel() |
|
|
|
defer cancel() |
|
|
|
storageObj, err := d.Storage.List(ctx, options) |
|
|
|
storageObj, err := d.Storage.List(ctx, options) |
|
|
|
d.recordStorageDuration(err != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
d.recordStorageDuration(err != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
if err != nil { |
|
|
|
if err != nil { |
|
|
|
|
|
|
|
log.Error(err, "unable to list objects from unified storage") |
|
|
|
cancel() |
|
|
|
cancel() |
|
|
|
} |
|
|
|
} |
|
|
|
areEqual := Compare(storageObj, res) |
|
|
|
areEqual := Compare(storageObj, res) |
|
|
|
@ -142,9 +171,8 @@ func (d *DualWriterMode1) List(ctx context.Context, options *metainternalversion |
|
|
|
if !areEqual { |
|
|
|
if !areEqual { |
|
|
|
log.Info("object from legacy and storage are not equal") |
|
|
|
log.Info("object from legacy and storage are not equal") |
|
|
|
} |
|
|
|
} |
|
|
|
}(res) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, errLegacy |
|
|
|
return err |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) Delete(ctx context.Context, name string, deleteValidation rest.ValidateObjectFunc, options *metav1.DeleteOptions) (runtime.Object, bool, error) { |
|
|
|
func (d *DualWriterMode1) Delete(ctx context.Context, name string, deleteValidation rest.ValidateObjectFunc, options *metav1.DeleteOptions) (runtime.Object, bool, error) { |
|
|
|
@ -161,9 +189,19 @@ func (d *DualWriterMode1) Delete(ctx context.Context, name string, deleteValidat |
|
|
|
} |
|
|
|
} |
|
|
|
d.recordLegacyDuration(false, mode1Str, name, method, startLegacy) |
|
|
|
d.recordLegacyDuration(false, mode1Str, name, method, startLegacy) |
|
|
|
|
|
|
|
|
|
|
|
go func(res runtime.Object) { |
|
|
|
//nolint:errcheck
|
|
|
|
|
|
|
|
go d.deleteFromUnifiedStorage(ctx, res, name, deleteValidation, options) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, async, err |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) deleteFromUnifiedStorage(ctx context.Context, res runtime.Object, name string, deleteValidation rest.ValidateObjectFunc, options *metav1.DeleteOptions) error { |
|
|
|
|
|
|
|
var method = "delete" |
|
|
|
|
|
|
|
log := d.Log.WithValues("name", name, "method", method, "name", name) |
|
|
|
|
|
|
|
|
|
|
|
startStorage := time.Now() |
|
|
|
startStorage := time.Now() |
|
|
|
ctx, cancel := context.WithTimeoutCause(ctx, time.Second*10, errors.New("storage delete timeout")) |
|
|
|
// Ignores cancellation signals from parent context. Will automatically be canceled after 10 seconds.
|
|
|
|
|
|
|
|
ctx, cancel := context.WithTimeoutCause(context.WithoutCancel(ctx), time.Second*10, errors.New("storage delete timeout")) |
|
|
|
defer cancel() |
|
|
|
defer cancel() |
|
|
|
storageObj, _, err := d.Storage.Delete(ctx, name, deleteValidation, options) |
|
|
|
storageObj, _, err := d.Storage.Delete(ctx, name, deleteValidation, options) |
|
|
|
d.recordStorageDuration(err != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
d.recordStorageDuration(err != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
@ -175,9 +213,8 @@ func (d *DualWriterMode1) Delete(ctx context.Context, name string, deleteValidat |
|
|
|
if !areEqual { |
|
|
|
if !areEqual { |
|
|
|
log.Info("object from legacy and storage are not equal") |
|
|
|
log.Info("object from legacy and storage are not equal") |
|
|
|
} |
|
|
|
} |
|
|
|
}(res) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, async, err |
|
|
|
return err |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
// DeleteCollection overrides the behavior of the generic DualWriter and deletes only from LegacyStorage.
|
|
|
|
// DeleteCollection overrides the behavior of the generic DualWriter and deletes only from LegacyStorage.
|
|
|
|
@ -195,9 +232,19 @@ func (d *DualWriterMode1) DeleteCollection(ctx context.Context, deleteValidation |
|
|
|
} |
|
|
|
} |
|
|
|
d.recordLegacyDuration(false, mode1Str, d.resource, method, startLegacy) |
|
|
|
d.recordLegacyDuration(false, mode1Str, d.resource, method, startLegacy) |
|
|
|
|
|
|
|
|
|
|
|
go func(res runtime.Object) { |
|
|
|
//nolint:errcheck
|
|
|
|
|
|
|
|
go d.deleteCollectionFromUnifiedStorage(ctx, res, deleteValidation, options, listOptions) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, err |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) deleteCollectionFromUnifiedStorage(ctx context.Context, res runtime.Object, deleteValidation rest.ValidateObjectFunc, options *metav1.DeleteOptions, listOptions *metainternalversion.ListOptions) error { |
|
|
|
|
|
|
|
var method = "delete-collection" |
|
|
|
|
|
|
|
log := d.Log.WithValues("resourceVersion", listOptions.ResourceVersion, "method", method) |
|
|
|
|
|
|
|
|
|
|
|
startStorage := time.Now() |
|
|
|
startStorage := time.Now() |
|
|
|
ctx, cancel := context.WithTimeoutCause(ctx, time.Second*10, errors.New("storage deletecollection timeout")) |
|
|
|
// Ignores cancellation signals from parent context. Will automatically be canceled after 10 seconds.
|
|
|
|
|
|
|
|
ctx, cancel := context.WithTimeoutCause(context.WithoutCancel(ctx), time.Second*10, errors.New("storage deletecollection timeout")) |
|
|
|
defer cancel() |
|
|
|
defer cancel() |
|
|
|
storageObj, err := d.Storage.DeleteCollection(ctx, deleteValidation, options, listOptions) |
|
|
|
storageObj, err := d.Storage.DeleteCollection(ctx, deleteValidation, options, listOptions) |
|
|
|
d.recordStorageDuration(err != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
d.recordStorageDuration(err != nil, mode1Str, d.resource, method, startStorage) |
|
|
|
@ -209,9 +256,8 @@ func (d *DualWriterMode1) DeleteCollection(ctx context.Context, deleteValidation |
|
|
|
if !areEqual { |
|
|
|
if !areEqual { |
|
|
|
log.Info("object from legacy and storage are not equal") |
|
|
|
log.Info("object from legacy and storage are not equal") |
|
|
|
} |
|
|
|
} |
|
|
|
}(res) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, err |
|
|
|
return err |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) Update(ctx context.Context, name string, objInfo rest.UpdatedObjectInfo, createValidation rest.ValidateObjectFunc, updateValidation rest.ValidateObjectUpdateFunc, forceAllowCreate bool, options *metav1.UpdateOptions) (runtime.Object, bool, error) { |
|
|
|
func (d *DualWriterMode1) Update(ctx context.Context, name string, objInfo rest.UpdatedObjectInfo, createValidation rest.ValidateObjectFunc, updateValidation rest.ValidateObjectUpdateFunc, forceAllowCreate bool, options *metav1.UpdateOptions) (runtime.Object, bool, error) { |
|
|
|
@ -228,8 +274,18 @@ func (d *DualWriterMode1) Update(ctx context.Context, name string, objInfo rest. |
|
|
|
} |
|
|
|
} |
|
|
|
d.recordLegacyDuration(false, mode1Str, d.resource, method, startLegacy) |
|
|
|
d.recordLegacyDuration(false, mode1Str, d.resource, method, startLegacy) |
|
|
|
|
|
|
|
|
|
|
|
go func(res runtime.Object) { |
|
|
|
//nolint:errcheck
|
|
|
|
ctx, cancel := context.WithTimeoutCause(ctx, time.Second*10, errors.New("storage update timeout")) |
|
|
|
go d.updateOnUnifiedStorage(ctx, res, name, objInfo, createValidation, updateValidation, forceAllowCreate, options) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, async, err |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) updateOnUnifiedStorage(ctx context.Context, res runtime.Object, name string, objInfo rest.UpdatedObjectInfo, createValidation rest.ValidateObjectFunc, updateValidation rest.ValidateObjectUpdateFunc, forceAllowCreate bool, options *metav1.UpdateOptions) error { |
|
|
|
|
|
|
|
var method = "update" |
|
|
|
|
|
|
|
log := d.Log.WithValues("name", name, "method", method, "name", name) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// Ignores cancellation signals from parent context. Will automatically be canceled after 10 seconds.
|
|
|
|
|
|
|
|
ctx, cancel := context.WithTimeoutCause(context.WithoutCancel(ctx), time.Second*10, errors.New("storage update timeout")) |
|
|
|
|
|
|
|
|
|
|
|
resCopy := res.DeepCopyObject() |
|
|
|
resCopy := res.DeepCopyObject() |
|
|
|
// get the object to be updated
|
|
|
|
// get the object to be updated
|
|
|
|
@ -271,9 +327,8 @@ func (d *DualWriterMode1) Update(ctx context.Context, name string, objInfo rest. |
|
|
|
if !areEqual { |
|
|
|
if !areEqual { |
|
|
|
log.WithValues("name", name).Info("object from legacy and storage are not equal") |
|
|
|
log.WithValues("name", name).Info("object from legacy and storage are not equal") |
|
|
|
} |
|
|
|
} |
|
|
|
}(res) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return res, async, err |
|
|
|
return errObjectSt |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
func (d *DualWriterMode1) Destroy() { |
|
|
|
func (d *DualWriterMode1) Destroy() { |
|
|
|
|