TravelingLex
TravelingLex

Reputation: 477

Update Status for K8s Custom Resource

I'm trying to update the status of a custom resource and I'm unable to figure out why its not working..

Here is the _types.go:

// ScoringServerStatus defines the observed state of ScoringServer
type ScoringServerStatus struct {
    // INSERT ADDITIONAL STATUS FIELD - define observed state of cluster
    // Important: Run "make" to regenerate code after modifying this file
    Reason     string             `json:"reason"`
    Message    string             `json:"message"`
    Conditions []metav1.Condition `json:"conditions"`
}

//+kubebuilder:object:root=true
//+kubebuilder:subresource:status

// ScoringServer is the Schema for the scoringservers API
type ScoringServer struct {
    metav1.TypeMeta   `json:",inline"`
    metav1.ObjectMeta `json:"metadata,omitempty"`

    Spec   ScoringServerSpec   `json:"spec,omitempty"`
    Status ScoringServerStatus `json:"status,omitempty"`
}

I'm trying to set the value of Reason and Message in this status:

if !isProjectAvailable {
        infoMessage = "Unable to find requested project, can't deploy scoring server"
        log.Log.Info(infoMessage)
        statusUpdate := scoringv1.ScoringServerStatus{Reason: "Unable to verify project in Machinify", Message: infoMessage}
        log.Log.Info(statusUpdate.Reason)
        scoringServer.Status = statusUpdate
        if err := r.Status().Update(ctx, scoringServer); err != nil {
            log.Log.Info(err.Error())
        }
        return ctrl.Result{Requeue: false, RequeueAfter: 0}, nil
    }

But nothing changes when I run this. I'm not receiving any errors and if I describe the resource I don't see an updated status...

Upvotes: 4

Views: 3063

Answers (3)

kilianc
kilianc

Reputation: 7816

If you are using kubebuilder, remember to re-apply your CRD yaml file; I just spent 1h debugging this.

❯ k apply -f config/crd/bases/<my.domain_type>.yaml
❯ make run

That did it for me!

Upvotes: 1

Kubus
Kubus

Reputation: 777

After you successfully updated the status of your CR you should force to call the Reconcile func again by returning a reconcile.Result in the following manner:

if err := r.Status().Update(ctx, scoringServer); err != nil {
  log.Log.Info(err.Error())
}

if err != nil {
  return reconcile.Result{}, err
}

Try replace this code fragment:

return ctrl.Result{Requeue: false, RequeueAfter: 0}, nil

with

if err != nil {
  return reconcile.Result{}, err
}

To avoid unnecessary reconciliation loops you can check for changes in the status:

if !reflect.DeepEqual(oldStatus, newStatus) {
  if err := r.Status().Update(ctx, scoringServer); err != nil {
    log.Log.Info(err.Error())
  }

  if err != nil {
    return reconcile.Result{}, err
  }
}

Upvotes: 0

Anton Engelhardt
Anton Engelhardt

Reputation: 41

i just faced the same issue and browsed for answers and somehow your code gave me a hint.

For me this worked fine:

err := r.Client.Status().Update(ctx, k8sproj)
if err != nil {
  fmt.Printf("Could not update project id: \n%s\n ", err)
}

Notice the Client()...

Hope it helps!

Upvotes: 1

Related Questions