github.com/kotalco/kotal@v0.3.0/apis/polkadot/v1alpha1/node_validation_webhook.go (about)

     1  package v1alpha1
     2  
     3  import (
     4  	apierrors "k8s.io/apimachinery/pkg/api/errors"
     5  	"k8s.io/apimachinery/pkg/runtime"
     6  	"k8s.io/apimachinery/pkg/runtime/schema"
     7  	"k8s.io/apimachinery/pkg/util/validation/field"
     8  	"sigs.k8s.io/controller-runtime/pkg/webhook"
     9  	"sigs.k8s.io/controller-runtime/pkg/webhook/admission"
    10  )
    11  
    12  // +kubebuilder:webhook:verbs=create;update,path=/validate-polkadot-kotal-io-v1alpha1-node,mutating=false,failurePolicy=fail,groups=polkadot.kotal.io,resources=nodes,versions=v1alpha1,name=validate-polkadot-v1alpha1-node.kb.io,sideEffects=None,admissionReviewVersions=v1
    13  
    14  var _ webhook.Validator = &Node{}
    15  
    16  // validate shared validation logic for create and update resources
    17  func (r *Node) validate() field.ErrorList {
    18  	var nodeErrors field.ErrorList
    19  
    20  	if r.Spec.Validator {
    21  		// validate rpc must be disabled if node is validator
    22  		if r.Spec.RPC {
    23  			err := field.Invalid(field.NewPath("spec").Child("rpc"), r.Spec.RPC, "must be false if node is validator")
    24  			nodeErrors = append(nodeErrors, err)
    25  		}
    26  		// validate ws must be disabled if node is validator
    27  		if r.Spec.WS {
    28  			err := field.Invalid(field.NewPath("spec").Child("ws"), r.Spec.WS, "must be false if node is validator")
    29  			nodeErrors = append(nodeErrors, err)
    30  		}
    31  		// validate pruning must be disabled if node is validator
    32  		if pruning := r.Spec.Pruning; pruning != nil && *pruning {
    33  			err := field.Invalid(field.NewPath("spec").Child("pruning"), r.Spec.Pruning, "must be false if node is validator")
    34  			nodeErrors = append(nodeErrors, err)
    35  		}
    36  
    37  	}
    38  
    39  	return nodeErrors
    40  }
    41  
    42  // ValidateCreate implements webhook.Validator so a webhook will be registered for the type
    43  func (r *Node) ValidateCreate() (admission.Warnings, error) {
    44  	var allErrors field.ErrorList
    45  
    46  	nodelog.Info("validate create", "name", r.Name)
    47  
    48  	allErrors = append(allErrors, r.validate()...)
    49  	allErrors = append(allErrors, r.Spec.Resources.ValidateCreate()...)
    50  
    51  	if len(allErrors) == 0 {
    52  		return nil, nil
    53  	}
    54  
    55  	return nil, apierrors.NewInvalid(schema.GroupKind{}, r.Name, allErrors)
    56  }
    57  
    58  // ValidateUpdate implements webhook.Validator so a webhook will be registered for the type
    59  func (r *Node) ValidateUpdate(old runtime.Object) (admission.Warnings, error) {
    60  	var allErrors field.ErrorList
    61  	oldNode := old.(*Node)
    62  
    63  	nodelog.Info("validate update", "name", r.Name)
    64  
    65  	allErrors = append(allErrors, r.validate()...)
    66  	allErrors = append(allErrors, r.Spec.Resources.ValidateUpdate(&oldNode.Spec.Resources)...)
    67  
    68  	if r.Spec.Network != oldNode.Spec.Network {
    69  		err := field.Invalid(field.NewPath("spec").Child("network"), r.Spec.Network, "field is immutable")
    70  		allErrors = append(allErrors, err)
    71  	}
    72  
    73  	if len(allErrors) == 0 {
    74  		return nil, nil
    75  	}
    76  
    77  	return nil, apierrors.NewInvalid(schema.GroupKind{}, r.Name, allErrors)
    78  }
    79  
    80  // ValidateDelete implements webhook.Validator so a webhook will be registered for the type
    81  func (r *Node) ValidateDelete() (admission.Warnings, error) {
    82  	nodelog.Info("validate delete", "name", r.Name)
    83  
    84  	return nil, nil
    85  }