=jsonPatch"`
}

// PatchType specifies the type of patch operation for a mutation.
// +enum
type PatchType string

const (
	// ApplyConfiguration indicates that the mutation is using apply configuration to mutate the object.
	PatchTypeApplyConfiguration PatchType = "ApplyConfiguration"
	// JSONPatch indicates that the object is mutated through JSON Patch.
	PatchTypeJSONPatch PatchType = "JSONPatch"
)

// ApplyConfiguration defines the desired configuration values of an object.
type ApplyConfiguration struct {
	// expression will be evaluated by CEL to create an apply configuration.
	// ref: https://github.com/google/cel-spec
	//
	// Apply configurations are declared in CEL using object initialization. For example, this CEL expression
	// returns an apply configuration to set a single field:
	//
	//	Object{
	//	  spec: Object.spec{
	//	    serviceAccountName: "example"
	//	  }
	//	}
	//
	// Apply configurations may not modify atomic structs, maps or arrays due to the risk of accidental deletion of
	// values not included in the apply configuration.
	//
	// CEL expressions have access to the object types needed to create apply configurations:
	//
	// - 'Object' - CEL type of the resource object.
	// - 'Object.<fieldName>' - CEL type of object field (such as 'Object.spec')
	// - 'Object.<fieldName1>.<fieldName2>...<fieldNameN>` - CEL type of nested field (such as 'Object.spec.containers')
	//
	// CEL expressions have access to the contents of the API request, organized into CEL variables as well as some other useful variables:
	//
	// - 'object' - The object from the incoming request. The value is null for DELETE requests.
	// - 'oldObject' - The existing object. The value is null for CREATE requests.
	// - 'request' - Attributes of the API request([ref](/pkg/apis/admission/types.go#AdmissionRequest)).
	// - 'params' - Parameter resource referred to by the policy binding being evaluated. Only populated if the policy has a ParamKind.
	// - 'namespaceObject' - The namespace object that the incoming object belongs to. The value is null for cluster-scoped resources.
	// - 'variables' - Map of composited variables, from its name to its lazily evaluated value.
	//   For example, a variable named 'foo' can be accessed as 'variables.foo'.
	// - 'authorizer' - A CEL Authorizer. May be used to perform authorization checks for the principal (user or service account) of the request.
	//   See https://pkg.go.dev/k8s.io/apiserver/pkg/cel/library#Authz
	// - 'authorizer.requestResource' - A CEL ResourceCheck constructed from the 'authorizer' and configured with the
	//   request resource.
	//
	// The `apiVersion`, `kind`, `metadata.name` and `metadata.generateName` are always accessible from the root of the
	// object. No other metadata properties are accessible.
	//
	// Only property names of the form `[a-zA-Z_.-/][a-zA-Z0-9_.-/]*` are accessible.
	// Required.
	Expression string `json:"expression,omitempty" protobuf:"bytes,1,opt,name=expression"`
}

// JSONPatch defines a JSON Patch.
type JSONPatch struct {
	// expression will be evaluated by CEL to create a [JSON patch](https://jsonpatch.com/).
	// ref: https://github.com/google/cel-spec
	//
	// expression must return an array of JSONPatch values.
	//
	// For example, this CEL expression returns a JSON patch to conditionally modify a value:
	//
	//	  [
	//	    JSONPatch{op: "test", path: "/spec/example", value: "Red"},
	//	    JSONPatch{op: "replace", path: "/spec/example", value: "Green"}
	//	  ]
	//
	// To define an object for the patch value, use Object types. For example:
	//
	//	  [
	//	    JSONPatch{
	//	      op: "add",
	//	      path: "/spec/selector",
	//	      value: Object.spec.selector{matchLabels: {"environment": "test"}}
	//	    }
	//	  ]
	//
	// To use strings containing '/' and '~' as JSONPatch path keys, use "jsonpatch.escapeKey". For example:
	//
	//	  [
	//	    JSONPatch{
	//	      op: "add",
	//	      path: "/metadata/labels/" + jsonpatch.escapeKey("example.com/environment"),
	//	      value: "test"
	//	    },
	//	  ]
	//
	// CEL expressions have access to the types needed to create JSON patches and objects:
	//
	// - 'JSONPatch' - CEL type of JSON Patch operations. JSONPatch has the fields 'op', 'from', 'path' and 'value'.
	//   See [JSON patch](https://jsonpatch.com/) for more details. The 'value' field may be set to any of: string,
	//   integer, array, map or object.  If set, the 'path' and 'from' fields must be set to a
	//   [JSON pointer](https://datatracker.ietf.org/doc/html/rfc6901/) string, where the 'jsonpatch.escapeKey()' CEL
	//   function may be used to escape path keys containing '/' and '~'.
	// - 'Object' - CEL type of the resource object.
	// - 'Object.<fieldName>' - CEL type of object field (such as 'Object.spec')
	// - 'Object.<fieldName1>.<fieldName2>...<fieldNameN>` - CEL type of nested field (such as 'Object.spec.containers')
	//
	// CEL expressions have access to the contents of the API request, organized into CEL variables as well as some other useful variables:
	//
	// - 'object' - The object from the incoming request. The value is null for DELETE requests.
	// - 'oldObject' - The existing object. The value is null for CREATE requests.
	// - 'request' - Attributes of the API request([ref](/pkg/apis/admission/types.go#AdmissionRequest)).
	// - 'params' - Parameter resource referred to by the policy binding being evaluated. Only populated if the policy has a ParamKind.
	// - 'namespaceObject' - The namespace object that the incoming object belongs to. The value is null for cluster-scoped resources.
	// - 'variables' - Map of composited variables, from its name to its lazily evaluated value.
	//   For example, a variable named 'foo' can be accessed as 'variables.foo'.
	// - 'authorizer' - A CEL Authorizer. May be used to perform authorization checks for the principal (user or service account) of the request.
	//   See https://pkg.go.dev/k8s.io/apiserver/pkg/cel/library#Authz
	// - 'authorizer.requestResource' - A CEL ResourceCheck constructed from the 'authorizer' and configured with the
	//   request resource.
	//
	// CEL expressions have access to [Kubernetes CEL function libraries](https://kubernetes.io/docs/reference/using-api/cel/#cel-options-language-features-and-libraries)
	// as well as:
	//
	// - 'jsonpatch.escapeKey' - Performs JSONPatch key escaping. '~' and  '/' are escaped as '~0' and `~1' respectively).
	//
	//
	// Only property names of the form `[a-zA-Z_.-/][a-zA-Z0-9_.-/]*` are accessible.
	// Required.
	Expression string `json:"expression,omitempty" protobuf:"bytes,1,opt,name=expression"`
}

// +genclient
// +genclient:nonNamespaced
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
// +k8s:prerelease-lifecycle-gen:introduced=1.34

// MutatingAdmissionPolicyBinding binds the MutatingAdmissionPolicy with parametrized resources.
// MutatingAdmissionPolicyBinding and the optional parameter resource together define how cluster administrators
// configure policies for clusters.
//
// For a given admission request, each binding will cause its policy to be
// evaluated N times, where N is 1 for policies/bindings that don't use
// params, otherwise N is the number of parameters selected by the binding.
// Each evaluation is constrained by a [runtime cost budget](https://kubernetes.io/docs/reference/using-api/cel/#runtime-cost-budget).
//
// Adding/removing policies, bindings, or params can not affect whether a
// given (policy, binding, param) combination is within its own CEL budget.
type MutatingAdmissionPolicyBinding struct {
	metav1.TypeMeta `json:",inline"`
	// Standard object metadata; More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata.
	// +optional
	metav1.ObjectMeta `json:"metadata,omitempty" protobuf:"bytes,1,opt,name=metadata"`
	// Specification of the desired behavior of the MutatingAdmissionPolicyBinding.
	Spec MutatingAdmissionPolicyBindingSpec `json:"spec,omitempty" protobuf:"bytes,2,opt,name=spec"`
}

// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
// +k8s:prerelease-lifecycle-gen:introduced=1.34

// MutatingAdmissionPolicyBindingList is a list of MutatingAdmissionPolicyBinding.
type MutatingAdmissionPolicyBindingList struct {
	metav1.TypeMeta `json:",inline"`
	// Standard list metadata.
	// More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds
	// +optional
	metav1.ListMeta `json:"metadata,omitempty" protobuf:"bytes,1,opt,name=metadata"`
	// List of PolicyBinding.
	Items []MutatingAdmissionPolicyBinding `json:"items" protobuf:"bytes,2,rep,name=items"`
}

// MutatingAdmissionPolicyBindingSpec is the specification of the MutatingAdmissionPolicyBinding.
type MutatingAdmissionPolicyBindingSpec struct {
	// policyName references a MutatingAdmissionPolicy name which the MutatingAdmissionPolicyBinding binds to.
	// If the referenced resource does not exist, this binding is considered invalid and will be ignored
	// Required.
	PolicyName string `json:"policyName,omitempty" protobuf:"bytes,1,rep,name=policyName"`

	// paramRef specifies the parameter resource used to configure the admission control policy.
	// It should point to a resource of the type specified in spec.ParamKind of the bound MutatingAdmissionPolicy.
	// If the policy specifies a ParamKind and the resource referred to by ParamRef does not exist, this binding is considered mis-configured and the FailurePolicy of the MutatingAdmissionPolicy applied.
	// If the policy does not specify a ParamKind then this field is ignored, and the rules are evaluated without a param.
	// +optional
	ParamRef *ParamRef `json:"paramRef,omitempty" protobuf:"bytes,2,rep,name=paramRef"`

	// matchResources limits what resources match this binding and may be mutated by it.
	// Note that if matchResources matches a resource, the resource must also match a policy's matchConstraints and
	// matchConditions before the resource may be mutated.
	// When matchResources is unset, it does not constrain resource matching, and only the policy's matchConstraints
	// and matchConditions must match for the resource to be mutated.
	// Additionally, matchResources.resourceRules are optional and do not constraint matching when unset.
	// Note that this is differs from MutatingAdmissionPolicy matchConstraints, where resourceRules are required.
	// The CREATE, UPDATE and CONNECT operations are allowed.  The DELETE operation may not be matched.
	// '*' matches CREATE, UPDATE and CONNECT.
	// +optional
	MatchResources *MatchResources `json:"matchResources,omitempty" protobuf:"bytes,3,rep,name=matchResources"`
}
