From 7a1c62b8bc63f10dbad7673c59b6f62a6c9497bd Mon Sep 17 00:00:00 2001 From: Andrey Smirnov Date: Wed, 31 Jul 2024 19:08:04 +0400 Subject: [PATCH] feat: publish installed extensions as node labels/annotations Extensions are posted the following way: `extensions.talos.dev/=` The name should be valid as a label (annotation) key. If the value is valid as a label value, use labels, otherwise use annotations. Also implements node annotations in the machine config as a side-effect. Fixes #9089 Fixes #8971 See #9070 Signed-off-by: Andrey Smirnov --- api/resource/definitions/k8s/k8s.proto | 6 + hack/release.toml | 19 + .../controllers/k8s/node_annotation_spec.go | 108 ++++ .../k8s/node_annotation_spec_test.go | 122 ++++ .../pkg/controllers/k8s/node_apply.go | 86 ++- .../pkg/controllers/k8s/node_apply_test.go | 121 +++- .../pkg/controllers/k8s/node_label_spec.go | 50 +- .../controllers/k8s/node_label_spec_test.go | 37 ++ .../pkg/runtime/v1alpha1/v1alpha1_runtime.go | 2 + .../runtime/v1alpha2/v1alpha2_controller.go | 1 + .../pkg/runtime/v1alpha2/v1alpha2_state.go | 1 + internal/integration/api/node-annotations.go | 163 +++++ internal/integration/api/node-labels.go | 2 +- .../api/resource/definitions/k8s/k8s.pb.go | 565 ++++++++++-------- .../definitions/k8s/k8s_vtproto.pb.go | 180 ++++++ pkg/machinery/config/config/machine.go | 4 + .../config/schemas/config.schema.json | 12 + .../types/v1alpha1/v1alpha1_provider.go | 5 + .../config/types/v1alpha1/v1alpha1_types.go | 6 + .../types/v1alpha1/v1alpha1_types_doc.go | 10 +- .../types/v1alpha1/v1alpha1_validation.go | 4 + pkg/machinery/constants/constants.go | 6 + pkg/machinery/labels/validate.go | 32 + pkg/machinery/labels/validate_test.go | 42 ++ .../resources/k8s/deep_copy.generated.go | 8 +- pkg/machinery/resources/k8s/k8s.go | 2 +- pkg/machinery/resources/k8s/k8s_test.go | 1 + .../resources/k8s/node_annotation_spec.go | 64 ++ .../resources/k8s/node_label_spec.go | 2 +- website/content/v1.8/reference/api.md | 17 + .../configuration/v1alpha1/config.md | 4 + .../content/v1.8/schemas/config.schema.json | 12 + .../editing-machine-configuration.md | 2 + 33 files changed, 1419 insertions(+), 277 deletions(-) create mode 100644 internal/app/machined/pkg/controllers/k8s/node_annotation_spec.go create mode 100644 internal/app/machined/pkg/controllers/k8s/node_annotation_spec_test.go create mode 100644 internal/integration/api/node-annotations.go create mode 100644 pkg/machinery/resources/k8s/node_annotation_spec.go diff --git a/api/resource/definitions/k8s/k8s.proto b/api/resource/definitions/k8s/k8s.proto index 9266520fa5..e72b450d33 100755 --- a/api/resource/definitions/k8s/k8s.proto +++ b/api/resource/definitions/k8s/k8s.proto @@ -170,6 +170,12 @@ message ManifestStatusSpec { repeated string manifests_applied = 1; } +// NodeAnnotationSpecSpec represents an annoation that's attached to a Talos node. +message NodeAnnotationSpecSpec { + string key = 1; + string value = 2; +} + // NodeIPConfigSpec holds the Node IP specification. message NodeIPConfigSpec { repeated string valid_subnets = 1; diff --git a/hack/release.toml b/hack/release.toml index 9c968ec6e3..1744181530 100644 --- a/hack/release.toml +++ b/hack/release.toml @@ -108,6 +108,25 @@ Talos Linux on config generation now adds a label `node.kubernetes.io/exclude-fr title = "Secure Boot" description = """\ Talos Linux now can optionally include well-known UEFI (Microsoft) SecureBoot keys into the auto-enrollment UEFI database. +""" + + [notes.annotations] + title = "Node Annotations" + description = """\ +Talos Linux now supports configuring Kubernetes node annotations via machine configuration (`.machine.nodeAnnotations`) in a way similar to node labels. +""" + + [notes.kubelet] + title = "Extensions in Kubernetes Nodes" + description = """\ +Talos Linux now publishes list of installed extensions as Kubernetes node labels/annotations. + +The key format is `extensions.talos.dev/` and the value is the extension version. +If the extension name is not valid as a label key, it will be skipped. +If the extension version is a valid label value, it will be put to the label; otherwise it will be put to the annotation. + +For Talos machines booted of the Image Factory artifacts, this means that the schematic ID will be published as the annotation +`extensions.talos.dev/schematic` (as it is longer than 63 characters). """ [make_deps] diff --git a/internal/app/machined/pkg/controllers/k8s/node_annotation_spec.go b/internal/app/machined/pkg/controllers/k8s/node_annotation_spec.go new file mode 100644 index 0000000000..d16ab2fbdb --- /dev/null +++ b/internal/app/machined/pkg/controllers/k8s/node_annotation_spec.go @@ -0,0 +1,108 @@ +// This Source Code Form is subject to the terms of the Mozilla Public +// License, v. 2.0. If a copy of the MPL was not distributed with this +// file, You can obtain one at http://mozilla.org/MPL/2.0/. + +package k8s + +import ( + "context" + "fmt" + + "github.com/cosi-project/runtime/pkg/controller" + "github.com/cosi-project/runtime/pkg/safe" + "github.com/cosi-project/runtime/pkg/state" + "github.com/siderolabs/gen/optional" + "go.uber.org/zap" + + "github.com/siderolabs/talos/pkg/machinery/labels" + "github.com/siderolabs/talos/pkg/machinery/resources/config" + "github.com/siderolabs/talos/pkg/machinery/resources/k8s" + "github.com/siderolabs/talos/pkg/machinery/resources/runtime" +) + +// NodeAnnotationSpecController manages k8s.NodeAnnotationsConfig based on configuration. +type NodeAnnotationSpecController struct{} + +// Name implements controller.Controller interface. +func (ctrl *NodeAnnotationSpecController) Name() string { + return "k8s.NodeAnnotationSpecController" +} + +// Inputs implements controller.Controller interface. +func (ctrl *NodeAnnotationSpecController) Inputs() []controller.Input { + return []controller.Input{ + { + Namespace: config.NamespaceName, + Type: config.MachineConfigType, + ID: optional.Some(config.V1Alpha1ID), + Kind: controller.InputWeak, + }, + { + Namespace: runtime.NamespaceName, + Type: runtime.ExtensionStatusType, + Kind: controller.InputWeak, + }, + } +} + +// Outputs implements controller.Controller interface. +func (ctrl *NodeAnnotationSpecController) Outputs() []controller.Output { + return []controller.Output{ + { + Type: k8s.NodeAnnotationSpecType, + Kind: controller.OutputExclusive, + }, + } +} + +// Run implements controller.Controller interface. +// +//nolint:gocyclo +func (ctrl *NodeAnnotationSpecController) Run(ctx context.Context, r controller.Runtime, logger *zap.Logger) error { + for { + select { + case <-ctx.Done(): + return nil + case <-r.EventCh(): + } + + cfg, err := safe.ReaderGetByID[*config.MachineConfig](ctx, r, config.V1Alpha1ID) + if err != nil && !state.IsNotFoundError(err) { + return fmt.Errorf("error getting config: %w", err) + } + + r.StartTrackingOutputs() + + nodeAnnotations := map[string]string{} + + if cfg != nil && cfg.Config().Machine() != nil { + for k, v := range cfg.Config().Machine().NodeAnnotations() { + nodeAnnotations[k] = v + } + } + + if err = extensionsToNodeKV( + ctx, r, nodeAnnotations, + func(annotationValue string) bool { + return labels.ValidateLabelValue(annotationValue) != nil + }, + ); err != nil { + return fmt.Errorf("error converting extensions to node annotations: %w", err) + } + + for key, value := range nodeAnnotations { + if err = safe.WriterModify(ctx, r, k8s.NewNodeAnnotationSpec(key), func(k *k8s.NodeAnnotationSpec) error { + k.TypedSpec().Key = key + k.TypedSpec().Value = value + + return nil + }); err != nil { + return fmt.Errorf("error updating node label spec: %w", err) + } + } + + if err = safe.CleanupOutputs[*k8s.NodeAnnotationSpec](ctx, r); err != nil { + return err + } + } +} diff --git a/internal/app/machined/pkg/controllers/k8s/node_annotation_spec_test.go b/internal/app/machined/pkg/controllers/k8s/node_annotation_spec_test.go new file mode 100644 index 0000000000..395801c137 --- /dev/null +++ b/internal/app/machined/pkg/controllers/k8s/node_annotation_spec_test.go @@ -0,0 +1,122 @@ +// This Source Code Form is subject to the terms of the Mozilla Public +// License, v. 2.0. If a copy of the MPL was not distributed with this +// file, You can obtain one at http://mozilla.org/MPL/2.0/. + +package k8s_test + +import ( + "testing" + "time" + + "github.com/cosi-project/runtime/pkg/resource/rtestutils" + "github.com/cosi-project/runtime/pkg/safe" + "github.com/cosi-project/runtime/pkg/state" + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/suite" + + "github.com/siderolabs/talos/internal/app/machined/pkg/controllers/ctest" + k8sctrl "github.com/siderolabs/talos/internal/app/machined/pkg/controllers/k8s" + "github.com/siderolabs/talos/pkg/machinery/config/container" + "github.com/siderolabs/talos/pkg/machinery/config/types/v1alpha1" + "github.com/siderolabs/talos/pkg/machinery/extensions" + "github.com/siderolabs/talos/pkg/machinery/resources/config" + "github.com/siderolabs/talos/pkg/machinery/resources/k8s" + "github.com/siderolabs/talos/pkg/machinery/resources/runtime" +) + +type NodeAnnotationsSuite struct { + ctest.DefaultSuite +} + +func TestNodeAnnotationsSuite(t *testing.T) { + t.Parallel() + + suite.Run(t, &NodeAnnotationsSuite{ + DefaultSuite: ctest.DefaultSuite{ + Timeout: 5 * time.Second, + AfterSetup: func(s *ctest.DefaultSuite) { + s.Require().NoError(s.Runtime().RegisterController(&k8sctrl.NodeAnnotationSpecController{})) + }, + }, + }) +} + +func (suite *NodeAnnotationsSuite) updateMachineConfig(annotations map[string]string) { + cfg, err := safe.StateGetByID[*config.MachineConfig](suite.Ctx(), suite.State(), config.V1Alpha1ID) + if err != nil && !state.IsNotFoundError(err) { + suite.Require().NoError(err) + } + + if cfg == nil { + cfg = config.NewMachineConfig(container.NewV1Alpha1(&v1alpha1.Config{ + MachineConfig: &v1alpha1.MachineConfig{ + MachineType: "controlplane", + MachineNodeAnnotations: annotations, + }, + })) + + suite.Require().NoError(suite.State().Create(suite.Ctx(), cfg)) + } else { + cfg.Container().RawV1Alpha1().MachineConfig.MachineNodeAnnotations = annotations + suite.Require().NoError(suite.State().Update(suite.Ctx(), cfg)) + } +} + +func (suite *NodeAnnotationsSuite) TestChangeLabel() { + // given + expectedAnnotation := "some/annotation" + oldValue := "oldValue" + expectedValue := "newValue" + + // when + suite.updateMachineConfig(map[string]string{ + expectedAnnotation: oldValue, + }) + + rtestutils.AssertResources(suite.Ctx(), suite.T(), suite.State(), []string{expectedAnnotation}, + func(labelSpec *k8s.NodeAnnotationSpec, asrt *assert.Assertions) { + asrt.Equal(oldValue, labelSpec.TypedSpec().Value) + }) + + suite.updateMachineConfig(map[string]string{ + expectedAnnotation: expectedValue, + }) + + // then + rtestutils.AssertResources(suite.Ctx(), suite.T(), suite.State(), []string{expectedAnnotation}, + func(labelSpec *k8s.NodeAnnotationSpec, asrt *assert.Assertions) { + asrt.Equal(expectedValue, labelSpec.TypedSpec().Value) + }) +} + +func (suite *NodeAnnotationsSuite) TestExtensionAnnotations() { + ext1 := runtime.NewExtensionStatus(runtime.NamespaceName, "0") + ext1.TypedSpec().Metadata = extensions.Metadata{ + Name: "zfs", + Version: "2.2.4", + } + + ext2 := runtime.NewExtensionStatus(runtime.NamespaceName, "1") + ext2.TypedSpec().Metadata = extensions.Metadata{ + Name: "drbd", + Version: "9.2.8-v1.7.5", + } + + ext3 := runtime.NewExtensionStatus(runtime.NamespaceName, "2") + ext3.TypedSpec().Metadata = extensions.Metadata{ + Name: "schematic", + Version: "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + } + + suite.Require().NoError(suite.State().Create(suite.Ctx(), ext1)) + suite.Require().NoError(suite.State().Create(suite.Ctx(), ext2)) + suite.Require().NoError(suite.State().Create(suite.Ctx(), ext3)) + + rtestutils.AssertNoResource[*k8s.NodeAnnotationSpec](suite.Ctx(), suite.T(), suite.State(), "extensions.talos.dev/zfs") + rtestutils.AssertNoResource[*k8s.NodeAnnotationSpec](suite.Ctx(), suite.T(), suite.State(), "extensions.talos.dev/drbd") + + rtestutils.AssertResources(suite.Ctx(), suite.T(), suite.State(), []string{"extensions.talos.dev/schematic"}, + func(labelSpec *k8s.NodeAnnotationSpec, asrt *assert.Assertions) { + asrt.Equal("e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", labelSpec.TypedSpec().Value) + }) +} diff --git a/internal/app/machined/pkg/controllers/k8s/node_apply.go b/internal/app/machined/pkg/controllers/k8s/node_apply.go index d6ee03feca..3112610578 100644 --- a/internal/app/machined/pkg/controllers/k8s/node_apply.go +++ b/internal/app/machined/pkg/controllers/k8s/node_apply.go @@ -43,6 +43,11 @@ func (ctrl *NodeApplyController) Name() string { // Inputs implements controller.Controller interface. func (ctrl *NodeApplyController) Inputs() []controller.Input { return []controller.Input{ + { + Namespace: k8s.NamespaceName, + Type: k8s.NodeAnnotationSpecType, + Kind: controller.InputWeak, + }, { Namespace: k8s.NamespaceName, Type: k8s.NodeLabelSpecType, @@ -107,6 +112,7 @@ func (ctrl *NodeApplyController) Run(ctx context.Context, r controller.Runtime, } } +//nolint:dupl func (ctrl *NodeApplyController) getNodeLabelSpecs(ctx context.Context, r controller.Runtime) (map[string]string, error) { items, err := safe.ReaderListAll[*k8s.NodeLabelSpec](ctx, r) if err != nil { @@ -122,6 +128,22 @@ func (ctrl *NodeApplyController) getNodeLabelSpecs(ctx context.Context, r contro return result, nil } +//nolint:dupl +func (ctrl *NodeApplyController) getNodeAnnotationSpecs(ctx context.Context, r controller.Runtime) (map[string]string, error) { + items, err := safe.ReaderListAll[*k8s.NodeAnnotationSpec](ctx, r) + if err != nil { + return nil, fmt.Errorf("error listing node annotation spec resources: %w", err) + } + + result := make(map[string]string, items.Len()) + + for iter := items.Iterator(); iter.Next(); { + result[iter.Value().TypedSpec().Key] = iter.Value().TypedSpec().Value + } + + return result, nil +} + func (ctrl *NodeApplyController) getNodeTaintSpecs(ctx context.Context, r controller.Runtime) ([]k8s.NodeTaintSpecSpec, error) { items, err := safe.ReaderListAll[*k8s.NodeTaintSpec](ctx, r) if err != nil { @@ -203,6 +225,11 @@ func (ctrl *NodeApplyController) reconcileWithK8s( return err } + nodeAnnotationSpecs, err := ctrl.getNodeAnnotationSpecs(ctx, r) + if err != nil { + return err + } + nodeTaintSpecs, err := ctrl.getNodeTaintSpecs(ctx, r) if err != nil { return err @@ -213,7 +240,7 @@ func (ctrl *NodeApplyController) reconcileWithK8s( return err } - return ctrl.sync(ctx, logger, k8sClient, nodename, nodeLabelSpecs, nodeTaintSpecs, nodeShouldCordon) + return ctrl.sync(ctx, logger, k8sClient, nodename, nodeLabelSpecs, nodeAnnotationSpecs, nodeTaintSpecs, nodeShouldCordon) } func (ctrl *NodeApplyController) sync( @@ -221,13 +248,13 @@ func (ctrl *NodeApplyController) sync( logger *zap.Logger, k8sClient *kubernetes.Client, nodeName string, - nodeLabelSpecs map[string]string, + nodeLabelSpecs, nodeAnnotationSpecs map[string]string, nodeTaintSpecs []k8s.NodeTaintSpecSpec, nodeShouldCordon bool, ) error { // run several attempts retrying conflict errors return retry.Constant(10*time.Second, retry.WithUnits(100*time.Millisecond)).RetryWithContext(ctx, func(ctx context.Context) error { - err := ctrl.syncOnce(ctx, logger, k8sClient, nodeName, nodeLabelSpecs, nodeTaintSpecs, nodeShouldCordon) + err := ctrl.syncOnce(ctx, logger, k8sClient, nodeName, nodeLabelSpecs, nodeAnnotationSpecs, nodeTaintSpecs, nodeShouldCordon) if err != nil && (apierrors.IsConflict(err) || apierrors.IsForbidden(err)) { return retry.ExpectedError(err) @@ -279,7 +306,7 @@ func (ctrl *NodeApplyController) syncOnce( logger *zap.Logger, k8sClient *kubernetes.Client, nodeName string, - nodeLabelSpecs map[string]string, + nodeLabelSpecs, nodeAnnotationSpecs map[string]string, nodeTaintSpecs []k8s.NodeTaintSpecSpec, nodeShouldCordon bool, ) error { @@ -297,12 +324,18 @@ func (ctrl *NodeApplyController) syncOnce( return fmt.Errorf("error unmarshaling owned labels: %w", err) } + ownedAnnotationsMap, err := umarshalOwnedAnnotation(node, constants.AnnotationOwnedAnnotations) + if err != nil { + return fmt.Errorf("error unmarshaling owned annotations: %w", err) + } + ownedTaintsMap, err := umarshalOwnedAnnotation(node, constants.AnnotationOwnedTaints) if err != nil { return fmt.Errorf("error unmarshaling owned taints: %w", err) } ctrl.ApplyLabels(logger, node, ownedLabelsMap, nodeLabelSpecs) + ctrl.ApplyAnnotations(logger, node, ownedAnnotationsMap, nodeAnnotationSpecs) ctrl.ApplyTaints(logger, node, ownedTaintsMap, nodeTaintSpecs) ctrl.ApplyCordoned(logger, node, nodeShouldCordon) @@ -310,6 +343,10 @@ func (ctrl *NodeApplyController) syncOnce( return fmt.Errorf("error marshaling owned labels: %w", err) } + if err = marshalOwnedAnnotation(node, constants.AnnotationOwnedAnnotations, ownedAnnotationsMap); err != nil { + return fmt.Errorf("error marshaling owned annotations: %w", err) + } + if err = marshalOwnedAnnotation(node, constants.AnnotationOwnedTaints, ownedTaintsMap); err != nil { return fmt.Errorf("error marshaling owned taints: %w", err) } @@ -319,47 +356,58 @@ func (ctrl *NodeApplyController) syncOnce( return err } -// ApplyLabels performs the inner loop of the node label reconciliation. -// -// This method is exported for testing purposes. -func (ctrl *NodeApplyController) ApplyLabels(logger *zap.Logger, node *v1.Node, ownedLabels map[string]struct{}, nodeLabelSpecs map[string]string) { +func (ctrl *NodeApplyController) applyNodeKV(logger *zap.Logger, nodeKV map[string]string, owned map[string]struct{}, spec map[string]string) { // set labels from the spec - for key, value := range nodeLabelSpecs { - currentValue, exists := node.Labels[key] + for key, value := range spec { + currentValue, exists := nodeKV[key] // label is not set on the node yet, so take it over if !exists { - node.Labels[key] = value - ownedLabels[key] = struct{}{} + nodeKV[key] = value + owned[key] = struct{}{} continue } // no change to the label, skip it if currentValue == value { - ownedLabels[key] = struct{}{} + owned[key] = struct{}{} continue } - if _, owned := ownedLabels[key]; !owned { + if _, owned := owned[key]; !owned { logger.Debug("skipping label update, label is not owned", zap.String("key", key), zap.String("value", value)) continue } - node.Labels[key] = value + nodeKV[key] = value } // remove labels which are owned but are not in the spec - for key := range ownedLabels { - if _, exists := nodeLabelSpecs[key]; !exists { - delete(node.Labels, key) - delete(ownedLabels, key) + for key := range owned { + if _, exists := spec[key]; !exists { + delete(nodeKV, key) + delete(owned, key) } } } +// ApplyLabels performs the inner loop of the node label reconciliation. +// +// This method is exported for testing purposes. +func (ctrl *NodeApplyController) ApplyLabels(logger *zap.Logger, node *v1.Node, ownedLabels map[string]struct{}, nodeLabelSpecs map[string]string) { + ctrl.applyNodeKV(logger, node.Labels, ownedLabels, nodeLabelSpecs) +} + +// ApplyAnnotations performs the inner loop of the node annotation reconciliation. +// +// This method is exported for testing purposes. +func (ctrl *NodeApplyController) ApplyAnnotations(logger *zap.Logger, node *v1.Node, ownedAnnotations map[string]struct{}, nodeAnnotationSpecs map[string]string) { + ctrl.applyNodeKV(logger, node.Annotations, ownedAnnotations, nodeAnnotationSpecs) +} + // ApplyTaints performs the inner loop of the node taints reconciliation. // // This method is exported for testing purposes. diff --git a/internal/app/machined/pkg/controllers/k8s/node_apply_test.go b/internal/app/machined/pkg/controllers/k8s/node_apply_test.go index bd749fae05..b5973ee6e4 100644 --- a/internal/app/machined/pkg/controllers/k8s/node_apply_test.go +++ b/internal/app/machined/pkg/controllers/k8s/node_apply_test.go @@ -19,7 +19,7 @@ import ( "github.com/siderolabs/talos/pkg/machinery/resources/k8s" ) -func TestApplyLabels(t *testing.T) { +func TestApplyLabels(t *testing.T) { //nolint:dupl t.Parallel() ctrl := &k8sctrl.NodeApplyController{} @@ -138,6 +138,125 @@ func TestApplyLabels(t *testing.T) { } } +func TestApplyAnnotations(t *testing.T) { //nolint:dupl + t.Parallel() + + ctrl := &k8sctrl.NodeApplyController{} + logger := zaptest.NewLogger(t) + + for _, tt := range []struct { + name string + inputAnnotations map[string]string + ownedAnnotations []string + annotationSpec map[string]string + + expectedAnnotations map[string]string + expectedOwnedAnnotations []string + }{ + { + name: "empty", + inputAnnotations: map[string]string{}, + ownedAnnotations: []string{}, + annotationSpec: map[string]string{}, + + expectedAnnotations: map[string]string{}, + expectedOwnedAnnotations: []string{}, + }, + { + name: "initial annotations", + inputAnnotations: map[string]string{ + "hostname": "foo", + }, + ownedAnnotations: []string{}, + annotationSpec: map[string]string{ + "talos/foo": "value1", + "talos/bar": "value2", + }, + + expectedAnnotations: map[string]string{ + "hostname": "foo", + "talos/foo": "value1", + "talos/bar": "value2", + }, + expectedOwnedAnnotations: []string{ + "talos/bar", + "talos/foo", + }, + }, + { + name: "update owned annotations", + inputAnnotations: map[string]string{ + "hostname": "foo", + "label1": "value1", + "label2": "value2", + }, + ownedAnnotations: []string{ + "label1", + "label2", + }, + annotationSpec: map[string]string{ + "label1": "value3", + }, + + expectedAnnotations: map[string]string{ + "hostname": "foo", + "label1": "value3", + }, + expectedOwnedAnnotations: []string{ + "label1", + }, + }, + { + name: "ignore not owned annotations", + inputAnnotations: map[string]string{ + "hostname": "foo", + "ann1": "value1", + "ann2": "value2", + "ann3": "value3", + }, + ownedAnnotations: []string{}, + annotationSpec: map[string]string{ + "ann1": "value3", + "ann2": "value2", + }, + + expectedAnnotations: map[string]string{ + "hostname": "foo", + "ann1": "value1", + "ann2": "value2", + "ann3": "value3", + }, + expectedOwnedAnnotations: []string{ + "ann2", + }, + }, + } { + t.Run(tt.name, func(t *testing.T) { + t.Parallel() + + node := &v1.Node{} + node.Annotations = tt.inputAnnotations + + ownedAnnotations := xslices.ToSet(tt.ownedAnnotations) + if ownedAnnotations == nil { + ownedAnnotations = map[string]struct{}{} + } + + ctrl.ApplyAnnotations(logger, node, ownedAnnotations, tt.annotationSpec) + + newOwnedAnnotations := maps.Keys(ownedAnnotations) + if newOwnedAnnotations == nil { + newOwnedAnnotations = []string{} + } + + slices.Sort(newOwnedAnnotations) + + assert.Equal(t, tt.expectedAnnotations, node.Annotations) + assert.Equal(t, tt.expectedOwnedAnnotations, newOwnedAnnotations) + }) + } +} + func TestApplyTaints(t *testing.T) { t.Parallel() diff --git a/internal/app/machined/pkg/controllers/k8s/node_label_spec.go b/internal/app/machined/pkg/controllers/k8s/node_label_spec.go index 9392e82ebf..1874ff7278 100644 --- a/internal/app/machined/pkg/controllers/k8s/node_label_spec.go +++ b/internal/app/machined/pkg/controllers/k8s/node_label_spec.go @@ -15,8 +15,10 @@ import ( "go.uber.org/zap" "github.com/siderolabs/talos/pkg/machinery/constants" + "github.com/siderolabs/talos/pkg/machinery/labels" "github.com/siderolabs/talos/pkg/machinery/resources/config" "github.com/siderolabs/talos/pkg/machinery/resources/k8s" + "github.com/siderolabs/talos/pkg/machinery/resources/runtime" ) // NodeLabelSpecController manages k8s.NodeLabelsConfig based on configuration. @@ -36,6 +38,11 @@ func (ctrl *NodeLabelSpecController) Inputs() []controller.Input { ID: optional.Some(config.V1Alpha1ID), Kind: controller.InputWeak, }, + { + Namespace: runtime.NamespaceName, + Type: runtime.ExtensionStatusType, + Kind: controller.InputWeak, + }, } } @@ -67,20 +74,27 @@ func (ctrl *NodeLabelSpecController) Run(ctx context.Context, r controller.Runti r.StartTrackingOutputs() - var nodeLabels map[string]string + nodeLabels := map[string]string{} if cfg != nil && cfg.Config().Machine() != nil { - nodeLabels = cfg.Config().Machine().NodeLabels() + for k, v := range cfg.Config().Machine().NodeLabels() { + nodeLabels[k] = v + } if cfg.Config().Machine().Type().IsControlPlane() { - if nodeLabels == nil { - nodeLabels = map[string]string{} - } - nodeLabels[constants.LabelNodeRoleControlPlane] = "" } } + if err = extensionsToNodeKV( + ctx, r, nodeLabels, + func(labelValue string) bool { + return labels.ValidateLabelValue(labelValue) == nil + }, + ); err != nil { + return fmt.Errorf("error converting extensions to node labels: %w", err) + } + for key, value := range nodeLabels { if err = safe.WriterModify(ctx, r, k8s.NewNodeLabelSpec(key), func(k *k8s.NodeLabelSpec) error { k.TypedSpec().Key = key @@ -97,3 +111,27 @@ func (ctrl *NodeLabelSpecController) Run(ctx context.Context, r controller.Runti } } } + +func extensionsToNodeKV(ctx context.Context, r controller.Reader, spec map[string]string, valueFilter func(string) bool) error { + extensionStatuses, err := safe.ReaderListAll[*runtime.ExtensionStatus](ctx, r) + if err != nil { + return fmt.Errorf("error listing extension statuses: %w", err) + } + + for iter := extensionStatuses.Iterator(); iter.Next(); { + extensionStatus := iter.Value() + + if extensionStatus.TypedSpec().Metadata.Name == "" { + continue + } + + name := constants.K8sExtensionPrefix + extensionStatus.TypedSpec().Metadata.Name + value := extensionStatus.TypedSpec().Metadata.Version + + if labels.ValidateQualifiedName(name) == nil && valueFilter(value) { + spec[name] = value + } + } + + return nil +} diff --git a/internal/app/machined/pkg/controllers/k8s/node_label_spec_test.go b/internal/app/machined/pkg/controllers/k8s/node_label_spec_test.go index feaa29a9ac..e1d0258095 100644 --- a/internal/app/machined/pkg/controllers/k8s/node_label_spec_test.go +++ b/internal/app/machined/pkg/controllers/k8s/node_label_spec_test.go @@ -20,8 +20,10 @@ import ( "github.com/siderolabs/talos/pkg/machinery/config/machine" "github.com/siderolabs/talos/pkg/machinery/config/types/v1alpha1" "github.com/siderolabs/talos/pkg/machinery/constants" + "github.com/siderolabs/talos/pkg/machinery/extensions" "github.com/siderolabs/talos/pkg/machinery/resources/config" "github.com/siderolabs/talos/pkg/machinery/resources/k8s" + "github.com/siderolabs/talos/pkg/machinery/resources/runtime" ) type NodeLabelsSuite struct { @@ -133,3 +135,38 @@ func (suite *NodeLabelsSuite) TestDeleteLabel() { rtestutils.AssertNoResource[*k8s.NodeLabelSpec](suite.Ctx(), suite.T(), suite.State(), expectedLabel) rtestutils.AssertNoResource[*k8s.NodeLabelSpec](suite.Ctx(), suite.T(), suite.State(), constants.LabelNodeRoleControlPlane) } + +func (suite *NodeLabelsSuite) TestExtensionLabels() { + ext1 := runtime.NewExtensionStatus(runtime.NamespaceName, "0") + ext1.TypedSpec().Metadata = extensions.Metadata{ + Name: "zfs", + Version: "2.2.4", + } + + ext2 := runtime.NewExtensionStatus(runtime.NamespaceName, "1") + ext2.TypedSpec().Metadata = extensions.Metadata{ + Name: "drbd", + Version: "9.2.8-v1.7.5", + } + + ext3 := runtime.NewExtensionStatus(runtime.NamespaceName, "2") + ext3.TypedSpec().Metadata = extensions.Metadata{ + Name: "schematic", + Version: "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + } + + suite.Require().NoError(suite.State().Create(suite.Ctx(), ext1)) + suite.Require().NoError(suite.State().Create(suite.Ctx(), ext2)) + suite.Require().NoError(suite.State().Create(suite.Ctx(), ext3)) + + rtestutils.AssertResources(suite.Ctx(), suite.T(), suite.State(), []string{"extensions.talos.dev/zfs"}, + func(labelSpec *k8s.NodeLabelSpec, asrt *assert.Assertions) { + asrt.Equal("2.2.4", labelSpec.TypedSpec().Value) + }) + rtestutils.AssertResources(suite.Ctx(), suite.T(), suite.State(), []string{"extensions.talos.dev/drbd"}, + func(labelSpec *k8s.NodeLabelSpec, asrt *assert.Assertions) { + asrt.Equal("9.2.8-v1.7.5", labelSpec.TypedSpec().Value) + }) + + rtestutils.AssertNoResource[*k8s.NodeLabelSpec](suite.Ctx(), suite.T(), suite.State(), "extensions.talos.dev/schematic") +} diff --git a/internal/app/machined/pkg/runtime/v1alpha1/v1alpha1_runtime.go b/internal/app/machined/pkg/runtime/v1alpha1/v1alpha1_runtime.go index c3d5b83276..ca2567870f 100644 --- a/internal/app/machined/pkg/runtime/v1alpha1/v1alpha1_runtime.go +++ b/internal/app/machined/pkg/runtime/v1alpha1/v1alpha1_runtime.go @@ -130,6 +130,7 @@ func (r *Runtime) CanApplyImmediate(cfg config.Provider) error { // * .machine.registries (note that auth is not applied immediately, containerd limitation) // * .machine.pods // * .machine.seccompProfiles + // * .machine.nodeAnnotations // * .machine.nodeLabels // * .machine.nodeTaints // * .machine.features.kubernetesTalosAPIAccess @@ -154,6 +155,7 @@ func (r *Runtime) CanApplyImmediate(cfg config.Provider) error { newConfig.MachineConfig.MachineRegistries = currentConfig.MachineConfig.MachineRegistries newConfig.MachineConfig.MachinePods = currentConfig.MachineConfig.MachinePods newConfig.MachineConfig.MachineSeccompProfiles = currentConfig.MachineConfig.MachineSeccompProfiles + newConfig.MachineConfig.MachineNodeAnnotations = currentConfig.MachineConfig.MachineNodeAnnotations newConfig.MachineConfig.MachineNodeLabels = currentConfig.MachineConfig.MachineNodeLabels newConfig.MachineConfig.MachineNodeTaints = currentConfig.MachineConfig.MachineNodeTaints diff --git a/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_controller.go b/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_controller.go index 0f540e1951..2eefb73f80 100644 --- a/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_controller.go +++ b/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_controller.go @@ -171,6 +171,7 @@ func (ctrl *Controller) Run(ctx context.Context, drainer *runtime.Drainer) error &k8s.ManifestController{}, k8s.NewNodeIPConfigController(), &k8s.NodeIPController{}, + &k8s.NodeAnnotationSpecController{}, &k8s.NodeApplyController{}, &k8s.NodeCordonedSpecController{}, &k8s.NodeLabelSpecController{}, diff --git a/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_state.go b/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_state.go index 6debe2447e..4354d73c85 100644 --- a/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_state.go +++ b/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_state.go @@ -133,6 +133,7 @@ func NewState() (*State, error) { &k8s.Manifest{}, &k8s.ManifestStatus{}, &k8s.BootstrapManifestsConfig{}, + &k8s.NodeAnnotationSpec{}, &k8s.NodeCordonedSpec{}, &k8s.NodeIP{}, &k8s.NodeIPConfig{}, diff --git a/internal/integration/api/node-annotations.go b/internal/integration/api/node-annotations.go new file mode 100644 index 0000000000..784c422072 --- /dev/null +++ b/internal/integration/api/node-annotations.go @@ -0,0 +1,163 @@ +// This Source Code Form is subject to the terms of the Mozilla Public +// License, v. 2.0. If a copy of the MPL was not distributed with this +// file, You can obtain one at http://mozilla.org/MPL/2.0/. + +//go:build integration_api + +package api + +import ( + "context" + "time" + + v1 "k8s.io/api/core/v1" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/watch" + + "github.com/siderolabs/talos/internal/integration/base" + machineapi "github.com/siderolabs/talos/pkg/machinery/api/machine" + "github.com/siderolabs/talos/pkg/machinery/client" + "github.com/siderolabs/talos/pkg/machinery/config/machine" + "github.com/siderolabs/talos/pkg/machinery/config/types/v1alpha1" +) + +// NodeAnnotationsSuite verifies updating node annotations via machine config. +type NodeAnnotationsSuite struct { + base.K8sSuite + + ctx context.Context //nolint:containedctx + ctxCancel context.CancelFunc +} + +// SuiteName ... +func (suite *NodeAnnotationsSuite) SuiteName() string { + return "api.NodeAnnotationsSuite" +} + +// SetupTest ... +func (suite *NodeAnnotationsSuite) SetupTest() { + // make sure API calls have timeout + suite.ctx, suite.ctxCancel = context.WithTimeout(context.Background(), 5*time.Minute) +} + +// TearDownTest ... +func (suite *NodeAnnotationsSuite) TearDownTest() { + if suite.ctxCancel != nil { + suite.ctxCancel() + } +} + +// TestUpdateControlPlane verifies node annotation updates on control plane nodes. +func (suite *NodeAnnotationsSuite) TestUpdateControlPlane() { + node := suite.RandomDiscoveredNodeInternalIP(machine.TypeControlPlane) + + suite.testUpdate(node) +} + +// TestUpdateWorker verifies node annotation updates on worker nodes. +func (suite *NodeAnnotationsSuite) TestUpdateWorker() { + node := suite.RandomDiscoveredNodeInternalIP(machine.TypeWorker) + + suite.testUpdate(node) +} + +// testUpdate cycles through a set of node annotation updates reverting the change in the end. +func (suite *NodeAnnotationsSuite) testUpdate(node string) { + k8sNode, err := suite.GetK8sNodeByInternalIP(suite.ctx, node) + suite.Require().NoError(err) + + suite.T().Logf("updating annotations on node %q (%q)", node, k8sNode.Name) + + watcher, err := suite.Clientset.CoreV1().Nodes().Watch(suite.ctx, metav1.ListOptions{ + FieldSelector: metadataKeyName + k8sNode.Name, + Watch: true, + }) + suite.Require().NoError(err) + + defer watcher.Stop() + + // set two new annotation + suite.setNodeAnnotations(node, map[string]string{ + "talos.dev/ann1": "value1", + "talos.dev/ann2": "value2", + }) + + suite.waitUntil(watcher, map[string]string{ + "talos.dev/ann1": "value1", + "talos.dev/ann2": "value2", + }) + + // remove one annotation owned by Talos + suite.setNodeAnnotations(node, map[string]string{ + "talos.dev/ann1": "foo", + }) + + suite.waitUntil(watcher, map[string]string{ + "talos.dev/ann1": "foo", + "talos.dev/ann2": "", + }) + + // remove all Talos annoations + suite.setNodeAnnotations(node, nil) + + suite.waitUntil(watcher, map[string]string{ + "talos.dev/ann1": "", + "talos.dev/ann2": "", + }) +} + +func (suite *NodeAnnotationsSuite) waitUntil(watcher watch.Interface, expectedAnnotations map[string]string) { +outer: + for { + select { + case ev := <-watcher.ResultChan(): + k8sNode, ok := ev.Object.(*v1.Node) + suite.Require().Truef(ok, "watch event is not of type v1.Node but was %T", ev.Object) + + suite.T().Logf("annotations %#v", k8sNode.Annotations) + + for k, v := range expectedAnnotations { + if v == "" { + _, ok := k8sNode.Annotations[k] + if ok { + suite.T().Logf("annotation %q is still present", k) + + continue outer + } + } + + if k8sNode.Annotations[k] != v { + suite.T().Logf("annotation %q is %q but expected %q", k, k8sNode.Annotations[k], v) + + continue outer + } + } + + return + case <-suite.ctx.Done(): + suite.T().Fatal("timeout") + } + } +} + +func (suite *NodeAnnotationsSuite) setNodeAnnotations(nodeIP string, nodeAnnotations map[string]string) { //nolint:dupl + nodeCtx := client.WithNode(suite.ctx, nodeIP) + + nodeConfig, err := suite.ReadConfigFromNode(nodeCtx) + suite.Require().NoError(err) + + bytes := suite.PatchV1Alpha1Config(nodeConfig, func(nodeConfigRaw *v1alpha1.Config) { + nodeConfigRaw.MachineConfig.MachineNodeAnnotations = nodeAnnotations + }) + + _, err = suite.Client.ApplyConfiguration(nodeCtx, &machineapi.ApplyConfigurationRequest{ + Data: bytes, + Mode: machineapi.ApplyConfigurationRequest_NO_REBOOT, + }) + + suite.Require().NoError(err) +} + +func init() { + allSuites = append(allSuites, new(NodeAnnotationsSuite)) +} diff --git a/internal/integration/api/node-labels.go b/internal/integration/api/node-labels.go index dd55ce2540..a9f94e185f 100644 --- a/internal/integration/api/node-labels.go +++ b/internal/integration/api/node-labels.go @@ -208,7 +208,7 @@ outer: } } -func (suite *NodeLabelsSuite) setNodeLabels(nodeIP string, nodeLabels map[string]string) { +func (suite *NodeLabelsSuite) setNodeLabels(nodeIP string, nodeLabels map[string]string) { //nolint:dupl nodeCtx := client.WithNode(suite.ctx, nodeIP) nodeConfig, err := suite.ReadConfigFromNode(nodeCtx) diff --git a/pkg/machinery/api/resource/definitions/k8s/k8s.pb.go b/pkg/machinery/api/resource/definitions/k8s/k8s.pb.go index e3a3e51771..03424c50c6 100644 --- a/pkg/machinery/api/resource/definitions/k8s/k8s.pb.go +++ b/pkg/machinery/api/resource/definitions/k8s/k8s.pb.go @@ -1473,6 +1473,62 @@ func (x *ManifestStatusSpec) GetManifestsApplied() []string { return nil } +// NodeAnnotationSpecSpec represents an annoation that's attached to a Talos node. +type NodeAnnotationSpecSpec struct { + state protoimpl.MessageState + sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + + Key string `protobuf:"bytes,1,opt,name=key,proto3" json:"key,omitempty"` + Value string `protobuf:"bytes,2,opt,name=value,proto3" json:"value,omitempty"` +} + +func (x *NodeAnnotationSpecSpec) Reset() { + *x = NodeAnnotationSpecSpec{} + if protoimpl.UnsafeEnabled { + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[19] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) + } +} + +func (x *NodeAnnotationSpecSpec) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*NodeAnnotationSpecSpec) ProtoMessage() {} + +func (x *NodeAnnotationSpecSpec) ProtoReflect() protoreflect.Message { + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[19] + if protoimpl.UnsafeEnabled && x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use NodeAnnotationSpecSpec.ProtoReflect.Descriptor instead. +func (*NodeAnnotationSpecSpec) Descriptor() ([]byte, []int) { + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{19} +} + +func (x *NodeAnnotationSpecSpec) GetKey() string { + if x != nil { + return x.Key + } + return "" +} + +func (x *NodeAnnotationSpecSpec) GetValue() string { + if x != nil { + return x.Value + } + return "" +} + // NodeIPConfigSpec holds the Node IP specification. type NodeIPConfigSpec struct { state protoimpl.MessageState @@ -1486,7 +1542,7 @@ type NodeIPConfigSpec struct { func (x *NodeIPConfigSpec) Reset() { *x = NodeIPConfigSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[19] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[20] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1499,7 +1555,7 @@ func (x *NodeIPConfigSpec) String() string { func (*NodeIPConfigSpec) ProtoMessage() {} func (x *NodeIPConfigSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[19] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[20] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1512,7 +1568,7 @@ func (x *NodeIPConfigSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use NodeIPConfigSpec.ProtoReflect.Descriptor instead. func (*NodeIPConfigSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{19} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{20} } func (x *NodeIPConfigSpec) GetValidSubnets() []string { @@ -1541,7 +1597,7 @@ type NodeIPSpec struct { func (x *NodeIPSpec) Reset() { *x = NodeIPSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[20] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[21] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1554,7 +1610,7 @@ func (x *NodeIPSpec) String() string { func (*NodeIPSpec) ProtoMessage() {} func (x *NodeIPSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[20] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[21] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1567,7 +1623,7 @@ func (x *NodeIPSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use NodeIPSpec.ProtoReflect.Descriptor instead. func (*NodeIPSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{20} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{21} } func (x *NodeIPSpec) GetAddresses() []*common.NetIP { @@ -1590,7 +1646,7 @@ type NodeLabelSpecSpec struct { func (x *NodeLabelSpecSpec) Reset() { *x = NodeLabelSpecSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[21] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[22] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1603,7 +1659,7 @@ func (x *NodeLabelSpecSpec) String() string { func (*NodeLabelSpecSpec) ProtoMessage() {} func (x *NodeLabelSpecSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[21] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[22] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1616,7 +1672,7 @@ func (x *NodeLabelSpecSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use NodeLabelSpecSpec.ProtoReflect.Descriptor instead. func (*NodeLabelSpecSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{21} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{22} } func (x *NodeLabelSpecSpec) GetKey() string { @@ -1649,7 +1705,7 @@ type NodeStatusSpec struct { func (x *NodeStatusSpec) Reset() { *x = NodeStatusSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[22] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[23] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1662,7 +1718,7 @@ func (x *NodeStatusSpec) String() string { func (*NodeStatusSpec) ProtoMessage() {} func (x *NodeStatusSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[22] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[23] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1675,7 +1731,7 @@ func (x *NodeStatusSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use NodeStatusSpec.ProtoReflect.Descriptor instead. func (*NodeStatusSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{22} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{23} } func (x *NodeStatusSpec) GetNodename() string { @@ -1727,7 +1783,7 @@ type NodeTaintSpecSpec struct { func (x *NodeTaintSpecSpec) Reset() { *x = NodeTaintSpecSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[23] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[24] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1740,7 +1796,7 @@ func (x *NodeTaintSpecSpec) String() string { func (*NodeTaintSpecSpec) ProtoMessage() {} func (x *NodeTaintSpecSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[23] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[24] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1753,7 +1809,7 @@ func (x *NodeTaintSpecSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use NodeTaintSpecSpec.ProtoReflect.Descriptor instead. func (*NodeTaintSpecSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{23} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{24} } func (x *NodeTaintSpecSpec) GetKey() string { @@ -1791,7 +1847,7 @@ type NodenameSpec struct { func (x *NodenameSpec) Reset() { *x = NodenameSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[24] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[25] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1804,7 +1860,7 @@ func (x *NodenameSpec) String() string { func (*NodenameSpec) ProtoMessage() {} func (x *NodenameSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[24] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[25] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1817,7 +1873,7 @@ func (x *NodenameSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use NodenameSpec.ProtoReflect.Descriptor instead. func (*NodenameSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{24} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{25} } func (x *NodenameSpec) GetNodename() string { @@ -1854,7 +1910,7 @@ type Resources struct { func (x *Resources) Reset() { *x = Resources{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[25] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[26] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1867,7 +1923,7 @@ func (x *Resources) String() string { func (*Resources) ProtoMessage() {} func (x *Resources) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[25] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[26] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1880,7 +1936,7 @@ func (x *Resources) ProtoReflect() protoreflect.Message { // Deprecated: Use Resources.ProtoReflect.Descriptor instead. func (*Resources) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{25} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{26} } func (x *Resources) GetRequests() map[string]string { @@ -1915,7 +1971,7 @@ type SchedulerConfigSpec struct { func (x *SchedulerConfigSpec) Reset() { *x = SchedulerConfigSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[26] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[27] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1928,7 +1984,7 @@ func (x *SchedulerConfigSpec) String() string { func (*SchedulerConfigSpec) ProtoMessage() {} func (x *SchedulerConfigSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[26] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[27] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1941,7 +1997,7 @@ func (x *SchedulerConfigSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use SchedulerConfigSpec.ProtoReflect.Descriptor instead. func (*SchedulerConfigSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{26} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{27} } func (x *SchedulerConfigSpec) GetEnabled() bool { @@ -2006,7 +2062,7 @@ type SecretsStatusSpec struct { func (x *SecretsStatusSpec) Reset() { *x = SecretsStatusSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[27] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[28] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2019,7 +2075,7 @@ func (x *SecretsStatusSpec) String() string { func (*SecretsStatusSpec) ProtoMessage() {} func (x *SecretsStatusSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[27] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[28] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2032,7 +2088,7 @@ func (x *SecretsStatusSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use SecretsStatusSpec.ProtoReflect.Descriptor instead. func (*SecretsStatusSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{27} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{28} } func (x *SecretsStatusSpec) GetReady() bool { @@ -2061,7 +2117,7 @@ type SingleManifest struct { func (x *SingleManifest) Reset() { *x = SingleManifest{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[28] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[29] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2074,7 +2130,7 @@ func (x *SingleManifest) String() string { func (*SingleManifest) ProtoMessage() {} func (x *SingleManifest) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[28] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[29] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2087,7 +2143,7 @@ func (x *SingleManifest) ProtoReflect() protoreflect.Message { // Deprecated: Use SingleManifest.ProtoReflect.Descriptor instead. func (*SingleManifest) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{28} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{29} } func (x *SingleManifest) GetObject() *structpb.Struct { @@ -2109,7 +2165,7 @@ type StaticPodServerStatusSpec struct { func (x *StaticPodServerStatusSpec) Reset() { *x = StaticPodServerStatusSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[29] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[30] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2122,7 +2178,7 @@ func (x *StaticPodServerStatusSpec) String() string { func (*StaticPodServerStatusSpec) ProtoMessage() {} func (x *StaticPodServerStatusSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[29] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[30] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2135,7 +2191,7 @@ func (x *StaticPodServerStatusSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use StaticPodServerStatusSpec.ProtoReflect.Descriptor instead. func (*StaticPodServerStatusSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{29} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{30} } func (x *StaticPodServerStatusSpec) GetUrl() string { @@ -2157,7 +2213,7 @@ type StaticPodSpec struct { func (x *StaticPodSpec) Reset() { *x = StaticPodSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[30] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[31] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2170,7 +2226,7 @@ func (x *StaticPodSpec) String() string { func (*StaticPodSpec) ProtoMessage() {} func (x *StaticPodSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[30] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[31] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2183,7 +2239,7 @@ func (x *StaticPodSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use StaticPodSpec.ProtoReflect.Descriptor instead. func (*StaticPodSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{30} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{31} } func (x *StaticPodSpec) GetPod() *structpb.Struct { @@ -2205,7 +2261,7 @@ type StaticPodStatusSpec struct { func (x *StaticPodStatusSpec) Reset() { *x = StaticPodStatusSpec{} if protoimpl.UnsafeEnabled { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[31] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[32] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2218,7 +2274,7 @@ func (x *StaticPodStatusSpec) String() string { func (*StaticPodStatusSpec) ProtoMessage() {} func (x *StaticPodStatusSpec) ProtoReflect() protoreflect.Message { - mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[31] + mi := &file_resource_definitions_k8s_k8s_proto_msgTypes[32] if protoimpl.UnsafeEnabled && x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2231,7 +2287,7 @@ func (x *StaticPodStatusSpec) ProtoReflect() protoreflect.Message { // Deprecated: Use StaticPodStatusSpec.ProtoReflect.Descriptor instead. func (*StaticPodStatusSpec) Descriptor() ([]byte, []int) { - return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{31} + return file_resource_definitions_k8s_k8s_proto_rawDescGZIP(), []int{32} } func (x *StaticPodStatusSpec) GetPodStatus() *structpb.Struct { @@ -2573,145 +2629,149 @@ var file_resource_definitions_k8s_k8s_proto_rawDesc = []byte{ 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x12, 0x2b, 0x0a, 0x11, 0x6d, 0x61, 0x6e, 0x69, 0x66, 0x65, 0x73, 0x74, 0x73, 0x5f, 0x61, 0x70, 0x70, 0x6c, 0x69, 0x65, 0x64, 0x18, 0x01, 0x20, 0x03, 0x28, 0x09, 0x52, 0x10, 0x6d, 0x61, 0x6e, 0x69, 0x66, 0x65, 0x73, 0x74, 0x73, 0x41, 0x70, 0x70, 0x6c, - 0x69, 0x65, 0x64, 0x22, 0x60, 0x0a, 0x10, 0x4e, 0x6f, 0x64, 0x65, 0x49, 0x50, 0x43, 0x6f, 0x6e, - 0x66, 0x69, 0x67, 0x53, 0x70, 0x65, 0x63, 0x12, 0x23, 0x0a, 0x0d, 0x76, 0x61, 0x6c, 0x69, 0x64, - 0x5f, 0x73, 0x75, 0x62, 0x6e, 0x65, 0x74, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x09, 0x52, 0x0c, - 0x76, 0x61, 0x6c, 0x69, 0x64, 0x53, 0x75, 0x62, 0x6e, 0x65, 0x74, 0x73, 0x12, 0x27, 0x0a, 0x0f, - 0x65, 0x78, 0x63, 0x6c, 0x75, 0x64, 0x65, 0x5f, 0x73, 0x75, 0x62, 0x6e, 0x65, 0x74, 0x73, 0x18, - 0x02, 0x20, 0x03, 0x28, 0x09, 0x52, 0x0e, 0x65, 0x78, 0x63, 0x6c, 0x75, 0x64, 0x65, 0x53, 0x75, - 0x62, 0x6e, 0x65, 0x74, 0x73, 0x22, 0x39, 0x0a, 0x0a, 0x4e, 0x6f, 0x64, 0x65, 0x49, 0x50, 0x53, - 0x70, 0x65, 0x63, 0x12, 0x2b, 0x0a, 0x09, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x65, 0x73, - 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x63, 0x6f, 0x6d, 0x6d, 0x6f, 0x6e, 0x2e, - 0x4e, 0x65, 0x74, 0x49, 0x50, 0x52, 0x09, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x65, 0x73, - 0x22, 0x3b, 0x0a, 0x11, 0x4e, 0x6f, 0x64, 0x65, 0x4c, 0x61, 0x62, 0x65, 0x6c, 0x53, 0x70, 0x65, - 0x63, 0x53, 0x70, 0x65, 0x63, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, - 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, - 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x22, 0xa3, 0x03, - 0x0a, 0x0e, 0x4e, 0x6f, 0x64, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, - 0x12, 0x1a, 0x0a, 0x08, 0x6e, 0x6f, 0x64, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, - 0x28, 0x09, 0x52, 0x08, 0x6e, 0x6f, 0x64, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x1d, 0x0a, 0x0a, - 0x6e, 0x6f, 0x64, 0x65, 0x5f, 0x72, 0x65, 0x61, 0x64, 0x79, 0x18, 0x02, 0x20, 0x01, 0x28, 0x08, - 0x52, 0x09, 0x6e, 0x6f, 0x64, 0x65, 0x52, 0x65, 0x61, 0x64, 0x79, 0x12, 0x24, 0x0a, 0x0d, 0x75, - 0x6e, 0x73, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x61, 0x62, 0x6c, 0x65, 0x18, 0x03, 0x20, 0x01, - 0x28, 0x08, 0x52, 0x0d, 0x75, 0x6e, 0x73, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x61, 0x62, 0x6c, - 0x65, 0x12, 0x52, 0x0a, 0x06, 0x6c, 0x61, 0x62, 0x65, 0x6c, 0x73, 0x18, 0x04, 0x20, 0x03, 0x28, - 0x0b, 0x32, 0x3a, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, - 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, - 0x38, 0x73, 0x2e, 0x4e, 0x6f, 0x64, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, - 0x63, 0x2e, 0x4c, 0x61, 0x62, 0x65, 0x6c, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x06, 0x6c, - 0x61, 0x62, 0x65, 0x6c, 0x73, 0x12, 0x61, 0x0a, 0x0b, 0x61, 0x6e, 0x6e, 0x6f, 0x74, 0x61, 0x74, - 0x69, 0x6f, 0x6e, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x3f, 0x2e, 0x74, 0x61, 0x6c, - 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, - 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x4e, 0x6f, 0x64, 0x65, - 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x2e, 0x41, 0x6e, 0x6e, 0x6f, 0x74, - 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x0b, 0x61, 0x6e, 0x6e, - 0x6f, 0x74, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x1a, 0x39, 0x0a, 0x0b, 0x4c, 0x61, 0x62, 0x65, - 0x6c, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, - 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, - 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, - 0x02, 0x38, 0x01, 0x1a, 0x3e, 0x0a, 0x10, 0x41, 0x6e, 0x6e, 0x6f, 0x74, 0x61, 0x74, 0x69, 0x6f, - 0x6e, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, + 0x69, 0x65, 0x64, 0x22, 0x40, 0x0a, 0x16, 0x4e, 0x6f, 0x64, 0x65, 0x41, 0x6e, 0x6e, 0x6f, 0x74, + 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x53, 0x70, 0x65, 0x63, 0x53, 0x70, 0x65, 0x63, 0x12, 0x10, 0x0a, + 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, + 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, + 0x76, 0x61, 0x6c, 0x75, 0x65, 0x22, 0x60, 0x0a, 0x10, 0x4e, 0x6f, 0x64, 0x65, 0x49, 0x50, 0x43, + 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x53, 0x70, 0x65, 0x63, 0x12, 0x23, 0x0a, 0x0d, 0x76, 0x61, 0x6c, + 0x69, 0x64, 0x5f, 0x73, 0x75, 0x62, 0x6e, 0x65, 0x74, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x09, + 0x52, 0x0c, 0x76, 0x61, 0x6c, 0x69, 0x64, 0x53, 0x75, 0x62, 0x6e, 0x65, 0x74, 0x73, 0x12, 0x27, + 0x0a, 0x0f, 0x65, 0x78, 0x63, 0x6c, 0x75, 0x64, 0x65, 0x5f, 0x73, 0x75, 0x62, 0x6e, 0x65, 0x74, + 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x09, 0x52, 0x0e, 0x65, 0x78, 0x63, 0x6c, 0x75, 0x64, 0x65, + 0x53, 0x75, 0x62, 0x6e, 0x65, 0x74, 0x73, 0x22, 0x39, 0x0a, 0x0a, 0x4e, 0x6f, 0x64, 0x65, 0x49, + 0x50, 0x53, 0x70, 0x65, 0x63, 0x12, 0x2b, 0x0a, 0x09, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, + 0x65, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0d, 0x2e, 0x63, 0x6f, 0x6d, 0x6d, 0x6f, + 0x6e, 0x2e, 0x4e, 0x65, 0x74, 0x49, 0x50, 0x52, 0x09, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, + 0x65, 0x73, 0x22, 0x3b, 0x0a, 0x11, 0x4e, 0x6f, 0x64, 0x65, 0x4c, 0x61, 0x62, 0x65, 0x6c, 0x53, + 0x70, 0x65, 0x63, 0x53, 0x70, 0x65, 0x63, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, - 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, - 0x02, 0x38, 0x01, 0x22, 0x53, 0x0a, 0x11, 0x4e, 0x6f, 0x64, 0x65, 0x54, 0x61, 0x69, 0x6e, 0x74, - 0x53, 0x70, 0x65, 0x63, 0x53, 0x70, 0x65, 0x63, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, - 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x16, 0x0a, 0x06, 0x65, 0x66, - 0x66, 0x65, 0x63, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x65, 0x66, 0x66, 0x65, - 0x63, 0x74, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x22, 0x8b, 0x01, 0x0a, 0x0c, 0x4e, 0x6f, 0x64, - 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x53, 0x70, 0x65, 0x63, 0x12, 0x1a, 0x0a, 0x08, 0x6e, 0x6f, 0x64, - 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x6e, 0x6f, 0x64, - 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x29, 0x0a, 0x10, 0x68, 0x6f, 0x73, 0x74, 0x6e, 0x61, 0x6d, - 0x65, 0x5f, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, - 0x0f, 0x68, 0x6f, 0x73, 0x74, 0x6e, 0x61, 0x6d, 0x65, 0x56, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, - 0x12, 0x34, 0x0a, 0x16, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x6e, 0x6f, 0x64, 0x65, 0x5f, 0x72, 0x65, - 0x67, 0x69, 0x73, 0x74, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, - 0x52, 0x14, 0x73, 0x6b, 0x69, 0x70, 0x4e, 0x6f, 0x64, 0x65, 0x52, 0x65, 0x67, 0x69, 0x73, 0x74, - 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0xa7, 0x02, 0x0a, 0x09, 0x52, 0x65, 0x73, 0x6f, 0x75, - 0x72, 0x63, 0x65, 0x73, 0x12, 0x53, 0x0a, 0x08, 0x72, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x73, - 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x37, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, - 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, - 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, - 0x73, 0x2e, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, - 0x08, 0x72, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x73, 0x12, 0x4d, 0x0a, 0x06, 0x6c, 0x69, 0x6d, - 0x69, 0x74, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x35, 0x2e, 0x74, 0x61, 0x6c, 0x6f, - 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, - 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x52, 0x65, 0x73, 0x6f, 0x75, - 0x72, 0x63, 0x65, 0x73, 0x2e, 0x4c, 0x69, 0x6d, 0x69, 0x74, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, - 0x52, 0x06, 0x6c, 0x69, 0x6d, 0x69, 0x74, 0x73, 0x1a, 0x3b, 0x0a, 0x0d, 0x52, 0x65, 0x71, 0x75, - 0x65, 0x73, 0x74, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, + 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x22, + 0xa3, 0x03, 0x0a, 0x0e, 0x4e, 0x6f, 0x64, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, + 0x65, 0x63, 0x12, 0x1a, 0x0a, 0x08, 0x6e, 0x6f, 0x64, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, + 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x6e, 0x6f, 0x64, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x1d, + 0x0a, 0x0a, 0x6e, 0x6f, 0x64, 0x65, 0x5f, 0x72, 0x65, 0x61, 0x64, 0x79, 0x18, 0x02, 0x20, 0x01, + 0x28, 0x08, 0x52, 0x09, 0x6e, 0x6f, 0x64, 0x65, 0x52, 0x65, 0x61, 0x64, 0x79, 0x12, 0x24, 0x0a, + 0x0d, 0x75, 0x6e, 0x73, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x61, 0x62, 0x6c, 0x65, 0x18, 0x03, + 0x20, 0x01, 0x28, 0x08, 0x52, 0x0d, 0x75, 0x6e, 0x73, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x61, + 0x62, 0x6c, 0x65, 0x12, 0x52, 0x0a, 0x06, 0x6c, 0x61, 0x62, 0x65, 0x6c, 0x73, 0x18, 0x04, 0x20, + 0x03, 0x28, 0x0b, 0x32, 0x3a, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, + 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, + 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x4e, 0x6f, 0x64, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, + 0x70, 0x65, 0x63, 0x2e, 0x4c, 0x61, 0x62, 0x65, 0x6c, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, + 0x06, 0x6c, 0x61, 0x62, 0x65, 0x6c, 0x73, 0x12, 0x61, 0x0a, 0x0b, 0x61, 0x6e, 0x6e, 0x6f, 0x74, + 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x3f, 0x2e, 0x74, + 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, + 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x4e, 0x6f, + 0x64, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x2e, 0x41, 0x6e, 0x6e, + 0x6f, 0x74, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x0b, 0x61, + 0x6e, 0x6e, 0x6f, 0x74, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x1a, 0x39, 0x0a, 0x0b, 0x4c, 0x61, + 0x62, 0x65, 0x6c, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, - 0x65, 0x3a, 0x02, 0x38, 0x01, 0x1a, 0x39, 0x0a, 0x0b, 0x4c, 0x69, 0x6d, 0x69, 0x74, 0x73, 0x45, - 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, - 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, - 0x22, 0x80, 0x05, 0x0a, 0x13, 0x53, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x72, 0x43, 0x6f, - 0x6e, 0x66, 0x69, 0x67, 0x53, 0x70, 0x65, 0x63, 0x12, 0x18, 0x0a, 0x07, 0x65, 0x6e, 0x61, 0x62, - 0x6c, 0x65, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x07, 0x65, 0x6e, 0x61, 0x62, 0x6c, - 0x65, 0x64, 0x12, 0x14, 0x0a, 0x05, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x05, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x12, 0x61, 0x0a, 0x0a, 0x65, 0x78, 0x74, 0x72, - 0x61, 0x5f, 0x61, 0x72, 0x67, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x42, 0x2e, 0x74, - 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, - 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x53, 0x63, - 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x72, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x53, 0x70, 0x65, - 0x63, 0x2e, 0x45, 0x78, 0x74, 0x72, 0x61, 0x41, 0x72, 0x67, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, - 0x52, 0x09, 0x65, 0x78, 0x74, 0x72, 0x61, 0x41, 0x72, 0x67, 0x73, 0x12, 0x50, 0x0a, 0x0d, 0x65, - 0x78, 0x74, 0x72, 0x61, 0x5f, 0x76, 0x6f, 0x6c, 0x75, 0x6d, 0x65, 0x73, 0x18, 0x04, 0x20, 0x03, - 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, - 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, - 0x6b, 0x38, 0x73, 0x2e, 0x45, 0x78, 0x74, 0x72, 0x61, 0x56, 0x6f, 0x6c, 0x75, 0x6d, 0x65, 0x52, - 0x0c, 0x65, 0x78, 0x74, 0x72, 0x61, 0x56, 0x6f, 0x6c, 0x75, 0x6d, 0x65, 0x73, 0x12, 0x82, 0x01, - 0x0a, 0x15, 0x65, 0x6e, 0x76, 0x69, 0x72, 0x6f, 0x6e, 0x6d, 0x65, 0x6e, 0x74, 0x5f, 0x76, 0x61, - 0x72, 0x69, 0x61, 0x62, 0x6c, 0x65, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x4d, 0x2e, - 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, - 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x53, - 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x72, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x53, 0x70, - 0x65, 0x63, 0x2e, 0x45, 0x6e, 0x76, 0x69, 0x72, 0x6f, 0x6e, 0x6d, 0x65, 0x6e, 0x74, 0x56, 0x61, - 0x72, 0x69, 0x61, 0x62, 0x6c, 0x65, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x14, 0x65, 0x6e, - 0x76, 0x69, 0x72, 0x6f, 0x6e, 0x6d, 0x65, 0x6e, 0x74, 0x56, 0x61, 0x72, 0x69, 0x61, 0x62, 0x6c, - 0x65, 0x73, 0x12, 0x47, 0x0a, 0x09, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, 0x18, - 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, - 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, - 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, - 0x52, 0x09, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, 0x12, 0x2f, 0x0a, 0x06, 0x63, - 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x67, 0x6f, - 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, - 0x72, 0x75, 0x63, 0x74, 0x52, 0x06, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x1a, 0x3c, 0x0a, 0x0e, - 0x45, 0x78, 0x74, 0x72, 0x61, 0x41, 0x72, 0x67, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, - 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, - 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, - 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x1a, 0x47, 0x0a, 0x19, 0x45, 0x6e, - 0x76, 0x69, 0x72, 0x6f, 0x6e, 0x6d, 0x65, 0x6e, 0x74, 0x56, 0x61, 0x72, 0x69, 0x61, 0x62, 0x6c, - 0x65, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, - 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, - 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, - 0x02, 0x38, 0x01, 0x22, 0x43, 0x0a, 0x11, 0x53, 0x65, 0x63, 0x72, 0x65, 0x74, 0x73, 0x53, 0x74, - 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x12, 0x14, 0x0a, 0x05, 0x72, 0x65, 0x61, 0x64, - 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x05, 0x72, 0x65, 0x61, 0x64, 0x79, 0x12, 0x18, - 0x0a, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, - 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x22, 0x41, 0x0a, 0x0e, 0x53, 0x69, 0x6e, 0x67, - 0x6c, 0x65, 0x4d, 0x61, 0x6e, 0x69, 0x66, 0x65, 0x73, 0x74, 0x12, 0x2f, 0x0a, 0x06, 0x6f, 0x62, - 0x6a, 0x65, 0x63, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x67, 0x6f, 0x6f, + 0x65, 0x3a, 0x02, 0x38, 0x01, 0x1a, 0x3e, 0x0a, 0x10, 0x41, 0x6e, 0x6e, 0x6f, 0x74, 0x61, 0x74, + 0x69, 0x6f, 0x6e, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, + 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, + 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, + 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x53, 0x0a, 0x11, 0x4e, 0x6f, 0x64, 0x65, 0x54, 0x61, 0x69, + 0x6e, 0x74, 0x53, 0x70, 0x65, 0x63, 0x53, 0x70, 0x65, 0x63, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, + 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x16, 0x0a, 0x06, + 0x65, 0x66, 0x66, 0x65, 0x63, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x65, 0x66, + 0x66, 0x65, 0x63, 0x74, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x03, 0x20, + 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x22, 0x8b, 0x01, 0x0a, 0x0c, 0x4e, + 0x6f, 0x64, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x53, 0x70, 0x65, 0x63, 0x12, 0x1a, 0x0a, 0x08, 0x6e, + 0x6f, 0x64, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x6e, + 0x6f, 0x64, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x29, 0x0a, 0x10, 0x68, 0x6f, 0x73, 0x74, 0x6e, + 0x61, 0x6d, 0x65, 0x5f, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, + 0x09, 0x52, 0x0f, 0x68, 0x6f, 0x73, 0x74, 0x6e, 0x61, 0x6d, 0x65, 0x56, 0x65, 0x72, 0x73, 0x69, + 0x6f, 0x6e, 0x12, 0x34, 0x0a, 0x16, 0x73, 0x6b, 0x69, 0x70, 0x5f, 0x6e, 0x6f, 0x64, 0x65, 0x5f, + 0x72, 0x65, 0x67, 0x69, 0x73, 0x74, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, + 0x28, 0x08, 0x52, 0x14, 0x73, 0x6b, 0x69, 0x70, 0x4e, 0x6f, 0x64, 0x65, 0x52, 0x65, 0x67, 0x69, + 0x73, 0x74, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0xa7, 0x02, 0x0a, 0x09, 0x52, 0x65, 0x73, + 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, 0x12, 0x53, 0x0a, 0x08, 0x72, 0x65, 0x71, 0x75, 0x65, 0x73, + 0x74, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x37, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, + 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, + 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, + 0x63, 0x65, 0x73, 0x2e, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x73, 0x45, 0x6e, 0x74, 0x72, + 0x79, 0x52, 0x08, 0x72, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x73, 0x12, 0x4d, 0x0a, 0x06, 0x6c, + 0x69, 0x6d, 0x69, 0x74, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x35, 0x2e, 0x74, 0x61, + 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, + 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x52, 0x65, 0x73, + 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, 0x2e, 0x4c, 0x69, 0x6d, 0x69, 0x74, 0x73, 0x45, 0x6e, 0x74, + 0x72, 0x79, 0x52, 0x06, 0x6c, 0x69, 0x6d, 0x69, 0x74, 0x73, 0x1a, 0x3b, 0x0a, 0x0d, 0x52, 0x65, + 0x71, 0x75, 0x65, 0x73, 0x74, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, + 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, + 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, + 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x1a, 0x39, 0x0a, 0x0b, 0x4c, 0x69, 0x6d, 0x69, 0x74, + 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, + 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, + 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, + 0x38, 0x01, 0x22, 0x80, 0x05, 0x0a, 0x13, 0x53, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x72, + 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x53, 0x70, 0x65, 0x63, 0x12, 0x18, 0x0a, 0x07, 0x65, 0x6e, + 0x61, 0x62, 0x6c, 0x65, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x07, 0x65, 0x6e, 0x61, + 0x62, 0x6c, 0x65, 0x64, 0x12, 0x14, 0x0a, 0x05, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x18, 0x02, 0x20, + 0x01, 0x28, 0x09, 0x52, 0x05, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x12, 0x61, 0x0a, 0x0a, 0x65, 0x78, + 0x74, 0x72, 0x61, 0x5f, 0x61, 0x72, 0x67, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x42, + 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, + 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, + 0x53, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x72, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x53, + 0x70, 0x65, 0x63, 0x2e, 0x45, 0x78, 0x74, 0x72, 0x61, 0x41, 0x72, 0x67, 0x73, 0x45, 0x6e, 0x74, + 0x72, 0x79, 0x52, 0x09, 0x65, 0x78, 0x74, 0x72, 0x61, 0x41, 0x72, 0x67, 0x73, 0x12, 0x50, 0x0a, + 0x0d, 0x65, 0x78, 0x74, 0x72, 0x61, 0x5f, 0x76, 0x6f, 0x6c, 0x75, 0x6d, 0x65, 0x73, 0x18, 0x04, + 0x20, 0x03, 0x28, 0x0b, 0x32, 0x2b, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, + 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, + 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x45, 0x78, 0x74, 0x72, 0x61, 0x56, 0x6f, 0x6c, 0x75, 0x6d, + 0x65, 0x52, 0x0c, 0x65, 0x78, 0x74, 0x72, 0x61, 0x56, 0x6f, 0x6c, 0x75, 0x6d, 0x65, 0x73, 0x12, + 0x82, 0x01, 0x0a, 0x15, 0x65, 0x6e, 0x76, 0x69, 0x72, 0x6f, 0x6e, 0x6d, 0x65, 0x6e, 0x74, 0x5f, + 0x76, 0x61, 0x72, 0x69, 0x61, 0x62, 0x6c, 0x65, 0x73, 0x18, 0x05, 0x20, 0x03, 0x28, 0x0b, 0x32, + 0x4d, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, + 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, + 0x2e, 0x53, 0x63, 0x68, 0x65, 0x64, 0x75, 0x6c, 0x65, 0x72, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, + 0x53, 0x70, 0x65, 0x63, 0x2e, 0x45, 0x6e, 0x76, 0x69, 0x72, 0x6f, 0x6e, 0x6d, 0x65, 0x6e, 0x74, + 0x56, 0x61, 0x72, 0x69, 0x61, 0x62, 0x6c, 0x65, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52, 0x14, + 0x65, 0x6e, 0x76, 0x69, 0x72, 0x6f, 0x6e, 0x6d, 0x65, 0x6e, 0x74, 0x56, 0x61, 0x72, 0x69, 0x61, + 0x62, 0x6c, 0x65, 0x73, 0x12, 0x47, 0x0a, 0x09, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, + 0x73, 0x18, 0x06, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x29, 0x2e, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2e, + 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, + 0x69, 0x6f, 0x6e, 0x73, 0x2e, 0x6b, 0x38, 0x73, 0x2e, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, + 0x65, 0x73, 0x52, 0x09, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, 0x12, 0x2f, 0x0a, + 0x06, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e, + 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, + 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x52, 0x06, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x1a, 0x3c, + 0x0a, 0x0e, 0x45, 0x78, 0x74, 0x72, 0x61, 0x41, 0x72, 0x67, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, + 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, + 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, + 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x1a, 0x47, 0x0a, 0x19, + 0x45, 0x6e, 0x76, 0x69, 0x72, 0x6f, 0x6e, 0x6d, 0x65, 0x6e, 0x74, 0x56, 0x61, 0x72, 0x69, 0x61, + 0x62, 0x6c, 0x65, 0x73, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, + 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, + 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, + 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0x43, 0x0a, 0x11, 0x53, 0x65, 0x63, 0x72, 0x65, 0x74, 0x73, + 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x12, 0x14, 0x0a, 0x05, 0x72, 0x65, + 0x61, 0x64, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x08, 0x52, 0x05, 0x72, 0x65, 0x61, 0x64, 0x79, + 0x12, 0x18, 0x0a, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, + 0x09, 0x52, 0x07, 0x76, 0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x22, 0x41, 0x0a, 0x0e, 0x53, 0x69, + 0x6e, 0x67, 0x6c, 0x65, 0x4d, 0x61, 0x6e, 0x69, 0x66, 0x65, 0x73, 0x74, 0x12, 0x2f, 0x0a, 0x06, + 0x6f, 0x62, 0x6a, 0x65, 0x63, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x67, + 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, + 0x74, 0x72, 0x75, 0x63, 0x74, 0x52, 0x06, 0x6f, 0x62, 0x6a, 0x65, 0x63, 0x74, 0x22, 0x2d, 0x0a, + 0x19, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, 0x50, 0x6f, 0x64, 0x53, 0x65, 0x72, 0x76, 0x65, 0x72, + 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x12, 0x10, 0x0a, 0x03, 0x75, 0x72, + 0x6c, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x22, 0x3a, 0x0a, 0x0d, + 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, 0x50, 0x6f, 0x64, 0x53, 0x70, 0x65, 0x63, 0x12, 0x29, 0x0a, + 0x03, 0x70, 0x6f, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, - 0x75, 0x63, 0x74, 0x52, 0x06, 0x6f, 0x62, 0x6a, 0x65, 0x63, 0x74, 0x22, 0x2d, 0x0a, 0x19, 0x53, - 0x74, 0x61, 0x74, 0x69, 0x63, 0x50, 0x6f, 0x64, 0x53, 0x65, 0x72, 0x76, 0x65, 0x72, 0x53, 0x74, - 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x12, 0x10, 0x0a, 0x03, 0x75, 0x72, 0x6c, 0x18, - 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x22, 0x3a, 0x0a, 0x0d, 0x53, 0x74, - 0x61, 0x74, 0x69, 0x63, 0x50, 0x6f, 0x64, 0x53, 0x70, 0x65, 0x63, 0x12, 0x29, 0x0a, 0x03, 0x70, - 0x6f, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, - 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x75, 0x63, - 0x74, 0x52, 0x03, 0x70, 0x6f, 0x64, 0x22, 0x4d, 0x0a, 0x13, 0x53, 0x74, 0x61, 0x74, 0x69, 0x63, - 0x50, 0x6f, 0x64, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x12, 0x36, 0x0a, - 0x0a, 0x70, 0x6f, 0x64, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, - 0x0b, 0x32, 0x17, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, - 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x52, 0x09, 0x70, 0x6f, 0x64, 0x53, - 0x74, 0x61, 0x74, 0x75, 0x73, 0x42, 0x48, 0x5a, 0x46, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, - 0x63, 0x6f, 0x6d, 0x2f, 0x73, 0x69, 0x64, 0x65, 0x72, 0x6f, 0x6c, 0x61, 0x62, 0x73, 0x2f, 0x74, - 0x61, 0x6c, 0x6f, 0x73, 0x2f, 0x70, 0x6b, 0x67, 0x2f, 0x6d, 0x61, 0x63, 0x68, 0x69, 0x6e, 0x65, - 0x72, 0x79, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2f, - 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2f, 0x6b, 0x38, 0x73, 0x62, - 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x75, 0x63, 0x74, 0x52, 0x03, 0x70, 0x6f, 0x64, 0x22, 0x4d, 0x0a, 0x13, 0x53, 0x74, 0x61, 0x74, + 0x69, 0x63, 0x50, 0x6f, 0x64, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x53, 0x70, 0x65, 0x63, 0x12, + 0x36, 0x0a, 0x0a, 0x70, 0x6f, 0x64, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x01, 0x20, + 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, + 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x52, 0x09, 0x70, 0x6f, + 0x64, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x42, 0x48, 0x5a, 0x46, 0x67, 0x69, 0x74, 0x68, 0x75, + 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x73, 0x69, 0x64, 0x65, 0x72, 0x6f, 0x6c, 0x61, 0x62, 0x73, + 0x2f, 0x74, 0x61, 0x6c, 0x6f, 0x73, 0x2f, 0x70, 0x6b, 0x67, 0x2f, 0x6d, 0x61, 0x63, 0x68, 0x69, + 0x6e, 0x65, 0x72, 0x79, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, + 0x65, 0x2f, 0x64, 0x65, 0x66, 0x69, 0x6e, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x2f, 0x6b, 0x38, + 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, } var ( @@ -2726,7 +2786,7 @@ func file_resource_definitions_k8s_k8s_proto_rawDescGZIP() []byte { return file_resource_definitions_k8s_k8s_proto_rawDescData } -var file_resource_definitions_k8s_k8s_proto_msgTypes = make([]protoimpl.MessageInfo, 44) +var file_resource_definitions_k8s_k8s_proto_msgTypes = make([]protoimpl.MessageInfo, 45) var file_resource_definitions_k8s_k8s_proto_goTypes = []any{ (*APIServerConfigSpec)(nil), // 0: talos.resource.definitions.k8s.APIServerConfigSpec (*AdmissionControlConfigSpec)(nil), // 1: talos.resource.definitions.k8s.AdmissionControlConfigSpec @@ -2747,73 +2807,74 @@ var file_resource_definitions_k8s_k8s_proto_goTypes = []any{ (*KubeletSpecSpec)(nil), // 16: talos.resource.definitions.k8s.KubeletSpecSpec (*ManifestSpec)(nil), // 17: talos.resource.definitions.k8s.ManifestSpec (*ManifestStatusSpec)(nil), // 18: talos.resource.definitions.k8s.ManifestStatusSpec - (*NodeIPConfigSpec)(nil), // 19: talos.resource.definitions.k8s.NodeIPConfigSpec - (*NodeIPSpec)(nil), // 20: talos.resource.definitions.k8s.NodeIPSpec - (*NodeLabelSpecSpec)(nil), // 21: talos.resource.definitions.k8s.NodeLabelSpecSpec - (*NodeStatusSpec)(nil), // 22: talos.resource.definitions.k8s.NodeStatusSpec - (*NodeTaintSpecSpec)(nil), // 23: talos.resource.definitions.k8s.NodeTaintSpecSpec - (*NodenameSpec)(nil), // 24: talos.resource.definitions.k8s.NodenameSpec - (*Resources)(nil), // 25: talos.resource.definitions.k8s.Resources - (*SchedulerConfigSpec)(nil), // 26: talos.resource.definitions.k8s.SchedulerConfigSpec - (*SecretsStatusSpec)(nil), // 27: talos.resource.definitions.k8s.SecretsStatusSpec - (*SingleManifest)(nil), // 28: talos.resource.definitions.k8s.SingleManifest - (*StaticPodServerStatusSpec)(nil), // 29: talos.resource.definitions.k8s.StaticPodServerStatusSpec - (*StaticPodSpec)(nil), // 30: talos.resource.definitions.k8s.StaticPodSpec - (*StaticPodStatusSpec)(nil), // 31: talos.resource.definitions.k8s.StaticPodStatusSpec - nil, // 32: talos.resource.definitions.k8s.APIServerConfigSpec.ExtraArgsEntry - nil, // 33: talos.resource.definitions.k8s.APIServerConfigSpec.EnvironmentVariablesEntry - nil, // 34: talos.resource.definitions.k8s.ControllerManagerConfigSpec.ExtraArgsEntry - nil, // 35: talos.resource.definitions.k8s.ControllerManagerConfigSpec.EnvironmentVariablesEntry - nil, // 36: talos.resource.definitions.k8s.ExtraManifest.ExtraHeadersEntry - nil, // 37: talos.resource.definitions.k8s.KubeletConfigSpec.ExtraArgsEntry - nil, // 38: talos.resource.definitions.k8s.NodeStatusSpec.LabelsEntry - nil, // 39: talos.resource.definitions.k8s.NodeStatusSpec.AnnotationsEntry - nil, // 40: talos.resource.definitions.k8s.Resources.RequestsEntry - nil, // 41: talos.resource.definitions.k8s.Resources.LimitsEntry - nil, // 42: talos.resource.definitions.k8s.SchedulerConfigSpec.ExtraArgsEntry - nil, // 43: talos.resource.definitions.k8s.SchedulerConfigSpec.EnvironmentVariablesEntry - (*structpb.Struct)(nil), // 44: google.protobuf.Struct - (*common.NetIP)(nil), // 45: common.NetIP - (*proto.Mount)(nil), // 46: talos.resource.definitions.proto.Mount + (*NodeAnnotationSpecSpec)(nil), // 19: talos.resource.definitions.k8s.NodeAnnotationSpecSpec + (*NodeIPConfigSpec)(nil), // 20: talos.resource.definitions.k8s.NodeIPConfigSpec + (*NodeIPSpec)(nil), // 21: talos.resource.definitions.k8s.NodeIPSpec + (*NodeLabelSpecSpec)(nil), // 22: talos.resource.definitions.k8s.NodeLabelSpecSpec + (*NodeStatusSpec)(nil), // 23: talos.resource.definitions.k8s.NodeStatusSpec + (*NodeTaintSpecSpec)(nil), // 24: talos.resource.definitions.k8s.NodeTaintSpecSpec + (*NodenameSpec)(nil), // 25: talos.resource.definitions.k8s.NodenameSpec + (*Resources)(nil), // 26: talos.resource.definitions.k8s.Resources + (*SchedulerConfigSpec)(nil), // 27: talos.resource.definitions.k8s.SchedulerConfigSpec + (*SecretsStatusSpec)(nil), // 28: talos.resource.definitions.k8s.SecretsStatusSpec + (*SingleManifest)(nil), // 29: talos.resource.definitions.k8s.SingleManifest + (*StaticPodServerStatusSpec)(nil), // 30: talos.resource.definitions.k8s.StaticPodServerStatusSpec + (*StaticPodSpec)(nil), // 31: talos.resource.definitions.k8s.StaticPodSpec + (*StaticPodStatusSpec)(nil), // 32: talos.resource.definitions.k8s.StaticPodStatusSpec + nil, // 33: talos.resource.definitions.k8s.APIServerConfigSpec.ExtraArgsEntry + nil, // 34: talos.resource.definitions.k8s.APIServerConfigSpec.EnvironmentVariablesEntry + nil, // 35: talos.resource.definitions.k8s.ControllerManagerConfigSpec.ExtraArgsEntry + nil, // 36: talos.resource.definitions.k8s.ControllerManagerConfigSpec.EnvironmentVariablesEntry + nil, // 37: talos.resource.definitions.k8s.ExtraManifest.ExtraHeadersEntry + nil, // 38: talos.resource.definitions.k8s.KubeletConfigSpec.ExtraArgsEntry + nil, // 39: talos.resource.definitions.k8s.NodeStatusSpec.LabelsEntry + nil, // 40: talos.resource.definitions.k8s.NodeStatusSpec.AnnotationsEntry + nil, // 41: talos.resource.definitions.k8s.Resources.RequestsEntry + nil, // 42: talos.resource.definitions.k8s.Resources.LimitsEntry + nil, // 43: talos.resource.definitions.k8s.SchedulerConfigSpec.ExtraArgsEntry + nil, // 44: talos.resource.definitions.k8s.SchedulerConfigSpec.EnvironmentVariablesEntry + (*structpb.Struct)(nil), // 45: google.protobuf.Struct + (*common.NetIP)(nil), // 46: common.NetIP + (*proto.Mount)(nil), // 47: talos.resource.definitions.proto.Mount } var file_resource_definitions_k8s_k8s_proto_depIdxs = []int32{ - 32, // 0: talos.resource.definitions.k8s.APIServerConfigSpec.extra_args:type_name -> talos.resource.definitions.k8s.APIServerConfigSpec.ExtraArgsEntry + 33, // 0: talos.resource.definitions.k8s.APIServerConfigSpec.extra_args:type_name -> talos.resource.definitions.k8s.APIServerConfigSpec.ExtraArgsEntry 10, // 1: talos.resource.definitions.k8s.APIServerConfigSpec.extra_volumes:type_name -> talos.resource.definitions.k8s.ExtraVolume - 33, // 2: talos.resource.definitions.k8s.APIServerConfigSpec.environment_variables:type_name -> talos.resource.definitions.k8s.APIServerConfigSpec.EnvironmentVariablesEntry - 25, // 3: talos.resource.definitions.k8s.APIServerConfigSpec.resources:type_name -> talos.resource.definitions.k8s.Resources + 34, // 2: talos.resource.definitions.k8s.APIServerConfigSpec.environment_variables:type_name -> talos.resource.definitions.k8s.APIServerConfigSpec.EnvironmentVariablesEntry + 26, // 3: talos.resource.definitions.k8s.APIServerConfigSpec.resources:type_name -> talos.resource.definitions.k8s.Resources 2, // 4: talos.resource.definitions.k8s.AdmissionControlConfigSpec.config:type_name -> talos.resource.definitions.k8s.AdmissionPluginSpec - 44, // 5: talos.resource.definitions.k8s.AdmissionPluginSpec.configuration:type_name -> google.protobuf.Struct - 44, // 6: talos.resource.definitions.k8s.AuditPolicyConfigSpec.config:type_name -> google.protobuf.Struct - 34, // 7: talos.resource.definitions.k8s.ControllerManagerConfigSpec.extra_args:type_name -> talos.resource.definitions.k8s.ControllerManagerConfigSpec.ExtraArgsEntry + 45, // 5: talos.resource.definitions.k8s.AdmissionPluginSpec.configuration:type_name -> google.protobuf.Struct + 45, // 6: talos.resource.definitions.k8s.AuditPolicyConfigSpec.config:type_name -> google.protobuf.Struct + 35, // 7: talos.resource.definitions.k8s.ControllerManagerConfigSpec.extra_args:type_name -> talos.resource.definitions.k8s.ControllerManagerConfigSpec.ExtraArgsEntry 10, // 8: talos.resource.definitions.k8s.ControllerManagerConfigSpec.extra_volumes:type_name -> talos.resource.definitions.k8s.ExtraVolume - 35, // 9: talos.resource.definitions.k8s.ControllerManagerConfigSpec.environment_variables:type_name -> talos.resource.definitions.k8s.ControllerManagerConfigSpec.EnvironmentVariablesEntry - 25, // 10: talos.resource.definitions.k8s.ControllerManagerConfigSpec.resources:type_name -> talos.resource.definitions.k8s.Resources - 45, // 11: talos.resource.definitions.k8s.EndpointSpec.addresses:type_name -> common.NetIP - 36, // 12: talos.resource.definitions.k8s.ExtraManifest.extra_headers:type_name -> talos.resource.definitions.k8s.ExtraManifest.ExtraHeadersEntry + 36, // 9: talos.resource.definitions.k8s.ControllerManagerConfigSpec.environment_variables:type_name -> talos.resource.definitions.k8s.ControllerManagerConfigSpec.EnvironmentVariablesEntry + 26, // 10: talos.resource.definitions.k8s.ControllerManagerConfigSpec.resources:type_name -> talos.resource.definitions.k8s.Resources + 46, // 11: talos.resource.definitions.k8s.EndpointSpec.addresses:type_name -> common.NetIP + 37, // 12: talos.resource.definitions.k8s.ExtraManifest.extra_headers:type_name -> talos.resource.definitions.k8s.ExtraManifest.ExtraHeadersEntry 8, // 13: talos.resource.definitions.k8s.ExtraManifestsConfigSpec.extra_manifests:type_name -> talos.resource.definitions.k8s.ExtraManifest 12, // 14: talos.resource.definitions.k8s.KubePrismConfigSpec.endpoints:type_name -> talos.resource.definitions.k8s.KubePrismEndpoint 12, // 15: talos.resource.definitions.k8s.KubePrismEndpointsSpec.endpoints:type_name -> talos.resource.definitions.k8s.KubePrismEndpoint - 37, // 16: talos.resource.definitions.k8s.KubeletConfigSpec.extra_args:type_name -> talos.resource.definitions.k8s.KubeletConfigSpec.ExtraArgsEntry - 46, // 17: talos.resource.definitions.k8s.KubeletConfigSpec.extra_mounts:type_name -> talos.resource.definitions.proto.Mount - 44, // 18: talos.resource.definitions.k8s.KubeletConfigSpec.extra_config:type_name -> google.protobuf.Struct - 44, // 19: talos.resource.definitions.k8s.KubeletConfigSpec.credential_provider_config:type_name -> google.protobuf.Struct - 46, // 20: talos.resource.definitions.k8s.KubeletSpecSpec.extra_mounts:type_name -> talos.resource.definitions.proto.Mount - 44, // 21: talos.resource.definitions.k8s.KubeletSpecSpec.config:type_name -> google.protobuf.Struct - 44, // 22: talos.resource.definitions.k8s.KubeletSpecSpec.credential_provider_config:type_name -> google.protobuf.Struct - 28, // 23: talos.resource.definitions.k8s.ManifestSpec.items:type_name -> talos.resource.definitions.k8s.SingleManifest - 45, // 24: talos.resource.definitions.k8s.NodeIPSpec.addresses:type_name -> common.NetIP - 38, // 25: talos.resource.definitions.k8s.NodeStatusSpec.labels:type_name -> talos.resource.definitions.k8s.NodeStatusSpec.LabelsEntry - 39, // 26: talos.resource.definitions.k8s.NodeStatusSpec.annotations:type_name -> talos.resource.definitions.k8s.NodeStatusSpec.AnnotationsEntry - 40, // 27: talos.resource.definitions.k8s.Resources.requests:type_name -> talos.resource.definitions.k8s.Resources.RequestsEntry - 41, // 28: talos.resource.definitions.k8s.Resources.limits:type_name -> talos.resource.definitions.k8s.Resources.LimitsEntry - 42, // 29: talos.resource.definitions.k8s.SchedulerConfigSpec.extra_args:type_name -> talos.resource.definitions.k8s.SchedulerConfigSpec.ExtraArgsEntry + 38, // 16: talos.resource.definitions.k8s.KubeletConfigSpec.extra_args:type_name -> talos.resource.definitions.k8s.KubeletConfigSpec.ExtraArgsEntry + 47, // 17: talos.resource.definitions.k8s.KubeletConfigSpec.extra_mounts:type_name -> talos.resource.definitions.proto.Mount + 45, // 18: talos.resource.definitions.k8s.KubeletConfigSpec.extra_config:type_name -> google.protobuf.Struct + 45, // 19: talos.resource.definitions.k8s.KubeletConfigSpec.credential_provider_config:type_name -> google.protobuf.Struct + 47, // 20: talos.resource.definitions.k8s.KubeletSpecSpec.extra_mounts:type_name -> talos.resource.definitions.proto.Mount + 45, // 21: talos.resource.definitions.k8s.KubeletSpecSpec.config:type_name -> google.protobuf.Struct + 45, // 22: talos.resource.definitions.k8s.KubeletSpecSpec.credential_provider_config:type_name -> google.protobuf.Struct + 29, // 23: talos.resource.definitions.k8s.ManifestSpec.items:type_name -> talos.resource.definitions.k8s.SingleManifest + 46, // 24: talos.resource.definitions.k8s.NodeIPSpec.addresses:type_name -> common.NetIP + 39, // 25: talos.resource.definitions.k8s.NodeStatusSpec.labels:type_name -> talos.resource.definitions.k8s.NodeStatusSpec.LabelsEntry + 40, // 26: talos.resource.definitions.k8s.NodeStatusSpec.annotations:type_name -> talos.resource.definitions.k8s.NodeStatusSpec.AnnotationsEntry + 41, // 27: talos.resource.definitions.k8s.Resources.requests:type_name -> talos.resource.definitions.k8s.Resources.RequestsEntry + 42, // 28: talos.resource.definitions.k8s.Resources.limits:type_name -> talos.resource.definitions.k8s.Resources.LimitsEntry + 43, // 29: talos.resource.definitions.k8s.SchedulerConfigSpec.extra_args:type_name -> talos.resource.definitions.k8s.SchedulerConfigSpec.ExtraArgsEntry 10, // 30: talos.resource.definitions.k8s.SchedulerConfigSpec.extra_volumes:type_name -> talos.resource.definitions.k8s.ExtraVolume - 43, // 31: talos.resource.definitions.k8s.SchedulerConfigSpec.environment_variables:type_name -> talos.resource.definitions.k8s.SchedulerConfigSpec.EnvironmentVariablesEntry - 25, // 32: talos.resource.definitions.k8s.SchedulerConfigSpec.resources:type_name -> talos.resource.definitions.k8s.Resources - 44, // 33: talos.resource.definitions.k8s.SchedulerConfigSpec.config:type_name -> google.protobuf.Struct - 44, // 34: talos.resource.definitions.k8s.SingleManifest.object:type_name -> google.protobuf.Struct - 44, // 35: talos.resource.definitions.k8s.StaticPodSpec.pod:type_name -> google.protobuf.Struct - 44, // 36: talos.resource.definitions.k8s.StaticPodStatusSpec.pod_status:type_name -> google.protobuf.Struct + 44, // 31: talos.resource.definitions.k8s.SchedulerConfigSpec.environment_variables:type_name -> talos.resource.definitions.k8s.SchedulerConfigSpec.EnvironmentVariablesEntry + 26, // 32: talos.resource.definitions.k8s.SchedulerConfigSpec.resources:type_name -> talos.resource.definitions.k8s.Resources + 45, // 33: talos.resource.definitions.k8s.SchedulerConfigSpec.config:type_name -> google.protobuf.Struct + 45, // 34: talos.resource.definitions.k8s.SingleManifest.object:type_name -> google.protobuf.Struct + 45, // 35: talos.resource.definitions.k8s.StaticPodSpec.pod:type_name -> google.protobuf.Struct + 45, // 36: talos.resource.definitions.k8s.StaticPodStatusSpec.pod_status:type_name -> google.protobuf.Struct 37, // [37:37] is the sub-list for method output_type 37, // [37:37] is the sub-list for method input_type 37, // [37:37] is the sub-list for extension type_name @@ -3056,7 +3117,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[19].Exporter = func(v any, i int) any { - switch v := v.(*NodeIPConfigSpec); i { + switch v := v.(*NodeAnnotationSpecSpec); i { case 0: return &v.state case 1: @@ -3068,7 +3129,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[20].Exporter = func(v any, i int) any { - switch v := v.(*NodeIPSpec); i { + switch v := v.(*NodeIPConfigSpec); i { case 0: return &v.state case 1: @@ -3080,7 +3141,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[21].Exporter = func(v any, i int) any { - switch v := v.(*NodeLabelSpecSpec); i { + switch v := v.(*NodeIPSpec); i { case 0: return &v.state case 1: @@ -3092,7 +3153,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[22].Exporter = func(v any, i int) any { - switch v := v.(*NodeStatusSpec); i { + switch v := v.(*NodeLabelSpecSpec); i { case 0: return &v.state case 1: @@ -3104,7 +3165,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[23].Exporter = func(v any, i int) any { - switch v := v.(*NodeTaintSpecSpec); i { + switch v := v.(*NodeStatusSpec); i { case 0: return &v.state case 1: @@ -3116,7 +3177,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[24].Exporter = func(v any, i int) any { - switch v := v.(*NodenameSpec); i { + switch v := v.(*NodeTaintSpecSpec); i { case 0: return &v.state case 1: @@ -3128,7 +3189,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[25].Exporter = func(v any, i int) any { - switch v := v.(*Resources); i { + switch v := v.(*NodenameSpec); i { case 0: return &v.state case 1: @@ -3140,7 +3201,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[26].Exporter = func(v any, i int) any { - switch v := v.(*SchedulerConfigSpec); i { + switch v := v.(*Resources); i { case 0: return &v.state case 1: @@ -3152,7 +3213,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[27].Exporter = func(v any, i int) any { - switch v := v.(*SecretsStatusSpec); i { + switch v := v.(*SchedulerConfigSpec); i { case 0: return &v.state case 1: @@ -3164,7 +3225,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[28].Exporter = func(v any, i int) any { - switch v := v.(*SingleManifest); i { + switch v := v.(*SecretsStatusSpec); i { case 0: return &v.state case 1: @@ -3176,7 +3237,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[29].Exporter = func(v any, i int) any { - switch v := v.(*StaticPodServerStatusSpec); i { + switch v := v.(*SingleManifest); i { case 0: return &v.state case 1: @@ -3188,7 +3249,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[30].Exporter = func(v any, i int) any { - switch v := v.(*StaticPodSpec); i { + switch v := v.(*StaticPodServerStatusSpec); i { case 0: return &v.state case 1: @@ -3200,6 +3261,18 @@ func file_resource_definitions_k8s_k8s_proto_init() { } } file_resource_definitions_k8s_k8s_proto_msgTypes[31].Exporter = func(v any, i int) any { + switch v := v.(*StaticPodSpec); i { + case 0: + return &v.state + case 1: + return &v.sizeCache + case 2: + return &v.unknownFields + default: + return nil + } + } + file_resource_definitions_k8s_k8s_proto_msgTypes[32].Exporter = func(v any, i int) any { switch v := v.(*StaticPodStatusSpec); i { case 0: return &v.state @@ -3218,7 +3291,7 @@ func file_resource_definitions_k8s_k8s_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: file_resource_definitions_k8s_k8s_proto_rawDesc, NumEnums: 0, - NumMessages: 44, + NumMessages: 45, NumExtensions: 0, NumServices: 0, }, diff --git a/pkg/machinery/api/resource/definitions/k8s/k8s_vtproto.pb.go b/pkg/machinery/api/resource/definitions/k8s/k8s_vtproto.pb.go index 35ec3dcd92..30f3fdd69f 100644 --- a/pkg/machinery/api/resource/definitions/k8s/k8s_vtproto.pb.go +++ b/pkg/machinery/api/resource/definitions/k8s/k8s_vtproto.pb.go @@ -1503,6 +1503,53 @@ func (m *ManifestStatusSpec) MarshalToSizedBufferVT(dAtA []byte) (int, error) { return len(dAtA) - i, nil } +func (m *NodeAnnotationSpecSpec) MarshalVT() (dAtA []byte, err error) { + if m == nil { + return nil, nil + } + size := m.SizeVT() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBufferVT(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *NodeAnnotationSpecSpec) MarshalToVT(dAtA []byte) (int, error) { + size := m.SizeVT() + return m.MarshalToSizedBufferVT(dAtA[:size]) +} + +func (m *NodeAnnotationSpecSpec) MarshalToSizedBufferVT(dAtA []byte) (int, error) { + if m == nil { + return 0, nil + } + i := len(dAtA) + _ = i + var l int + _ = l + if m.unknownFields != nil { + i -= len(m.unknownFields) + copy(dAtA[i:], m.unknownFields) + } + if len(m.Value) > 0 { + i -= len(m.Value) + copy(dAtA[i:], m.Value) + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Value))) + i-- + dAtA[i] = 0x12 + } + if len(m.Key) > 0 { + i -= len(m.Key) + copy(dAtA[i:], m.Key) + i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Key))) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + func (m *NodeIPConfigSpec) MarshalVT() (dAtA []byte, err error) { if m == nil { return nil, nil @@ -2875,6 +2922,24 @@ func (m *ManifestStatusSpec) SizeVT() (n int) { return n } +func (m *NodeAnnotationSpecSpec) SizeVT() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + l = len(m.Key) + if l > 0 { + n += 1 + l + protohelpers.SizeOfVarint(uint64(l)) + } + l = len(m.Value) + if l > 0 { + n += 1 + l + protohelpers.SizeOfVarint(uint64(l)) + } + n += len(m.unknownFields) + return n +} + func (m *NodeIPConfigSpec) SizeVT() (n int) { if m == nil { return 0 @@ -7310,6 +7375,121 @@ func (m *ManifestStatusSpec) UnmarshalVT(dAtA []byte) error { } return nil } +func (m *NodeAnnotationSpecSpec) UnmarshalVT(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return protohelpers.ErrIntOverflow + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: NodeAnnotationSpecSpec: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: NodeAnnotationSpecSpec: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Key", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return protohelpers.ErrIntOverflow + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return protohelpers.ErrInvalidLength + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return protohelpers.ErrInvalidLength + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Key = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field Value", wireType) + } + var stringLen uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return protohelpers.ErrIntOverflow + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + stringLen |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + intStringLen := int(stringLen) + if intStringLen < 0 { + return protohelpers.ErrInvalidLength + } + postIndex := iNdEx + intStringLen + if postIndex < 0 { + return protohelpers.ErrInvalidLength + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.Value = string(dAtA[iNdEx:postIndex]) + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := protohelpers.Skip(dAtA[iNdEx:]) + if err != nil { + return err + } + if (skippy < 0) || (iNdEx+skippy) < 0 { + return protohelpers.ErrInvalidLength + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + m.unknownFields = append(m.unknownFields, dAtA[iNdEx:iNdEx+skippy]...) + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} func (m *NodeIPConfigSpec) UnmarshalVT(dAtA []byte) error { l := len(dAtA) iNdEx := 0 diff --git a/pkg/machinery/config/config/machine.go b/pkg/machinery/config/config/machine.go index f6b0a302c0..aaafa1b07f 100644 --- a/pkg/machinery/config/config/machine.go +++ b/pkg/machinery/config/config/machine.go @@ -42,6 +42,7 @@ type MachineConfig interface { Kernel() Kernel SeccompProfiles() []SeccompProfile NodeLabels() NodeLabels + NodeAnnotations() NodeAnnotations NodeTaints() NodeTaints } @@ -55,6 +56,9 @@ type SeccompProfile interface { // NodeLabels defines the labels that should be set on a node. type NodeLabels map[string]string +// NodeAnnotations defines the annotations that should be set on a node. +type NodeAnnotations map[string]string + // NodeTaints defines the taints that should be set on a node. type NodeTaints map[string]string diff --git a/pkg/machinery/config/schemas/config.schema.json b/pkg/machinery/config/schemas/config.schema.json index 09647474d1..86062b13eb 100644 --- a/pkg/machinery/config/schemas/config.schema.json +++ b/pkg/machinery/config/schemas/config.schema.json @@ -2637,6 +2637,18 @@ "markdownDescription": "Configures the node labels for the machine.\n\nNote: In the default Kubernetes configuration, worker nodes are restricted to set\nlabels with some prefixes (see [NodeRestriction](https://kubernetes.io/docs/reference/access-authn-authz/admission-controllers/#noderestriction) admission plugin).", "x-intellij-html-description": "\u003cp\u003eConfigures the node labels for the machine.\u003c/p\u003e\n\n\u003cp\u003eNote: In the default Kubernetes configuration, worker nodes are restricted to set\nlabels with some prefixes (see \u003ca href=\"https://kubernetes.io/docs/reference/access-authn-authz/admission-controllers/#noderestriction\" target=\"_blank\"\u003eNodeRestriction\u003c/a\u003e admission plugin).\u003c/p\u003e\n" }, + "nodeAnnotations": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object", + "title": "nodeAnnotations", + "description": "Configures the node annotations for the machine.\n", + "markdownDescription": "Configures the node annotations for the machine.", + "x-intellij-html-description": "\u003cp\u003eConfigures the node annotations for the machine.\u003c/p\u003e\n" + }, "nodeTaints": { "patternProperties": { ".*": { diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_provider.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_provider.go index d7f06f05fc..1b2206281b 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_provider.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_provider.go @@ -91,6 +91,11 @@ func (m *MachineConfig) NodeLabels() config.NodeLabels { return m.MachineNodeLabels } +// NodeAnnotations implements the config.Provider interface. +func (m *MachineConfig) NodeAnnotations() config.NodeAnnotations { + return m.MachineNodeAnnotations +} + // NodeTaints implements the config.Provider interface. func (m *MachineConfig) NodeTaints() config.NodeTaints { return m.MachineNodeTaints diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_types.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_types.go index 419ed04ba7..b957bcaed0 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_types.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_types.go @@ -300,6 +300,12 @@ type MachineConfig struct { // value: 'map[string]string{"exampleLabel": "exampleLabelValue"}' MachineNodeLabels map[string]string `yaml:"nodeLabels,omitempty"` // description: | + // Configures the node annotations for the machine. + // examples: + // - name: node annotations example. + // value: 'map[string]string{"customer.io/rack": "r13a25"}' + MachineNodeAnnotations map[string]string `yaml:"nodeAnnotations,omitempty"` + // description: | // Configures the node taints for the machine. Effect is optional. // // Note: In the default Kubernetes configuration, worker nodes are not allowed to diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_types_doc.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_types_doc.go index beb95fbd3e..9875c4311f 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_types_doc.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_types_doc.go @@ -256,6 +256,13 @@ func (MachineConfig) Doc() *encoder.Doc { Description: "Configures the node labels for the machine.\n\nNote: In the default Kubernetes configuration, worker nodes are restricted to set\nlabels with some prefixes (see [NodeRestriction](https://kubernetes.io/docs/reference/access-authn-authz/admission-controllers/#noderestriction) admission plugin).", Comments: [3]string{"" /* encoder.HeadComment */, "Configures the node labels for the machine." /* encoder.LineComment */, "" /* encoder.FootComment */}, }, + { + Name: "nodeAnnotations", + Type: "map[string]string", + Note: "", + Description: "Configures the node annotations for the machine.", + Comments: [3]string{"" /* encoder.HeadComment */, "Configures the node annotations for the machine." /* encoder.LineComment */, "" /* encoder.FootComment */}, + }, { Name: "nodeTaints", Type: "map[string]string", @@ -292,7 +299,8 @@ func (MachineConfig) Doc() *encoder.Doc { doc.Fields[21].AddExample("", machineKernelExample()) doc.Fields[22].AddExample("", machineSeccompExample()) doc.Fields[23].AddExample("node labels example.", map[string]string{"exampleLabel": "exampleLabelValue"}) - doc.Fields[24].AddExample("node taints example.", map[string]string{"exampleTaint": "exampleTaintValue:NoSchedule"}) + doc.Fields[24].AddExample("node annotations example.", map[string]string{"customer.io/rack": "r13a25"}) + doc.Fields[25].AddExample("node taints example.", map[string]string{"exampleTaint": "exampleTaintValue:NoSchedule"}) return doc } diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_validation.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_validation.go index e3d70681cb..117d604956 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_validation.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_validation.go @@ -319,6 +319,10 @@ func (c *Config) Validate(mode validation.RuntimeMode, options ...validation.Opt result = multierror.Append(result, fmt.Errorf("invalid machine node labels: %w", err)) } + if err := labels.ValidateAnnotations(c.MachineConfig.MachineNodeAnnotations); err != nil { + result = multierror.Append(result, fmt.Errorf("invalid machine node annotations: %w", err)) + } + if err := labels.ValidateTaints(c.MachineConfig.MachineNodeTaints); err != nil { result = multierror.Append(result, fmt.Errorf("invalid machine node taints: %w", err)) } diff --git a/pkg/machinery/constants/constants.go b/pkg/machinery/constants/constants.go index 52891f254f..035ac541ab 100644 --- a/pkg/machinery/constants/constants.go +++ b/pkg/machinery/constants/constants.go @@ -768,9 +768,15 @@ const ( // AnnotationOwnedLabels is the annotation key for the list of node labels owned by Talos. AnnotationOwnedLabels = "talos.dev/owned-labels" + // AnnotationOwnedAnnotations is the annotation key for the list of node annotations owned by Talos. + AnnotationOwnedAnnotations = "talos.dev/owned-annotations" + // AnnotationOwnedTaints is the annotation key for the list of node taints owned by Talos. AnnotationOwnedTaints = "talos.dev/owned-taints" + // K8sExtensionPrefix is the prefix for node labels/annotations listing extensions. + K8sExtensionPrefix = "extensions.talos.dev/" + // DefaultNTPServer is the NTP server to use if not configured explicitly. DefaultNTPServer = "time.cloudflare.com" diff --git a/pkg/machinery/labels/validate.go b/pkg/machinery/labels/validate.go index ab81e10966..eb8ec3f4a1 100644 --- a/pkg/machinery/labels/validate.go +++ b/pkg/machinery/labels/validate.go @@ -39,6 +39,38 @@ func Validate(labels map[string]string) error { return multiErr.ErrorOrNil() } +// TotalAnnotationSizeLimitB is the maximum size of all annotations in bytes. +const TotalAnnotationSizeLimitB int64 = 256 * (1 << 10) // 256 kB + +// ValidateAnnotations validates that a set of annotations are correctly defined. +func ValidateAnnotations(annotations map[string]string) error { + var multiErr *multierror.Error + + keys := maps.Keys(annotations) + slices.Sort(keys) + + var size int64 + + for _, k := range keys { + if err := ValidateQualifiedName(k); err != nil { + multiErr = multierror.Append(multiErr, err) + } + + switch k { + case constants.AnnotationOwnedAnnotations, constants.AnnotationOwnedLabels, constants.AnnotationOwnedTaints: + multiErr = multierror.Append(multiErr, fmt.Errorf("annotation %q is reserved", k)) + } + + size += int64(len(k)) + int64(len(annotations[k])) + } + + if size > TotalAnnotationSizeLimitB { + multiErr = multierror.Append(multiErr, fmt.Errorf("total annotation size exceeds limit of %d bytes", TotalAnnotationSizeLimitB)) + } + + return multiErr.ErrorOrNil() +} + const ( dns1123LabelFmt string = "[a-z0-9]([-a-z0-9]*[a-z0-9])?" dns1123SubdomainFmt string = dns1123LabelFmt + "(\\." + dns1123LabelFmt + ")*" diff --git a/pkg/machinery/labels/validate_test.go b/pkg/machinery/labels/validate_test.go index 2abeb63e39..9a4df77876 100644 --- a/pkg/machinery/labels/validate_test.go +++ b/pkg/machinery/labels/validate_test.go @@ -10,6 +10,7 @@ import ( "github.com/stretchr/testify/assert" + "github.com/siderolabs/talos/pkg/machinery/constants" "github.com/siderolabs/talos/pkg/machinery/labels" ) @@ -56,6 +57,47 @@ func TestValidate(t *testing.T) { } } +func TestValidateAnnotations(t *testing.T) { + for _, tt := range []struct { + name string + annotations map[string]string + + expectedError string + }{ + { + name: "empty", + }, + { + name: "valid", + annotations: map[string]string{ + "talos.dev/ann1": "sha256:e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + "foo": "bar", + "kubernetes.io/rack": "rack2", + }, + }, + { + name: "invalid", + annotations: map[string]string{ + "foo_": "bar", + "/foo": "bar", + "a/b/c": "bar", + "kubernetes.io/hostname": "hostname1_", + constants.AnnotationOwnedAnnotations: "a", + }, + expectedError: "4 errors occurred:\n\t* prefix cannot be empty: \"/foo\"\n\t* invalid format: too many slashes: \"a/b/c\"\n\t* name \"foo_\" is invalid\n\t* annotation \"talos.dev/owned-annotations\" is reserved\n\n", //nolint:lll + }, + } { + t.Run(tt.name, func(t *testing.T) { + err := labels.ValidateAnnotations(tt.annotations) + if tt.expectedError != "" { + assert.EqualError(t, err, tt.expectedError) + } else { + assert.NoError(t, err) + } + }) + } +} + func TestValidateTaints(t *testing.T) { for _, tt := range []struct { name string diff --git a/pkg/machinery/resources/k8s/deep_copy.generated.go b/pkg/machinery/resources/k8s/deep_copy.generated.go index 3b16add2b4..8e06b17214 100644 --- a/pkg/machinery/resources/k8s/deep_copy.generated.go +++ b/pkg/machinery/resources/k8s/deep_copy.generated.go @@ -2,7 +2,7 @@ // License, v. 2.0. If a copy of the MPL was not distributed with this // file, You can obtain one at http://mozilla.org/MPL/2.0/. -// Code generated by "deep-copy -type AdmissionControlConfigSpec -type APIServerConfigSpec -type AuditPolicyConfigSpec -type BootstrapManifestsConfigSpec -type ConfigStatusSpec -type ControllerManagerConfigSpec -type EndpointSpec -type ExtraManifestsConfigSpec -type KubeletLifecycleSpec -type KubePrismConfigSpec -type KubePrismEndpointsSpec -type KubePrismStatusesSpec -type KubeletSpecSpec -type ManifestSpec -type ManifestStatusSpec -type NodeCordonedSpecSpec -type NodeLabelSpecSpec -type NodeTaintSpecSpec -type KubeletConfigSpec -type NodeIPSpec -type NodeIPConfigSpec -type NodeStatusSpec -type NodenameSpec -type SchedulerConfigSpec -type SecretsStatusSpec -type StaticPodSpec -type StaticPodStatusSpec -type StaticPodServerStatusSpec -header-file ../../../../hack/boilerplate.txt -o deep_copy.generated.go ."; DO NOT EDIT. +// Code generated by "deep-copy -type AdmissionControlConfigSpec -type APIServerConfigSpec -type AuditPolicyConfigSpec -type BootstrapManifestsConfigSpec -type ConfigStatusSpec -type ControllerManagerConfigSpec -type EndpointSpec -type ExtraManifestsConfigSpec -type KubeletLifecycleSpec -type KubePrismConfigSpec -type KubePrismEndpointsSpec -type KubePrismStatusesSpec -type KubeletSpecSpec -type ManifestSpec -type ManifestStatusSpec -type NodeAnnotationSpecSpec -type NodeCordonedSpecSpec -type NodeLabelSpecSpec -type NodeTaintSpecSpec -type KubeletConfigSpec -type NodeIPSpec -type NodeIPConfigSpec -type NodeStatusSpec -type NodenameSpec -type SchedulerConfigSpec -type SecretsStatusSpec -type StaticPodSpec -type StaticPodStatusSpec -type StaticPodServerStatusSpec -header-file ../../../../hack/boilerplate.txt -o deep_copy.generated.go ."; DO NOT EDIT. package k8s @@ -278,6 +278,12 @@ func (o ManifestStatusSpec) DeepCopy() ManifestStatusSpec { return cp } +// DeepCopy generates a deep copy of NodeAnnotationSpecSpec. +func (o NodeAnnotationSpecSpec) DeepCopy() NodeAnnotationSpecSpec { + var cp NodeAnnotationSpecSpec = o + return cp +} + // DeepCopy generates a deep copy of NodeCordonedSpecSpec. func (o NodeCordonedSpecSpec) DeepCopy() NodeCordonedSpecSpec { var cp NodeCordonedSpecSpec = o diff --git a/pkg/machinery/resources/k8s/k8s.go b/pkg/machinery/resources/k8s/k8s.go index 9786d4fbec..a56578c2e6 100644 --- a/pkg/machinery/resources/k8s/k8s.go +++ b/pkg/machinery/resources/k8s/k8s.go @@ -7,7 +7,7 @@ package k8s import "github.com/cosi-project/runtime/pkg/resource" -//go:generate deep-copy -type AdmissionControlConfigSpec -type APIServerConfigSpec -type AuditPolicyConfigSpec -type BootstrapManifestsConfigSpec -type ConfigStatusSpec -type ControllerManagerConfigSpec -type EndpointSpec -type ExtraManifestsConfigSpec -type KubeletLifecycleSpec -type KubePrismConfigSpec -type KubePrismEndpointsSpec -type KubePrismStatusesSpec -type KubeletSpecSpec -type ManifestSpec -type ManifestStatusSpec -type NodeCordonedSpecSpec -type NodeLabelSpecSpec -type NodeTaintSpecSpec -type KubeletConfigSpec -type NodeIPSpec -type NodeIPConfigSpec -type NodeStatusSpec -type NodenameSpec -type SchedulerConfigSpec -type SecretsStatusSpec -type StaticPodSpec -type StaticPodStatusSpec -type StaticPodServerStatusSpec -header-file ../../../../hack/boilerplate.txt -o deep_copy.generated.go . +//go:generate deep-copy -type AdmissionControlConfigSpec -type APIServerConfigSpec -type AuditPolicyConfigSpec -type BootstrapManifestsConfigSpec -type ConfigStatusSpec -type ControllerManagerConfigSpec -type EndpointSpec -type ExtraManifestsConfigSpec -type KubeletLifecycleSpec -type KubePrismConfigSpec -type KubePrismEndpointsSpec -type KubePrismStatusesSpec -type KubeletSpecSpec -type ManifestSpec -type ManifestStatusSpec -type NodeAnnotationSpecSpec -type NodeCordonedSpecSpec -type NodeLabelSpecSpec -type NodeTaintSpecSpec -type KubeletConfigSpec -type NodeIPSpec -type NodeIPConfigSpec -type NodeStatusSpec -type NodenameSpec -type SchedulerConfigSpec -type SecretsStatusSpec -type StaticPodSpec -type StaticPodStatusSpec -type StaticPodServerStatusSpec -header-file ../../../../hack/boilerplate.txt -o deep_copy.generated.go . // NamespaceName contains resources supporting Kubernetes components on all node types. const NamespaceName resource.Namespace = "k8s" diff --git a/pkg/machinery/resources/k8s/k8s_test.go b/pkg/machinery/resources/k8s/k8s_test.go index 3435c557b1..24b36d65d4 100644 --- a/pkg/machinery/resources/k8s/k8s_test.go +++ b/pkg/machinery/resources/k8s/k8s_test.go @@ -44,6 +44,7 @@ func TestRegisterResource(t *testing.T) { &k8s.ManifestStatus{}, &k8s.Manifest{}, &k8s.BootstrapManifestsConfig{}, + &k8s.NodeAnnotationSpec{}, &k8s.NodeCordonedSpec{}, &k8s.NodeLabelSpec{}, &k8s.NodeTaintSpec{}, diff --git a/pkg/machinery/resources/k8s/node_annotation_spec.go b/pkg/machinery/resources/k8s/node_annotation_spec.go new file mode 100644 index 0000000000..2622e3d0f7 --- /dev/null +++ b/pkg/machinery/resources/k8s/node_annotation_spec.go @@ -0,0 +1,64 @@ +// This Source Code Form is subject to the terms of the Mozilla Public +// License, v. 2.0. If a copy of the MPL was not distributed with this +// file, You can obtain one at http://mozilla.org/MPL/2.0/. + +package k8s //nolint:dupl + +import ( + "github.com/cosi-project/runtime/pkg/resource" + "github.com/cosi-project/runtime/pkg/resource/meta" + "github.com/cosi-project/runtime/pkg/resource/protobuf" + "github.com/cosi-project/runtime/pkg/resource/typed" + + "github.com/siderolabs/talos/pkg/machinery/proto" +) + +// NodeAnnotationSpecType is the type. +const NodeAnnotationSpecType = resource.Type("NodeAnnotationSpecs.k8s.talos.dev") + +// NodeAnnotationSpecSpec represents an annoation that's attached to a Talos node. +// +//gotagsrewrite:gen +type NodeAnnotationSpecSpec struct { + Key string `yaml:"key" protobuf:"1"` + Value string `yaml:"value" protobuf:"2"` +} + +// NodeAnnotationSpec ... +type NodeAnnotationSpec = typed.Resource[NodeAnnotationSpecSpec, NodeAnnotationSpecExtension] + +// NewNodeAnnotationSpec initializes a NodeAnnotation resource. +func NewNodeAnnotationSpec(id resource.ID) *NodeAnnotationSpec { + return typed.NewResource[NodeAnnotationSpecSpec, NodeAnnotationSpecExtension]( + resource.NewMetadata(NamespaceName, NodeAnnotationSpecType, id, resource.VersionUndefined), + NodeAnnotationSpecSpec{}, + ) +} + +// NodeAnnotationSpecExtension provides auxiliary methods for NodeAnnotation. +type NodeAnnotationSpecExtension struct{} + +// ResourceDefinition implements meta.ResourceDefinitionProvider interface. +func (NodeAnnotationSpecExtension) ResourceDefinition() meta.ResourceDefinitionSpec { + return meta.ResourceDefinitionSpec{ + Type: NodeAnnotationSpecType, + Aliases: []resource.Type{}, + DefaultNamespace: NamespaceName, + Sensitivity: meta.Sensitive, + PrintColumns: []meta.PrintColumn{ + { + Name: "Value", + JSONPath: "{.value}", + }, + }, + } +} + +func init() { + proto.RegisterDefaultTypes() + + err := protobuf.RegisterDynamic[NodeAnnotationSpecSpec](NodeAnnotationSpecType, &NodeAnnotationSpec{}) + if err != nil { + panic(err) + } +} diff --git a/pkg/machinery/resources/k8s/node_label_spec.go b/pkg/machinery/resources/k8s/node_label_spec.go index 1385e9b3df..815cbb72ae 100644 --- a/pkg/machinery/resources/k8s/node_label_spec.go +++ b/pkg/machinery/resources/k8s/node_label_spec.go @@ -2,7 +2,7 @@ // License, v. 2.0. If a copy of the MPL was not distributed with this // file, You can obtain one at http://mozilla.org/MPL/2.0/. -package k8s +package k8s //nolint:dupl import ( "github.com/cosi-project/runtime/pkg/resource" diff --git a/website/content/v1.8/reference/api.md b/website/content/v1.8/reference/api.md index 11adf31c28..af9c588ea7 100644 --- a/website/content/v1.8/reference/api.md +++ b/website/content/v1.8/reference/api.md @@ -127,6 +127,7 @@ description: Talos gRPC API reference. - [KubeletSpecSpec](#talos.resource.definitions.k8s.KubeletSpecSpec) - [ManifestSpec](#talos.resource.definitions.k8s.ManifestSpec) - [ManifestStatusSpec](#talos.resource.definitions.k8s.ManifestStatusSpec) + - [NodeAnnotationSpecSpec](#talos.resource.definitions.k8s.NodeAnnotationSpecSpec) - [NodeIPConfigSpec](#talos.resource.definitions.k8s.NodeIPConfigSpec) - [NodeIPSpec](#talos.resource.definitions.k8s.NodeIPSpec) - [NodeLabelSpecSpec](#talos.resource.definitions.k8s.NodeLabelSpecSpec) @@ -2435,6 +2436,22 @@ ManifestStatusSpec describes manifest application status. + + +### NodeAnnotationSpecSpec +NodeAnnotationSpecSpec represents an annoation that's attached to a Talos node. + + +| Field | Type | Label | Description | +| ----- | ---- | ----- | ----------- | +| key | [string](#string) | | | +| value | [string](#string) | | | + + + + + + ### NodeIPConfigSpec diff --git a/website/content/v1.8/reference/configuration/v1alpha1/config.md b/website/content/v1.8/reference/configuration/v1alpha1/config.md index 51c74e1c87..076ba95620 100644 --- a/website/content/v1.8/reference/configuration/v1alpha1/config.md +++ b/website/content/v1.8/reference/configuration/v1alpha1/config.md @@ -422,6 +422,10 @@ seccompProfiles: nodeLabels: exampleLabel: exampleLabelValue {{< /highlight >}} | | +|`nodeAnnotations` |map[string]string |Configures the node annotations for the machine.
Show example(s){{< highlight yaml >}} +nodeAnnotations: + customer.io/rack: r13a25 +{{< /highlight >}}
| | |`nodeTaints` |map[string]string |
Configures the node taints for the machine. Effect is optional.
Note: In the default Kubernetes configuration, worker nodes are not allowed to
modify the taints (see [NodeRestriction](https://kubernetes.io/docs/reference/access-authn-authz/admission-controllers/#noderestriction) admission plugin).
Show example(s){{< highlight yaml >}} nodeTaints: exampleTaint: exampleTaintValue:NoSchedule diff --git a/website/content/v1.8/schemas/config.schema.json b/website/content/v1.8/schemas/config.schema.json index 09647474d1..86062b13eb 100644 --- a/website/content/v1.8/schemas/config.schema.json +++ b/website/content/v1.8/schemas/config.schema.json @@ -2637,6 +2637,18 @@ "markdownDescription": "Configures the node labels for the machine.\n\nNote: In the default Kubernetes configuration, worker nodes are restricted to set\nlabels with some prefixes (see [NodeRestriction](https://kubernetes.io/docs/reference/access-authn-authz/admission-controllers/#noderestriction) admission plugin).", "x-intellij-html-description": "\u003cp\u003eConfigures the node labels for the machine.\u003c/p\u003e\n\n\u003cp\u003eNote: In the default Kubernetes configuration, worker nodes are restricted to set\nlabels with some prefixes (see \u003ca href=\"https://kubernetes.io/docs/reference/access-authn-authz/admission-controllers/#noderestriction\" target=\"_blank\"\u003eNodeRestriction\u003c/a\u003e admission plugin).\u003c/p\u003e\n" }, + "nodeAnnotations": { + "patternProperties": { + ".*": { + "type": "string" + } + }, + "type": "object", + "title": "nodeAnnotations", + "description": "Configures the node annotations for the machine.\n", + "markdownDescription": "Configures the node annotations for the machine.", + "x-intellij-html-description": "\u003cp\u003eConfigures the node annotations for the machine.\u003c/p\u003e\n" + }, "nodeTaints": { "patternProperties": { ".*": { diff --git a/website/content/v1.8/talos-guides/configuration/editing-machine-configuration.md b/website/content/v1.8/talos-guides/configuration/editing-machine-configuration.md index 87920ff8e0..2d49866d01 100644 --- a/website/content/v1.8/talos-guides/configuration/editing-machine-configuration.md +++ b/website/content/v1.8/talos-guides/configuration/editing-machine-configuration.md @@ -39,7 +39,9 @@ The list of config changes allowed to be applied immediately in Talos {{< releas * `.machine.certCANs` * `.machine.install` (configuration is only applied during install/upgrade) * `.machine.network` +* `.machine.nodeAnnotations` * `.machine.nodeLabels` +* `.machine.nodeTaints` * `.machine.sysfs` * `.machine.sysctls` * `.machine.logging`