-
-
Notifications
You must be signed in to change notification settings - Fork 366
Description
Current and expected behavior
Consider the following CRD:
#[derive(CustomResource, Deserialize, Serialize, Clone, Debug, JsonSchema)]
#[kube(
kind = "MyCRD",
group = "example.com",
version = "v1",
namespaced
)]
pub struct MyCRDSpec {
pub subitem: SubItemDenyUnknown,
}
#[derive(Deserialize, Serialize, Clone, Debug, JsonSchema)]
#[serde(deny_unknown_fields)]
pub struct SubItemDenyUnknown {
pub one: String,
pub two: bool,
pub three: i32,
}When #[serde(deny_unknown_fields)] is specified, this generates a CRD with both a additionalProperties: false, and properties: of the SubItemDenyUnknown object itself:
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
name: mycrds.example.com
spec:
group: example.com
names:
categories: []
kind: MyCRD
plural: mycrds
shortNames: []
singular: mycrd
scope: Namespaced
versions:
- additionalPrinterColumns: []
name: v1
schema:
openAPIV3Schema:
description: Auto-generated derived type for MyCRDSpec via `CustomResource`
properties:
spec:
properties:
subitem:
additionalProperties: false
properties:
one:
type: string
three:
format: int32
type: integer
two:
type: boolean
required:
- one
- three
- two
type: object
required:
- subitem
type: object
required:
- spec
title: MyCRD
type: object
served: true
storage: true
subresources: {}Because this object already contains properties, I would expect additionalProperties to not be specified here as it results in a Kubernetes CRD validation error:
Forbidden: additionalProperties and properties are mutual exclusivePossible solution
I saw a similar issue in #844. I am not sure if a similar fix is applicable here. I think omitting additionalProperties: false entirely might be more applicable (see context).
Additional context
The CRD Validation page in the Kubernetes docs states:
The field
additionalPropertiescannot be set tofalse.
It doesn't seem like this returns an error though, as I tried applying this CRD which applied successfully but pruned the additionalProperties: false from the actual applied CRD. The CRD I applied:
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
name: mycrds.example.com
spec:
group: example.com
names:
categories: []
kind: MyCRD
plural: mycrds
shortNames: []
singular: mycrd
scope: Namespaced
versions:
- additionalPrinterColumns: []
name: v1
schema:
openAPIV3Schema:
description: Auto-generated derived type for MyCRDSpec via `CustomResource`
properties:
spec:
properties:
one:
type: string
two:
type: object
additionalProperties: false
required:
- one
type: object
required:
- spec
title: MyCRD
type: object
served: true
storage: true
subresources: {}And this is what ended up on my cluster:
spec:
conversion:
strategy: None
group: example.com
names:
kind: MyCRD
listKind: MyCRDList
plural: mycrds
singular: mycrd
scope: Namespaced
versions:
- name: v1
schema:
openAPIV3Schema:
description: Auto-generated derived type for MyCRDSpec via `CustomResource`
properties:
spec:
properties:
one:
type: string
two:
type: object
required:
- one
type: object
required:
- spec
title: MyCRD
type: object
served: true
storage: true
subresources: {}
status:
acceptedNames:
kind: MyCRD
listKind: MyCRDList
plural: mycrds
singular: mycrd
conditions:
- lastTransitionTime: "2025-09-25T06:25:43Z"
message: no conflicts found
reason: NoConflicts
status: "True"
type: NamesAccepted
- lastTransitionTime: "2025-09-25T06:25:43Z"
message: the initial names have been accepted
reason: InitialNamesAccepted
status: "True"
type: Established
storedVersions:
- v1Environment
I am running with kind, using a regular kind create cluster:
Client Version: v1.33.4
Kustomize Version: v5.6.0
Server Version: v1.33.1Configuration and features
k8s-openapi = { version = "0.26.0", features = ["latest", "schemars"] }
kube = { version = "2.0.1", features = ["runtime", "client", "derive"] }YAML
No response
Affected crates
No response
Would you like to work on fixing this bug?
yes