I'm working on developing a k8s custom resource that as part of the business logic needs to reconcile its state when an external Job in the cluster have changed its own state.
Those Jobs aren't created by the custom resource itself but are externally created for a third party service, however I need to reconcile the state of the CRO for example when any of those external jobs have finished.
After reading bunch of documentation, I came up with setting a watcher for the controller, to watch Jobs like the following example
func (r *DatasetReconciler) SetupWithManager(mgr ctrl.Manager) error {
return ctrl.NewControllerManagedBy(mgr).
For(&datasetv1beta1.Dataset{}).
Watches(&source.Kind{Type: &batchv1.Job{}}, &handler.EnqueueRequestForObject{} /* filter by predicates, see https://pkg.go.dev/sigs.k8s.io/[email protected]/pkg/controller#Controller */).
Complete(r)
}
No I'm having my reconcile loop triggered for Jobs and my CRs with the corresponding name and namespace but I don't know anything about the object kind.
func (r *DatasetReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Result, error) {
l := log.FromContext(ctx)
l.Info("Enter Reconcile loop")
l.Info("Request", "Req", req)
//if this is triggered by my CR
dataset := &datasetv1beta1.Dataset{}
r.Get(ctx, types.NamespacedName{Name: req.Name, Namespace: req.Namespace}, dataset)
//whereas when triggered by a Job
job := &batchv1.Job{}
r.Get(ctx, types.NamespacedName{Name: req.Name, Namespace: req.Namespace}, job)
return ctrl.Result{}, nil
}
How can I check within Reconcile the object kind? so I can retrieve the full object data calling r.Get
By design, the event that triggered reconciliation is not passed to the reconciler so that you are forced to define and act on a state instead. This approach is referred to as level-based, as opposed to edge-based.
In your example you have two resources you are trying to keep track of. I would suggest either:
If you want to prevent reconciliation on certain events you can make use of predicates. From the event in the predicate function you can get the object type by e.Object.(*core.Pod)
for example.