From af411ae61e02d7d599a45a57fdac7f631f733039 Mon Sep 17 00:00:00 2001 From: Moritz Sanft <58110325+msanft@users.noreply.github.com> Date: Wed, 22 May 2024 09:14:34 +0200 Subject: [PATCH] bootstrapper: don't fail when prioritization fails --- bootstrapper/internal/etcdio/etcdio.go | 16 ++++--- bootstrapper/internal/kubernetes/BUILD.bazel | 1 - .../internal/kubernetes/kubernetes.go | 18 ++----- .../internal/kubernetes/kubernetes_test.go | 48 +++++++++++++------ 4 files changed, 48 insertions(+), 35 deletions(-) diff --git a/bootstrapper/internal/etcdio/etcdio.go b/bootstrapper/internal/etcdio/etcdio.go index 23816f0d8..384e3997b 100644 --- a/bootstrapper/internal/etcdio/etcdio.go +++ b/bootstrapper/internal/etcdio/etcdio.go @@ -19,7 +19,9 @@ import ( ) var ( - ErrNoEtcdProcess = errors.New("no etcd process found on node") + // ErrNoEtcdProcess is returned when no etcd process is found on the node. + ErrNoEtcdProcess = errors.New("no etcd process found on node") + // ErrMultipleEtcdProcesses is returned when multiple etcd processes are found on the node. ErrMultipleEtcdProcesses = errors.New("multiple etcd processes found on node") ) @@ -38,18 +40,18 @@ const ( targetPrio = 0 // Highest priority within the class ) -// EtcdIOClient is a client for managing etcd I/O. -type EtcdIOClient struct { +// Client is a client for managing etcd I/O. +type Client struct { log *slog.Logger } // NewClient creates a new etcd I/O management client. -func NewClient(log *slog.Logger) *EtcdIOClient { - return &EtcdIOClient{log: log} +func NewClient(log *slog.Logger) *Client { + return &Client{log: log} } // PrioritizeIO tries to find the etcd process on the node and prioritizes its I/O. -func (c *EtcdIOClient) PrioritizeIO() error { +func (c *Client) PrioritizeIO() error { // find etcd process(es) pid, err := c.findEtcdProcess() if err != nil { @@ -70,7 +72,7 @@ func (c *EtcdIOClient) PrioritizeIO() error { } // findEtcdProcess tries to find the etcd process on the node. -func (c *EtcdIOClient) findEtcdProcess() (int, error) { +func (c *Client) findEtcdProcess() (int, error) { procDir, err := os.Open("/proc") if err != nil { return 0, fmt.Errorf("opening /proc: %w", err) diff --git a/bootstrapper/internal/kubernetes/BUILD.bazel b/bootstrapper/internal/kubernetes/BUILD.bazel index 86ef3966e..935c3fefd 100644 --- a/bootstrapper/internal/kubernetes/BUILD.bazel +++ b/bootstrapper/internal/kubernetes/BUILD.bazel @@ -31,7 +31,6 @@ go_test( srcs = ["kubernetes_test.go"], embed = [":kubernetes"], deps = [ - "//bootstrapper/internal/etcdio", "//bootstrapper/internal/kubernetes/k8sapi", "//bootstrapper/internal/kubernetes/kubewaiter", "//internal/cloud/metadata", diff --git a/bootstrapper/internal/kubernetes/kubernetes.go b/bootstrapper/internal/kubernetes/kubernetes.go index 1081bfe30..82ebfa00b 100644 --- a/bootstrapper/internal/kubernetes/kubernetes.go +++ b/bootstrapper/internal/kubernetes/kubernetes.go @@ -9,7 +9,6 @@ package kubernetes import ( "context" - "errors" "fmt" "log/slog" "net" @@ -154,7 +153,7 @@ func (k *KubeWrapper) InitCluster( k.log.Info("Prioritizing etcd I/O") if err := k.etcdIOPrioritizer.PrioritizeIO(); err != nil { - return nil, fmt.Errorf("prioritizing etcd I/O: %w", err) + k.log.Warn("Prioritizing etcd I/O failed", "error", err) } err = k.client.Initialize(kubeConfig) @@ -266,11 +265,8 @@ func (k *KubeWrapper) JoinCluster(ctx context.Context, args *kubeadm.BootstrapTo // If on control plane (and thus with etcd), try to prioritize etcd I/O. if peerRole == role.ControlPlane { k.log.Info("Prioritizing etcd I/O") - err = k.etcdIOPrioritizer.PrioritizeIO() - if errors.Is(err, etcdio.ErrNoEtcdProcess) { - k.log.Warn("No etcd process found, skipping I/O prioritization. Is this a single-node cluster?") - } else if err != nil { - return fmt.Errorf("prioritizing etcd I/O: %w", err) + if err := k.etcdIOPrioritizer.PrioritizeIO(); err != nil { + k.log.Warn("Prioritizing etcd I/O failed", "error", err) } } @@ -334,12 +330,8 @@ func (k *KubeWrapper) StartKubelet() error { } k.log.Info("Prioritizing etcd I/O") - err := k.etcdIOPrioritizer.PrioritizeIO() - if errors.Is(err, etcdio.ErrNoEtcdProcess) { - k.log.Warn("Skipping etcd I/O prioritization as etcd process is not running. " + - "This is expected if this node is a non-control-plane node.") - } else if err != nil { - return fmt.Errorf("prioritizing etcd I/O: %w", err) + if err := k.etcdIOPrioritizer.PrioritizeIO(); err != nil { + k.log.Warn("Prioritizing etcd I/O failed", "error", err) } return nil diff --git a/bootstrapper/internal/kubernetes/kubernetes_test.go b/bootstrapper/internal/kubernetes/kubernetes_test.go index a2d54bb5b..bc165452a 100644 --- a/bootstrapper/internal/kubernetes/kubernetes_test.go +++ b/bootstrapper/internal/kubernetes/kubernetes_test.go @@ -14,7 +14,6 @@ import ( "strconv" "testing" - "github.com/edgelesssys/constellation/v2/bootstrapper/internal/etcdio" "github.com/edgelesssys/constellation/v2/bootstrapper/internal/kubernetes/k8sapi" "github.com/edgelesssys/constellation/v2/bootstrapper/internal/kubernetes/kubewaiter" "github.com/edgelesssys/constellation/v2/internal/cloud/metadata" @@ -182,13 +181,40 @@ func TestInitCluster(t *testing.T) { k8sVersion: "1.19", wantErr: true, }, - "etcd prioritizer fails on error": { + "etcd prioritizer doesn't fail on error": { clusterUtil: stubClusterUtil{kubeconfig: []byte("someKubeconfig")}, kubeAPIWaiter: stubKubeAPIWaiter{}, etcdIOPrioritizer: stubEtcdIOPrioritizer{assert.AnError}, - providerMetadata: &stubProviderMetadata{}, - k8sVersion: versions.Default, - wantErr: true, + providerMetadata: &stubProviderMetadata{ + selfResp: metadata.InstanceMetadata{ + Name: nodeName, + ProviderID: providerID, + VPCIP: privateIP, + AliasIPRanges: []string{aliasIPRange}, + }, + getLoadBalancerHostResp: loadbalancerIP, + getLoadBalancerPortResp: strconv.Itoa(constants.KubernetesPort), + }, + wantConfig: k8sapi.KubeadmInitYAML{ + InitConfiguration: kubeadm.InitConfiguration{ + NodeRegistration: kubeadm.NodeRegistrationOptions{ + KubeletExtraArgs: map[string]string{ + "node-ip": privateIP, + "provider-id": providerID, + }, + Name: nodeName, + }, + }, + ClusterConfiguration: kubeadm.ClusterConfiguration{ + ClusterName: "kubernetes", + ControlPlaneEndpoint: loadbalancerIP, + APIServer: kubeadm.APIServer{ + CertSANs: []string{privateIP}, + }, + }, + }, + wantErr: false, + k8sVersion: versions.Default, }, } @@ -377,16 +403,9 @@ func TestJoinCluster(t *testing.T) { role: role.Worker, wantErr: true, }, - "etcd prioritizer error fails": { + "etcd prioritizer error doesn't fail": { clusterUtil: stubClusterUtil{}, etcdIOPrioritizer: stubEtcdIOPrioritizer{assert.AnError}, - providerMetadata: &stubProviderMetadata{}, - role: role.Worker, - wantErr: true, - }, - "etcd prioritizer doesn't fail on worker": { - clusterUtil: stubClusterUtil{}, - etcdIOPrioritizer: stubEtcdIOPrioritizer{etcdio.ErrNoEtcdProcess}, providerMetadata: &stubProviderMetadata{ selfResp: metadata.InstanceMetadata{ ProviderID: "provider-id", @@ -394,7 +413,8 @@ func TestJoinCluster(t *testing.T) { VPCIP: "192.0.2.1", }, }, - role: role.Worker, + k8sComponents: k8sComponents, + role: role.Worker, wantConfig: kubeadm.JoinConfiguration{ Discovery: kubeadm.Discovery{ BootstrapToken: joinCommand,