Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion pkg/applyconfiguration/zz_generated.markerhelp.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

126 changes: 121 additions & 5 deletions pkg/crd/markers/crd.go
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,19 @@ func init() {
// +controllertools:marker:generateHelp:category=CRD

// SubresourceStatus enables the "/status" subresource on a CRD.
//
// The status subresource allows you to update the status field separately from the rest
// of the resource spec. This is useful for separating user-provided spec from system-provided status.
//
// Example:
//
// // +kubebuilder:subresource:status
// type MyCRD struct {
// metav1.TypeMeta
// metav1.ObjectMeta
// Spec MyCRDSpec
// Status MyCRDStatus
// }
type SubresourceStatus struct{}

func (s SubresourceStatus) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinitionSpec, version string) error {
Expand All @@ -94,19 +107,34 @@ func (s SubresourceStatus) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinit
// +controllertools:marker:generateHelp:category=CRD

// SubresourceScale enables the "/scale" subresource on a CRD.
//
// The scale subresource allows you to use `kubectl scale` and the HorizontalPodAutoscaler with your CRD.
//
// Example:
//
// // +kubebuilder:subresource:scale:specpath=.spec.replicas,statuspath=.status.replicas,selectorpath=.status.selector
// type MyCRD struct {
// metav1.TypeMeta
// metav1.ObjectMeta
// Spec MyCRDSpec
// Status MyCRDStatus
// }
type SubresourceScale struct {
// marker names are leftover legacy cruft

// SpecPath specifies the jsonpath to the replicas field for the scale's spec.
// This is where the desired number of replicas is stored (typically .spec.replicas).
SpecPath string `marker:"specpath"`

// StatusPath specifies the jsonpath to the replicas field for the scale's status.
// This is where the actual number of replicas is stored (typically .status.replicas).
StatusPath string `marker:"statuspath"`

// SelectorPath specifies the jsonpath to the pod label selector field for the scale's status.
//
// The selector field must be the *string* form (serialized form) of a selector.
// Setting a pod label selector is necessary for your type to work with the HorizontalPodAutoscaler.
// This is typically .status.selector.
SelectorPath *string `marker:"selectorpath"`
}

Expand Down Expand Up @@ -141,6 +169,15 @@ func (s SubresourceScale) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefiniti
// When conversion is enabled for a CRD (i.e. it's not a trivial-versions/single-version CRD),
// one version is set as the "storage version" to be stored in etcd. Attempting to store any
// other version will result in conversion to the storage version via a conversion webhook.
//
// Example:
//
// // +kubebuilder:storageversion
// type MyCRDv2 struct {
// metav1.TypeMeta
// metav1.ObjectMeta
// Spec MyCRDSpec
// }
type StorageVersion struct{}

func (s StorageVersion) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinitionSpec, version string) error {
Expand All @@ -167,6 +204,13 @@ func (s StorageVersion) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinition
// This is useful if you need to skip generating and listing version entries
// for 'internal' resource versions, which typically exist if using the
// Kubernetes upstream conversion-gen tool.
//
// Example:
//
// // +kubebuilder:skipversion
// type MyCRDInternal struct {
// // internal version not served by API
// }
type SkipVersion struct{}

func (s SkipVersion) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinitionSpec, version string) error {
Expand All @@ -191,20 +235,34 @@ func (s SkipVersion) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinitionSpe
// +controllertools:marker:generateHelp:category=CRD

// PrintColumn adds a column to "kubectl get" output for this CRD.
//
// This allows you to customize what columns are shown when users run `kubectl get` on your CRD.
//
// Example:
//
// // +kubebuilder:printcolumn:name="Status",type=string,JSONPath=`.status.phase`
// // +kubebuilder:printcolumn:name="Age",type=date,JSONPath=`.metadata.creationTimestamp`
// type MyCRD struct {
// metav1.TypeMeta
// metav1.ObjectMeta
// }
type PrintColumn struct {
// Name specifies the name of the column.
// Name specifies the name of the column as it will appear in the header.
Name string

// Type indicates the type of the column.
//
// It may be any OpenAPI data type listed at
// https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#data-types.
// Common values: "string", "integer", "number", "boolean", "date".
Type string

// JSONPath specifies the jsonpath expression used to extract the value of the column.
// The path is relative to the resource root. Example: `.status.phase` or `.spec.replicas`.
JSONPath string `marker:"JSONPath"` // legacy cruft

// Description specifies the help/description for this column.
// This is shown when using `kubectl get` with the `-o wide` flag.
Description string `marker:",optional"`

// Format specifies the format of the column.
Expand All @@ -216,7 +274,7 @@ type PrintColumn struct {
// Priority indicates how important it is that this column be displayed.
//
// Lower priority (*higher* numbered) columns will be hidden if the terminal
// width is too small.
// width is too small. Priority 0 columns are always shown.
Priority int32 `marker:",optional"`
}

Expand Down Expand Up @@ -252,36 +310,48 @@ func (s PrintColumn) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinitionSpe
// +controllertools:marker:generateHelp:category=CRD

// Resource configures naming and scope for a CRD.
//
// Example:
//
// // +kubebuilder:resource:path=mycrdplural,singular=mycrdsingular,shortName=mc;mcrd,categories=all,scope=Namespaced
// type MyCRD struct {
// metav1.TypeMeta
// metav1.ObjectMeta
// }
type Resource struct {
// Path specifies the plural "resource" for this CRD.
//
// It generally corresponds to a plural, lower-cased version of the Kind.
// For example, if the Kind is "MyCRD", the path might be "mycrds".
// See https://book.kubebuilder.io/cronjob-tutorial/gvks.html.
Path string `marker:",optional"`

// ShortName specifies aliases for this CRD.
//
// Short names are often used when people have work with your resource
// over and over again. For instance, "rs" for "replicaset" or
// "crd" for customresourcedefinition.
// "crd" for customresourcedefinition. Multiple short names can be specified
// separated by semicolons.
ShortName []string `marker:",optional"`

// Categories specifies which group aliases this resource is part of.
//
// Group aliases are used to work with groups of resources at once.
// The most common one is "all" which covers about a third of the base
// resources in Kubernetes, and is generally used for "user-facing" resources.
// This allows users to run commands like `kubectl get all` to include your CRD.
Categories []string `marker:",optional"`

// Singular overrides the singular form of your resource.
//
// The singular form is otherwise defaulted off the plural (path).
// This is used in API responses and `kubectl` output.
Singular string `marker:",optional"`

// Scope overrides the scope of the CRD (Cluster vs Namespaced).
//
// Scope defaults to "Namespaced". Cluster-scoped ("Cluster") resources
// don't exist in namespaces.
// don't exist in namespaces and are accessible from anywhere in the cluster.
Scope string `marker:",optional"`
}

Expand Down Expand Up @@ -310,6 +380,15 @@ func (s Resource) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinitionSpec,
// UnservedVersion does not serve this version.
//
// This is useful if you need to drop support for a version in favor of a newer version.
// The version will still be stored in etcd if it's the storage version, but won't be
// served via the API.
//
// Example:
//
// // +kubebuilder:unservedversion
// type MyCRDv1alpha1 struct {
// // This version is no longer served
// }
type UnservedVersion struct{}

func (s UnservedVersion) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinitionSpec, version string) error {
Expand All @@ -329,8 +408,20 @@ func (s UnservedVersion) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinitio
// +controllertools:marker:generateHelp:category=CRD

// DeprecatedVersion marks this version as deprecated.
//
// Deprecated versions show a warning message when used. This is useful for
// communicating to users that they should migrate to a newer version.
//
// Example:
//
// // +kubebuilder:deprecatedversion:warning="v1alpha1 is deprecated; use v1 instead"
// type MyCRDv1alpha1 struct {
// metav1.TypeMeta
// metav1.ObjectMeta
// }
type DeprecatedVersion struct {
// Warning message to be shown on the deprecated version
// Warning message to be shown on the deprecated version.
// This message is displayed to users when they interact with the deprecated version.
Warning *string `marker:",optional"`
}

Expand All @@ -357,10 +448,22 @@ func (s DeprecatedVersion) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinit
// Metadata configures the additional annotations or labels for this CRD.
// For example adding annotation "api-approved.kubernetes.io" for a CRD with Kubernetes groups,
// or annotation "cert-manager.io/inject-ca-from-secret" for a CRD that needs CA injection.
//
// Example:
//
// // +kubebuilder:metadata:annotations="api-approved.kubernetes.io/v1=https://github.com/myorg/myrepo/pull/123"
// // +kubebuilder:metadata:labels="app=myapp"
// type MyCRD struct {
// metav1.TypeMeta
// metav1.ObjectMeta
// }
type Metadata struct {
// Annotations will be added into the annotations of this CRD.
// Format: "key=value". Multiple annotations can be specified by repeating the marker.
Annotations []string `marker:",optional"`

// Labels will be added into the labels of this CRD.
// Format: "key=value". Multiple labels can be specified by repeating the marker.
Labels []string `marker:",optional"`
}

Expand Down Expand Up @@ -394,8 +497,21 @@ func (s Metadata) ApplyToCRD(crd *apiextensionsv1.CustomResourceDefinition, _ st
// +controllertools:marker:generateHelp:category=CRD

// SelectableField adds a field that may be used with field selectors.
//
// Field selectors allow users to filter resources based on field values when listing.
// For example, `kubectl get mycrds --field-selector status.phase=Running`.
//
// Example:
//
// // +kubebuilder:selectablefield:JSONPath=".status.phase"
// type MyCRD struct {
// metav1.TypeMeta
// metav1.ObjectMeta
// Status MyCRDStatus
// }
type SelectableField struct {
// JSONPath specifies the jsonpath expression which is used to produce a field selector value.
// The path is relative to the resource root. Example: `.status.phase`.
JSONPath string `marker:"JSONPath"`
}

Expand Down
10 changes: 5 additions & 5 deletions pkg/crd/markers/package.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,18 +23,18 @@ import (
func init() {
AllDefinitions = append(AllDefinitions,
mustOptional(markers.MakeDefinition("groupName", markers.DescribesPackage, "")).
WithHelp(markers.SimpleHelp("CRD", "specifies the API group name for this package.")),
WithHelp(markers.SimpleHelp("CRD", "specifies the API group name for this package. Example: +groupName=mygroup.example.com")),

must(markers.MakeDefinition("versionName", markers.DescribesPackage, "")).
WithHelp(markers.SimpleHelp("CRD", "overrides the API group version for this package (defaults to the package name).")),
WithHelp(markers.SimpleHelp("CRD", "overrides the API group version for this package (defaults to the package name). Example: +versionName=v1beta1")),

must(markers.MakeDefinition("kubebuilder:validation:Optional", markers.DescribesPackage, struct{}{})).
WithHelp(markers.SimpleHelp("CRD validation", "specifies that all fields in this package are optional by default.")),
WithHelp(markers.SimpleHelp("CRD validation", "specifies that all fields in this package are optional by default. Use at package level to make all fields optional unless explicitly marked as required.")),

must(markers.MakeDefinition("kubebuilder:validation:Required", markers.DescribesPackage, struct{}{})).
WithHelp(markers.SimpleHelp("CRD validation", "specifies that all fields in this package are required by default.")),
WithHelp(markers.SimpleHelp("CRD validation", "specifies that all fields in this package are required by default. Use at package level to make all fields required unless explicitly marked as optional.")),

must(markers.MakeDefinition("kubebuilder:skip", markers.DescribesPackage, struct{}{})).
WithHelp(markers.SimpleHelp("CRD", "don't consider this package as an API version.")),
WithHelp(markers.SimpleHelp("CRD", "don't consider this package as an API version. Use this to exclude internal or helper packages from CRD generation.")),
)
}
Loading
Loading