diff --git a/app/models/miq_server/worker_management/kubernetes.rb b/app/models/miq_server/worker_management/kubernetes.rb index 85b2ee88e8b..4a87de6822b 100644 --- a/app/models/miq_server/worker_management/kubernetes.rb +++ b/app/models/miq_server/worker_management/kubernetes.rb @@ -25,10 +25,7 @@ def sync_starting_workers worker_pod = current_pods[worker.system_uid] next if worker_pod.nil? - container_status = worker_pod.status.containerStatuses.find { |container| container.name == worker.worker_deployment_name } - if worker_pod.status.phase == "Running" && container_status.ready && container_status.started - worker.update!(:status => "started") - end + worker.update!(:status => "started") if worker_pod[:running] end end @@ -253,6 +250,7 @@ def save_pod(pod) ch[:label_name] = pod.metadata.labels.name ch[:last_state_terminated] = pod.status.containerStatuses.any? { |cs| cs.lastState.terminated } ch[:container_restarts] = pod.status.containerStatuses.sum { |cs| cs.restartCount.to_i } + ch[:running] = pod.status.phase == "Running" && pod.status.containerStatuses.all? { |cs| cs.ready && cs.started } name = pod.metadata.name current_pods[name] ||= ch diff --git a/spec/models/miq_server/worker_management/kubernetes_spec.rb b/spec/models/miq_server/worker_management/kubernetes_spec.rb index 02f450e1406..f6532587722 100644 --- a/spec/models/miq_server/worker_management/kubernetes_spec.rb +++ b/spec/models/miq_server/worker_management/kubernetes_spec.rb @@ -118,6 +118,88 @@ end end + context "#save_pod (private)" do + it "saves the deployment in #current_deployments" do + require 'kubeclient/resource' + + deployment = Kubeclient::Resource.new( + :metadata => { + :name => "1-automation", + :namespace => "manageiq", + :uid => "3f4aeff1-e1a5-45bf-8221-2627bfff38c6", + :resourceVersion => "1557249", + :generation => 2, + :creationTimestamp => "2024-07-29T19:50:23Z", + :labels => {:app => "manageiq", :"manageiq-orchestrated-by" => "orchestrator-5474db46d9-rfjmn"}, + :annotations => {:"deployment.kubernetes.io/revision" => "1"} + }, + :spec => {:replicas => 1, :selector => {:matchLabels => {:name => "1-automation"}}}, + :status => {:observedGeneration => 2, :replicas => 1, :updatedReplicas => 1, :readyReplicas => 1, :availableReplicas => 1} + ) + + server.worker_manager.send(:save_deployment, deployment) + + expect(server.worker_manager.current_deployments).to have_key("1-automation") + expect(server.worker_manager.current_deployments["1-automation"]).to include(:spec => deployment.spec.to_h) + end + end + + context "#save_deployment (private)" do + let(:phase) { "Running" } + let(:ready) { true } + let(:started) { true } + let(:restart_count) { 0 } + let(:last_state) { {} } + let(:pod) do + require 'kubeclient/resource' + Kubeclient::Resource.new( + :metadata => {:name => "1-automation-545fbd845-s2pjt", :labels => {:app => "manageiq", :"manageiq-orchestrated-by" => "orchestrator-5474db46d9-rfjmn", :name => "1-automation", :"pod-template-hash" => "545fbd845"}}, + :spec => {}, + :status => {:phase => phase, :containerStatuses => [{:name => "1-automation", :state => {:running => {:startedAt => "2024-07-29T19:50:25Z"}}, :lastState => last_state, :ready => ready, :restartCount => restart_count, :started => started}]} + ) + end + + it "saves the pod in #current_pods" do + server.worker_manager.send(:save_pod, pod) + + expect(server.worker_manager.current_pods).to have_key("1-automation-545fbd845-s2pjt") + expect(server.worker_manager.current_pods["1-automation-545fbd845-s2pjt"]).to include(:label_name => "1-automation", :last_state_terminated => false, :container_restarts => 0, :running => true) + end + + context "with a pod that is not running" do + let(:phase) { "ContainerCreating" } + + it "marks the pod as not running" do + server.worker_manager.send(:save_pod, pod) + + expect(server.worker_manager.current_pods).to have_key("1-automation-545fbd845-s2pjt") + expect(server.worker_manager.current_pods["1-automation-545fbd845-s2pjt"]).to include(:running => false) + end + end + + context "with a pod that has a restart count" do + let(:restart_count) { 2 } + + it "sets container_restarts" do + server.worker_manager.send(:save_pod, pod) + + expect(server.worker_manager.current_pods).to have_key("1-automation-545fbd845-s2pjt") + expect(server.worker_manager.current_pods["1-automation-545fbd845-s2pjt"]).to include(:container_restarts => 2) + end + end + + context "with a lastState of terminated" do + let(:last_state) { {:terminated => true} } + + it "sets last_state_terminated to true" do + server.worker_manager.send(:save_pod, pod) + + expect(server.worker_manager.current_pods).to have_key("1-automation-545fbd845-s2pjt") + expect(server.worker_manager.current_pods["1-automation-545fbd845-s2pjt"]).to include(:last_state_terminated => true) + end + end + end + context "#sync_from_system" do context "#ensure_kube_monitors_started" do it "podified, ensures pod monitor started and orphaned rows are removed" do @@ -210,7 +292,7 @@ metadata = double(:name => deployment_name, :labels => double(:name => pod_label)) state = double(:running => double(:startedAt => started_at)) last_state = double(:terminated => nil) - status = double(:containerStatuses => [double(:state => state, :lastState => last_state, :restartCount => 0)]) + status = double(:phase => "Running", :containerStatuses => [double(:state => state, :ready => true, :started => true, :lastState => last_state, :restartCount => 0)]) pods = [double(:metadata => metadata, :status => status)] allow(pods).to receive(:resourceVersion).and_return(resource_version) pods