func deploymentReachedCompletion(dc *deployapi.DeploymentConfig, rcs []kapi.ReplicationController, pods []kapi.Pod) (bool, error) { if len(rcs) == 0 { return false, nil } rc := rcs[len(rcs)-1] version := deployutil.DeploymentVersionFor(&rc) if version != dc.Status.LatestVersion { return false, nil } if !deployutil.IsCompleteDeployment(&rc) { return false, nil } cond := deployutil.GetDeploymentCondition(dc.Status, deployapi.DeploymentProgressing) if cond == nil || cond.Reason != deployutil.NewRcAvailableReason { return false, nil } expectedReplicas := dc.Spec.Replicas if dc.Spec.Test { expectedReplicas = 0 } if rc.Spec.Replicas != int32(expectedReplicas) { return false, fmt.Errorf("deployment is complete but doesn't have expected spec replicas: %d %d", rc.Spec.Replicas, expectedReplicas) } if rc.Status.Replicas != int32(expectedReplicas) { e2e.Logf("POSSIBLE_ANOMALY: deployment is complete but doesn't have expected status replicas: %d %d", rc.Status.Replicas, expectedReplicas) return false, nil } e2e.Logf("Latest rollout of dc/%s (rc/%s) is complete.", dc.Name, rc.Name) return true, nil }
func updateConditions(config *deployapi.DeploymentConfig, newStatus *deployapi.DeploymentConfigStatus, latestRC *kapi.ReplicationController) { // Availability condition. if newStatus.AvailableReplicas >= config.Spec.Replicas-deployutil.MaxUnavailable(*config) { minAvailability := deployutil.NewDeploymentCondition(deployapi.DeploymentAvailable, kapi.ConditionTrue, "", "Deployment config has minimum availability.") deployutil.SetDeploymentCondition(newStatus, *minAvailability) } else { noMinAvailability := deployutil.NewDeploymentCondition(deployapi.DeploymentAvailable, kapi.ConditionFalse, "", "Deployment config does not have minimum availability.") deployutil.SetDeploymentCondition(newStatus, *noMinAvailability) } // Condition about progress. cond := deployutil.GetDeploymentCondition(*newStatus, deployapi.DeploymentProgressing) if latestRC != nil { switch deployutil.DeploymentStatusFor(latestRC) { case deployapi.DeploymentStatusNew, deployapi.DeploymentStatusPending: msg := fmt.Sprintf("Waiting on deployer pod for %q to be scheduled", latestRC.Name) condition := deployutil.NewDeploymentCondition(deployapi.DeploymentProgressing, kapi.ConditionUnknown, "", msg) deployutil.SetDeploymentCondition(newStatus, *condition) case deployapi.DeploymentStatusRunning: msg := fmt.Sprintf("Replication controller %q is progressing", latestRC.Name) condition := deployutil.NewDeploymentCondition(deployapi.DeploymentProgressing, kapi.ConditionTrue, deployutil.ReplicationControllerUpdatedReason, msg) deployutil.SetDeploymentCondition(newStatus, *condition) case deployapi.DeploymentStatusFailed: if cond != nil && cond.Reason == deployutil.TimedOutReason { break } msg := fmt.Sprintf("Replication controller %q has failed progressing", latestRC.Name) condition := deployutil.NewDeploymentCondition(deployapi.DeploymentProgressing, kapi.ConditionFalse, deployutil.TimedOutReason, msg) deployutil.SetDeploymentCondition(newStatus, *condition) case deployapi.DeploymentStatusComplete: if cond != nil && cond.Reason == deployutil.NewRcAvailableReason { break } msg := fmt.Sprintf("Replication controller %q has completed progressing", latestRC.Name) condition := deployutil.NewDeploymentCondition(deployapi.DeploymentProgressing, kapi.ConditionTrue, deployutil.NewRcAvailableReason, msg) deployutil.SetDeploymentCondition(newStatus, *condition) } } // Pause / resume condition. Since we don't pause running deployments, let's use paused conditions only when a deployment // actually terminates. For now it may be ok to override lack of progress in the conditions, later we may want to separate // paused from the rest of the progressing conditions. if latestRC == nil || deployutil.IsTerminatedDeployment(latestRC) { pausedCondExists := cond != nil && cond.Reason == deployutil.PausedDeployReason if config.Spec.Paused && !pausedCondExists { condition := deployutil.NewDeploymentCondition(deployapi.DeploymentProgressing, kapi.ConditionUnknown, deployutil.PausedDeployReason, "Deployment config is paused") deployutil.SetDeploymentCondition(newStatus, *condition) } else if !config.Spec.Paused && pausedCondExists { condition := deployutil.NewDeploymentCondition(deployapi.DeploymentProgressing, kapi.ConditionUnknown, deployutil.ResumedDeployReason, "Deployment config is resumed") deployutil.SetDeploymentCondition(newStatus, *condition) } } }
func deploymentFailed(dc *deployapi.DeploymentConfig, rcs []kapi.ReplicationController, _ []kapi.Pod) (bool, error) { if len(rcs) == 0 { return false, nil } rc := rcs[len(rcs)-1] version := deployutil.DeploymentVersionFor(&rc) if version != dc.Status.LatestVersion { return false, nil } if !deployutil.IsFailedDeployment(&rc) { return false, nil } cond := deployutil.GetDeploymentCondition(dc.Status, deployapi.DeploymentProgressing) return cond != nil && cond.Reason == deployutil.TimedOutReason, nil }
// Status returns a message describing deployment status, and a bool value indicating if the status is considered done func (s *DeploymentConfigStatusViewer) Status(namespace, name string, desiredRevision int64) (string, bool, error) { config, err := s.dn.DeploymentConfigs(namespace).Get(name) if err != nil { return "", false, err } latestRevision := config.Status.LatestVersion if latestRevision == 0 { switch { case deployutil.HasImageChangeTrigger(config): return fmt.Sprintf("Deployment config %q waiting on image update\n", name), false, nil case len(config.Spec.Triggers) == 0: return "", true, fmt.Errorf("Deployment config %q waiting on manual update (use 'oc rollout latest %s')", name, name) } } if desiredRevision > 0 && latestRevision != desiredRevision { return "", false, fmt.Errorf("desired revision (%d) is different from the running revision (%d)", desiredRevision, latestRevision) } cond := deployutil.GetDeploymentCondition(config.Status, deployapi.DeploymentProgressing) if config.Generation <= config.Status.ObservedGeneration { switch { case cond != nil && cond.Reason == deployutil.NewRcAvailableReason: return fmt.Sprintf("%s\n", cond.Message), true, nil case cond != nil && cond.Reason == deployutil.TimedOutReason: return "", true, errors.New(cond.Message) case cond != nil && cond.Reason == deployutil.PausedDeployReason: return "", true, fmt.Errorf("Deployment config %q is paused. Resume to continue watching the status of the rollout.\n", config.Name) case config.Status.UpdatedReplicas < config.Spec.Replicas: return fmt.Sprintf("Waiting for rollout to finish: %d out of %d new replicas have been updated...\n", config.Status.UpdatedReplicas, config.Spec.Replicas), false, nil case config.Status.Replicas > config.Status.UpdatedReplicas: return fmt.Sprintf("Waiting for rollout to finish: %d old replicas are pending termination...\n", config.Status.Replicas-config.Status.UpdatedReplicas), false, nil case config.Status.AvailableReplicas < config.Status.UpdatedReplicas: return fmt.Sprintf("Waiting for rollout to finish: %d of %d updated replicas are available...\n", config.Status.AvailableReplicas, config.Status.UpdatedReplicas), false, nil } } return fmt.Sprintf("Waiting for latest deployment config spec to be observed by the controller loop...\n"), false, nil }
err = wait.PollImmediate(500*time.Millisecond, 30*time.Second, func() (bool, error) { dc, _, _, err := deploymentInfo(oc, name) if err != nil { return false, nil } return dc.Status.LatestVersion == 1, nil }) if err == wait.ErrWaitTimeout { err = fmt.Errorf("deployment config %q never incremented to the first version", name) } o.Expect(err).NotTo(o.HaveOccurred()) g.By("verifying that the deployment config has the desired condition and reason") var conditions []deployapi.DeploymentCondition err = wait.PollImmediate(500*time.Millisecond, 30*time.Second, func() (bool, error) { dc, _, _, err := deploymentInfo(oc, name) if err != nil { return false, nil } conditions = dc.Status.Conditions cond := deployutil.GetDeploymentCondition(dc.Status, deployapi.DeploymentProgressing) return cond != nil && cond.Reason == deployutil.NewReplicationControllerReason, nil }) if err == wait.ErrWaitTimeout { err = fmt.Errorf("deployment config %q never updated its conditions: %#v", name, conditions) } o.Expect(err).NotTo(o.HaveOccurred()) }) }) })