The retry logic we use to persist critical annotations makes it difficult to
delete an annotation without potentially also deleting annotations added by
another controller (e.g. the composition logic). This commit therefore changes
the way we detect whether we might have created an external resource but not
recorded the result. Previously we relied on the presence of the 'pending'
annotation to detect this state. Now we check whether the 'pending' annotation
is newer than any 'succeeded' or 'failed' annotation.
Signed-off-by: Nic Cope <negz@rk0n.org>
This commit is intended to address two issues that we diagnosed while
investigating https://github.com/crossplane/provider-aws/issues/802.
The first issue is that controller-runtime does not guarantee reads from cache
will return the freshest version of a resource. It's possible we could create an
external resource in one reconcile, then shortly after trigger another in which
it appears that the managed resource was never created because we didn't record
its external-name. This only affects the subset of managed resources with
non-deterministic external-names that are assigned during creation.
The second issue is that some external APIs are eventually consistent. A newly
created external resource may take some time before our ExternalClient's observe
call can confirm it exists. AWS EC2 is an example of one such API.
This commit attempts to address the first issue by making an Update to a managed
resource immediately before Create it called. This Update call will be rejected
by the API server if the managed resource we read from cache was not the latest
version.
It attempts to address the second issue by allowing managed resource controller
authors to configure an optional grace period that begins when an external
resource is successfully created. During this grace period we'll requeue and
keep waiting if Observe determines that the external resource doesn't exist,
rather than (re)creating it.
Signed-off-by: Nic Cope <negz@rk0n.org>
Updates all core/v1alpha1 imports to the common/v1, which is the new
home of these embedded API types.
Signed-off-by: hasheddan <georgedanielmangum@gmail.com>
This updates the AsOwner and AsController to use TypedReference, which
is a more scoped version of ObjectReference that still contains all
necessary fields to create a controller or owner reference for an
object.
Signed-off-by: hasheddan <georgedanielmangum@gmail.com>
Adds a TypedReferenceTo utility function that matches the ReferenceTo
implementation for ObjectReference, but returns a TypedReference
instead.
Signed-off-by: hasheddan <georgedanielmangum@gmail.com>
This allows propagation to function even when the propagating and/or propagated
secrets have been deleted and recreated, and thus allocated new UIDs.
Signed-off-by: Nic Cope <negz@rk0n.org>
We typically include the type hint at the start of enum-ish types, e.g.
AnnotationKeyFoo and ExternalResourceTagKeyBar. This was the one exception
to that pattern. Presumably this should not be noticed by most consumers of
this API, which use meta.GetExternalName to get this field.
Signed-off-by: Nic Cope <negz@rk0n.org>
* - Introduces Initializer hook to managed reconciler.
- ManagedNameAsExternalName is introduced and used
by default by all managed reconcilers.
Signed-off-by: Muvaffak Onus <onus.muvaffak@gmail.com>
* GetExternalName and SetExternalName functions are implemented
Signed-off-by: Muvaffak Onus <onus.muvaffak@gmail.com>
* - Unit tests for ManagedNameAsExternalName struct
- Move ExternalNameAnnotationKey into meta package.
Signed-off-by: Muvaffak Onus <onus.muvaffak@gmail.com>
* Remove Establisher mechanism and port existing
establisher to Initializer.
Signed-off-by: Muvaffak Onus <onus.muvaffak@gmail.com>
* Fix claim's external name annotation propagation to
the managed resource.
Signed-off-by: Muvaffak Onus <onus.muvaffak@gmail.com>
We don't seem to be able to rely on Go objects retaining type metadata
when deserialised. I've read (but not confirmed) that the decoding process
strips out TypeMeta, and observed TypeMeta disappearing during an Update()
call.
This API mirrors that of metav1.NewControllerRef. The caller can still attempt
to use TypeMeta if it is known to exist, i.e.:
```go
ref := meta.ReferenceTo(o, o.GetObjectKind().GroupVersionKind())
```
Signed-off-by: Nic Cope <negz@rk0n.org>