Merge pull request #137190 from everpeace/KEP-5491-alpha

KEP-5491: DRA: List Types for Attributes [Alpha]

Kubernetes-commit: ef247770b50e7105eb7453c8bfd5279b5a3656ae
This commit is contained in:
Kubernetes Publisher
2026-03-21 14:18:12 +05:30
12 changed files with 297 additions and 3 deletions

View File

@@ -12530,15 +12530,39 @@ var schemaYAML = typed.YAMLObject(`types:
- name: bool
type:
scalar: boolean
- name: bools
type:
list:
elementType:
scalar: boolean
elementRelationship: atomic
- name: int
type:
scalar: numeric
- name: ints
type:
list:
elementType:
scalar: numeric
elementRelationship: atomic
- name: string
type:
scalar: string
- name: strings
type:
list:
elementType:
scalar: string
elementRelationship: atomic
- name: version
type:
scalar: string
- name: versions
type:
list:
elementType:
scalar: string
elementRelationship: atomic
- name: io.k8s.api.resource.v1.DeviceCapacity
map:
fields:
@@ -13386,15 +13410,39 @@ var schemaYAML = typed.YAMLObject(`types:
- name: bool
type:
scalar: boolean
- name: bools
type:
list:
elementType:
scalar: boolean
elementRelationship: atomic
- name: int
type:
scalar: numeric
- name: ints
type:
list:
elementType:
scalar: numeric
elementRelationship: atomic
- name: string
type:
scalar: string
- name: strings
type:
list:
elementType:
scalar: string
elementRelationship: atomic
- name: version
type:
scalar: string
- name: versions
type:
list:
elementType:
scalar: string
elementRelationship: atomic
- name: io.k8s.api.resource.v1beta1.DeviceCapacity
map:
fields:
@@ -14071,15 +14119,39 @@ var schemaYAML = typed.YAMLObject(`types:
- name: bool
type:
scalar: boolean
- name: bools
type:
list:
elementType:
scalar: boolean
elementRelationship: atomic
- name: int
type:
scalar: numeric
- name: ints
type:
list:
elementType:
scalar: numeric
elementRelationship: atomic
- name: string
type:
scalar: string
- name: strings
type:
list:
elementType:
scalar: string
elementRelationship: atomic
- name: version
type:
scalar: string
- name: versions
type:
list:
elementType:
scalar: string
elementRelationship: atomic
- name: io.k8s.api.resource.v1beta2.DeviceCapacity
map:
fields:

View File

@@ -72,6 +72,14 @@ type CELDeviceSelectorApplyConfiguration struct {
//
// cel.bind(dra, device.attributes["dra.example.com"], dra.someBool && dra.anotherBool)
//
// When the DRAListTypeAttributes feature gate is enabled,
// the includes() helper is available and it can work for both scalar
// and list-type attributes. It was introduced to support smooth migration
// from scalar attributes to list-type attributes while keeping
// CEL expressions simple. For example:
//
// device.attributes["dra.example.com"].models.includes("some-model")
//
// The length of the expression must be smaller or equal to 10 Ki. The
// cost of evaluating it is also limited based on the estimated number
// of logical steps.

View File

@@ -32,6 +32,22 @@ type DeviceAttributeApplyConfiguration struct {
// VersionValue is a semantic version according to semver.org spec 2.0.0.
// Must not be longer than 64 characters.
VersionValue *string `json:"version,omitempty"`
// IntValues is a non-empty list of numbers.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
IntValues []int64 `json:"ints,omitempty"`
// BoolValues is a non-empty list of true/false values.
BoolValues []bool `json:"bools,omitempty"`
// StringValues is a non-empty list of strings.
// Each string must not be longer than 64 characters.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
StringValues []string `json:"strings,omitempty"`
// VersionValues is a non-empty list of semantic versions according to semver.org spec 2.0.0.
// Each version string must not be longer than 64 characters.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
VersionValues []string `json:"versions,omitempty"`
}
// DeviceAttributeApplyConfiguration constructs a declarative configuration of the DeviceAttribute type for use with
@@ -71,3 +87,43 @@ func (b *DeviceAttributeApplyConfiguration) WithVersionValue(value string) *Devi
b.VersionValue = &value
return b
}
// WithIntValues adds the given value to the IntValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the IntValues field.
func (b *DeviceAttributeApplyConfiguration) WithIntValues(values ...int64) *DeviceAttributeApplyConfiguration {
for i := range values {
b.IntValues = append(b.IntValues, values[i])
}
return b
}
// WithBoolValues adds the given value to the BoolValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the BoolValues field.
func (b *DeviceAttributeApplyConfiguration) WithBoolValues(values ...bool) *DeviceAttributeApplyConfiguration {
for i := range values {
b.BoolValues = append(b.BoolValues, values[i])
}
return b
}
// WithStringValues adds the given value to the StringValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the StringValues field.
func (b *DeviceAttributeApplyConfiguration) WithStringValues(values ...string) *DeviceAttributeApplyConfiguration {
for i := range values {
b.StringValues = append(b.StringValues, values[i])
}
return b
}
// WithVersionValues adds the given value to the VersionValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the VersionValues field.
func (b *DeviceAttributeApplyConfiguration) WithVersionValues(values ...string) *DeviceAttributeApplyConfiguration {
for i := range values {
b.VersionValues = append(b.VersionValues, values[i])
}
return b
}

View File

@@ -48,11 +48,21 @@ type DeviceConstraintApplyConfiguration struct {
// its specification, but if one device doesn't, then it also will not be
// chosen.
//
// When the DRAListTypeAttributes feature gate is enabled, comparison uses
// set semantics(i.e., element order and duplicates are ignored): list-valued attributes
// match when the intersection across all devices is non-empty.
// Scalar values are treated as single-element lists for backward compatibility.
//
// Must include the domain qualifier.
MatchAttribute *resourcev1.FullyQualifiedName `json:"matchAttribute,omitempty"`
// DistinctAttribute requires that all devices in question have this
// attribute and that its type and value are unique across those devices.
//
// When the DRAListTypeAttributes feature gate is enabled, comparison uses
// set semantics (i.e., element order and duplicates are ignored):
// list-valued attributes must be pairwise disjoint across devices.
// Scalar values are treated as singleton sets for backward compatibility.
//
// This acts as the inverse of MatchAttribute.
//
// This constraint is used to avoid allocating multiple requests to the same device

View File

@@ -72,6 +72,14 @@ type CELDeviceSelectorApplyConfiguration struct {
//
// cel.bind(dra, device.attributes["dra.example.com"], dra.someBool && dra.anotherBool)
//
// When the DRAListTypeAttributes feature gate is enabled,
// the includes() helper is available and it can work for both scalar
// and list-type attributes. It was introduced to support smooth migration
// from scalar attributes to list-type attributes while keeping
// CEL expressions simple. For example:
//
// device.attributes["dra.example.com"].models.includes("some-model")
//
// The length of the expression must be smaller or equal to 10 Ki. The
// cost of evaluating it is also limited based on the estimated number
// of logical steps.

View File

@@ -32,6 +32,22 @@ type DeviceAttributeApplyConfiguration struct {
// VersionValue is a semantic version according to semver.org spec 2.0.0.
// Must not be longer than 64 characters.
VersionValue *string `json:"version,omitempty"`
// IntValues is a non-empty list of numbers.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
IntValues []int64 `json:"ints,omitempty"`
// BoolValues is a non-empty list of true/false values.
BoolValues []bool `json:"bools,omitempty"`
// StringValues is a non-empty list of strings.
// Each string must not be longer than 64 characters.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
StringValues []string `json:"strings,omitempty"`
// VersionValues is a non-empty list of semantic versions according to semver.org spec 2.0.0.
// Each version string must not be longer than 64 characters.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
VersionValues []string `json:"versions,omitempty"`
}
// DeviceAttributeApplyConfiguration constructs a declarative configuration of the DeviceAttribute type for use with
@@ -71,3 +87,43 @@ func (b *DeviceAttributeApplyConfiguration) WithVersionValue(value string) *Devi
b.VersionValue = &value
return b
}
// WithIntValues adds the given value to the IntValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the IntValues field.
func (b *DeviceAttributeApplyConfiguration) WithIntValues(values ...int64) *DeviceAttributeApplyConfiguration {
for i := range values {
b.IntValues = append(b.IntValues, values[i])
}
return b
}
// WithBoolValues adds the given value to the BoolValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the BoolValues field.
func (b *DeviceAttributeApplyConfiguration) WithBoolValues(values ...bool) *DeviceAttributeApplyConfiguration {
for i := range values {
b.BoolValues = append(b.BoolValues, values[i])
}
return b
}
// WithStringValues adds the given value to the StringValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the StringValues field.
func (b *DeviceAttributeApplyConfiguration) WithStringValues(values ...string) *DeviceAttributeApplyConfiguration {
for i := range values {
b.StringValues = append(b.StringValues, values[i])
}
return b
}
// WithVersionValues adds the given value to the VersionValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the VersionValues field.
func (b *DeviceAttributeApplyConfiguration) WithVersionValues(values ...string) *DeviceAttributeApplyConfiguration {
for i := range values {
b.VersionValues = append(b.VersionValues, values[i])
}
return b
}

View File

@@ -48,11 +48,21 @@ type DeviceConstraintApplyConfiguration struct {
// its specification, but if one device doesn't, then it also will not be
// chosen.
//
// When the DRAListTypeAttributes feature gate is enabled, comparison uses
// set semantics(i.e., element order and duplicates are ignored): list-valued attributes
// match when the intersection across all devices is non-empty.
// Scalar values are treated as singleton sets for backward compatibility.
//
// Must include the domain qualifier.
MatchAttribute *resourcev1beta1.FullyQualifiedName `json:"matchAttribute,omitempty"`
// DistinctAttribute requires that all devices in question have this
// attribute and that its type and value are unique across those devices.
//
// When the DRAListTypeAttributes feature gate is enabled, comparison uses
// set semantics (i.e., element order and duplicates are ignored):
// list-valued attributes must be pairwise disjoint across devices.
// Scalar values are treated as singleton sets for backward compatibility.
//
// This acts as the inverse of MatchAttribute.
//
// This constraint is used to avoid allocating multiple requests to the same device

View File

@@ -72,6 +72,14 @@ type CELDeviceSelectorApplyConfiguration struct {
//
// cel.bind(dra, device.attributes["dra.example.com"], dra.someBool && dra.anotherBool)
//
// When the DRAListTypeAttributes feature gate is enabled,
// the includes() helper is available and it can work for both scalar
// and list-type attributes. It was introduced to support smooth migration
// from scalar attributes to list-type attributes while keeping
// CEL expressions simple. For example:
//
// device.attributes["dra.example.com"].models.includes("some-model")
//
// The length of the expression must be smaller or equal to 10 Ki. The
// cost of evaluating it is also limited based on the estimated number
// of logical steps.

View File

@@ -32,6 +32,22 @@ type DeviceAttributeApplyConfiguration struct {
// VersionValue is a semantic version according to semver.org spec 2.0.0.
// Must not be longer than 64 characters.
VersionValue *string `json:"version,omitempty"`
// IntValues is a non-empty list of numbers.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
IntValues []int64 `json:"ints,omitempty"`
// BoolValues is a non-empty list of true/false values.
BoolValues []bool `json:"bools,omitempty"`
// StringValues is a non-empty list of strings.
// Each string must not be longer than 64 characters.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
StringValues []string `json:"strings,omitempty"`
// VersionValues is a non-empty list of semantic versions according to semver.org spec 2.0.0.
// Each version string must not be longer than 64 characters.
//
// This is an alpha field and requires enabling the DRAListTypeAttributes feature gate.
VersionValues []string `json:"versions,omitempty"`
}
// DeviceAttributeApplyConfiguration constructs a declarative configuration of the DeviceAttribute type for use with
@@ -71,3 +87,43 @@ func (b *DeviceAttributeApplyConfiguration) WithVersionValue(value string) *Devi
b.VersionValue = &value
return b
}
// WithIntValues adds the given value to the IntValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the IntValues field.
func (b *DeviceAttributeApplyConfiguration) WithIntValues(values ...int64) *DeviceAttributeApplyConfiguration {
for i := range values {
b.IntValues = append(b.IntValues, values[i])
}
return b
}
// WithBoolValues adds the given value to the BoolValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the BoolValues field.
func (b *DeviceAttributeApplyConfiguration) WithBoolValues(values ...bool) *DeviceAttributeApplyConfiguration {
for i := range values {
b.BoolValues = append(b.BoolValues, values[i])
}
return b
}
// WithStringValues adds the given value to the StringValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the StringValues field.
func (b *DeviceAttributeApplyConfiguration) WithStringValues(values ...string) *DeviceAttributeApplyConfiguration {
for i := range values {
b.StringValues = append(b.StringValues, values[i])
}
return b
}
// WithVersionValues adds the given value to the VersionValues field in the declarative configuration
// and returns the receiver, so that objects can be build by chaining "With" function invocations.
// If called multiple times, values provided by each call will be appended to the VersionValues field.
func (b *DeviceAttributeApplyConfiguration) WithVersionValues(values ...string) *DeviceAttributeApplyConfiguration {
for i := range values {
b.VersionValues = append(b.VersionValues, values[i])
}
return b
}

View File

@@ -48,11 +48,21 @@ type DeviceConstraintApplyConfiguration struct {
// its specification, but if one device doesn't, then it also will not be
// chosen.
//
// When the DRAListTypeAttributes feature gate is enabled, comparison uses
// set semantics(i.e., element order and duplicates are ignored): list-valued attributes
// match when the intersection across all devices is non-empty.
// Scalar values are treated as singleton sets for backward compatibility.
//
// Must include the domain qualifier.
MatchAttribute *resourcev1beta2.FullyQualifiedName `json:"matchAttribute,omitempty"`
// DistinctAttribute requires that all devices in question have this
// attribute and that its type and value are unique across those devices.
//
// When the DRAListTypeAttributes feature gate is enabled, comparison uses
// set semantics (i.e., element order and duplicates are ignored):
// list-valued attributes must be pairwise disjoint across devices.
// Scalar values are treated as singleton sets for backward compatibility.
//
// This acts as the inverse of MatchAttribute.
//
// This constraint is used to avoid allocating multiple requests to the same device

2
go.mod
View File

@@ -23,7 +23,7 @@ require (
golang.org/x/time v0.14.0
google.golang.org/protobuf v1.36.12-0.20260120151049-f2248ac996af
gopkg.in/evanphx/json-patch.v4 v4.13.0
k8s.io/api v0.0.0-20260321024613-6bf46eb598a7
k8s.io/api v0.0.0-20260321105602-61bd78e724dd
k8s.io/apimachinery v0.0.0-20260319035426-a76ee7450772
k8s.io/klog/v2 v2.140.0
k8s.io/kube-openapi v0.0.0-20260317180543-43fb72c5454a

4
go.sum
View File

@@ -105,8 +105,8 @@ gopkg.in/inf.v0 v0.9.1/go.mod h1:cWUDdTG/fYaXco+Dcufb5Vnc6Gp2YChqWtbxRZE0mXw=
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
k8s.io/api v0.0.0-20260321024613-6bf46eb598a7 h1:OViBD2upI7EtIyqZiZ1/nqSNEA7Qz5RYPoyyp4IGdus=
k8s.io/api v0.0.0-20260321024613-6bf46eb598a7/go.mod h1:fj3AOwVJRH4zYT3LWoIZ4uKCWetMAIfelAD1pZFtdcw=
k8s.io/api v0.0.0-20260321105602-61bd78e724dd h1:xVntEPWYlN69Qkdx02ZQYO4+tY6QwbWLA2kD1RkcoDA=
k8s.io/api v0.0.0-20260321105602-61bd78e724dd/go.mod h1:fj3AOwVJRH4zYT3LWoIZ4uKCWetMAIfelAD1pZFtdcw=
k8s.io/apimachinery v0.0.0-20260319035426-a76ee7450772 h1:G8EM8vqSfIpITuNGsH/KVCiyELbL5Xe6tCRiJOWJuoU=
k8s.io/apimachinery v0.0.0-20260319035426-a76ee7450772/go.mod h1:Fjag9BypDOzB4sV3iuZaNeDsRkf89asmbm8aWLerfeU=
k8s.io/klog/v2 v2.140.0 h1:Tf+J3AH7xnUzZyVVXhTgGhEKnFqye14aadWv7bzXdzc=