const RevisionAnnotation … const RevisionHistoryAnnotation … const DesiredReplicasAnnotation … const MaxReplicasAnnotation … const RollbackRevisionNotFound … const RollbackTemplateUnchanged … const RollbackDone … const ReplicaSetUpdatedReason … const FailedRSCreateReason … const NewReplicaSetReason … const FoundNewRSReason … const NewRSAvailableReason … const TimedOutReason … const PausedDeployReason … const ResumedDeployReason … const MinimumReplicasAvailable … const MinimumReplicasUnavailable … // NewDeploymentCondition creates a new deployment condition. func NewDeploymentCondition(condType apps.DeploymentConditionType, status v1.ConditionStatus, reason, message string) *apps.DeploymentCondition { … } // GetDeploymentCondition returns the condition with the provided type. func GetDeploymentCondition(status apps.DeploymentStatus, condType apps.DeploymentConditionType) *apps.DeploymentCondition { … } // SetDeploymentCondition updates the deployment to include the provided condition. If the condition that // we are about to add already exists and has the same status and reason then we are not going to update. func SetDeploymentCondition(status *apps.DeploymentStatus, condition apps.DeploymentCondition) { … } // RemoveDeploymentCondition removes the deployment condition with the provided type. func RemoveDeploymentCondition(status *apps.DeploymentStatus, condType apps.DeploymentConditionType) { … } // filterOutCondition returns a new slice of deployment conditions without conditions with the provided type. func filterOutCondition(conditions []apps.DeploymentCondition, condType apps.DeploymentConditionType) []apps.DeploymentCondition { … } // ReplicaSetToDeploymentCondition converts a replica set condition into a deployment condition. // Useful for promoting replica set failure conditions into deployments. func ReplicaSetToDeploymentCondition(cond apps.ReplicaSetCondition) apps.DeploymentCondition { … } // SetDeploymentRevision updates the revision for a deployment. func SetDeploymentRevision(deployment *apps.Deployment, revision string) bool { … } // MaxRevision finds the highest revision in the replica sets func MaxRevision(logger klog.Logger, allRSs []*apps.ReplicaSet) int64 { … } // LastRevision finds the second max revision number in all replica sets (the last revision) func LastRevision(logger klog.Logger, allRSs []*apps.ReplicaSet) int64 { … } // Revision returns the revision number of the input object. func Revision(obj runtime.Object) (int64, error) { … } // SetNewReplicaSetAnnotations sets new replica set's annotations appropriately by updating its revision and // copying required deployment annotations to it; it returns true if replica set's annotation is changed. func SetNewReplicaSetAnnotations(ctx context.Context, deployment *apps.Deployment, newRS *apps.ReplicaSet, newRevision string, exists bool, revHistoryLimitInChars int) bool { … } var annotationsToSkip … // skipCopyAnnotation returns true if we should skip copying the annotation with the given annotation key // TODO: How to decide which annotations should / should not be copied? // // See https://github.com/kubernetes/kubernetes/pull/20035#issuecomment-179558615 func skipCopyAnnotation(key string) bool { … } // copyDeploymentAnnotationsToReplicaSet copies deployment's annotations to replica set's annotations, // and returns true if replica set's annotation is changed. // Note that apply and revision annotations are not copied. func copyDeploymentAnnotationsToReplicaSet(deployment *apps.Deployment, rs *apps.ReplicaSet) bool { … } // SetDeploymentAnnotationsTo sets deployment's annotations as given RS's annotations. // This action should be done if and only if the deployment is rolling back to this rs. // Note that apply and revision annotations are not changed. func SetDeploymentAnnotationsTo(deployment *apps.Deployment, rollbackToRS *apps.ReplicaSet) { … } func getSkippedAnnotations(annotations map[string]string) map[string]string { … } // FindActiveOrLatest returns the only active or the latest replica set in case there is at most one active // replica set. If there are more active replica sets, then we should proportionally scale them. func FindActiveOrLatest(newRS *apps.ReplicaSet, oldRSs []*apps.ReplicaSet) *apps.ReplicaSet { … } // GetDesiredReplicasAnnotation returns the number of desired replicas func GetDesiredReplicasAnnotation(logger klog.Logger, rs *apps.ReplicaSet) (int32, bool) { … } func getMaxReplicasAnnotation(logger klog.Logger, rs *apps.ReplicaSet) (int32, bool) { … } func getIntFromAnnotation(logger klog.Logger, rs *apps.ReplicaSet, annotationKey string) (int32, bool) { … } // SetReplicasAnnotations sets the desiredReplicas and maxReplicas into the annotations func SetReplicasAnnotations(rs *apps.ReplicaSet, desiredReplicas, maxReplicas int32) bool { … } // ReplicasAnnotationsNeedUpdate return true if ReplicasAnnotations need to be updated func ReplicasAnnotationsNeedUpdate(rs *apps.ReplicaSet, desiredReplicas, maxReplicas int32) bool { … } // MaxUnavailable returns the maximum unavailable pods a rolling deployment can take. func MaxUnavailable(deployment apps.Deployment) int32 { … } // MinAvailable returns the minimum available pods of a given deployment func MinAvailable(deployment *apps.Deployment) int32 { … } // MaxSurge returns the maximum surge pods a rolling deployment can take. func MaxSurge(deployment apps.Deployment) int32 { … } // GetProportion will estimate the proportion for the provided replica set using 1. the current size // of the parent deployment, 2. the replica count that needs be added on the replica sets of the // deployment, and 3. the total replicas added in the replica sets of the deployment so far. func GetProportion(logger klog.Logger, rs *apps.ReplicaSet, d apps.Deployment, deploymentReplicasToAdd, deploymentReplicasAdded int32) int32 { … } // getReplicaSetFraction estimates the fraction of replicas a replica set can have in // 1. a scaling event during a rollout or 2. when scaling a paused deployment. func getReplicaSetFraction(logger klog.Logger, rs apps.ReplicaSet, d apps.Deployment) int32 { … } // RsListFromClient returns an rsListFunc that wraps the given client. func RsListFromClient(c appsclient.AppsV1Interface) RsListFunc { … } type RsListFunc … type podListFunc … // ListReplicaSets returns a slice of RSes the given deployment targets. // Note that this does NOT attempt to reconcile ControllerRef (adopt/orphan), // because only the controller itself should do that. // However, it does filter out anything whose ControllerRef doesn't match. func ListReplicaSets(deployment *apps.Deployment, getRSList RsListFunc) ([]*apps.ReplicaSet, error) { … } // ListPods returns a list of pods the given deployment targets. // This needs a list of ReplicaSets for the Deployment, // which can be found with ListReplicaSets(). // Note that this does NOT attempt to reconcile ControllerRef (adopt/orphan), // because only the controller itself should do that. // However, it does filter out anything whose ControllerRef doesn't match. func ListPods(deployment *apps.Deployment, rsList []*apps.ReplicaSet, getPodList podListFunc) (*v1.PodList, error) { … } // EqualIgnoreHash returns true if two given podTemplateSpec are equal, ignoring the diff in value of Labels[pod-template-hash] // We ignore pod-template-hash because: // 1. The hash result would be different upon podTemplateSpec API changes // (e.g. the addition of a new field will cause the hash code to change) // 2. The deployment template won't have hash labels func EqualIgnoreHash(template1, template2 *v1.PodTemplateSpec) bool { … } // FindNewReplicaSet returns the new RS this given deployment targets (the one with the same pod template). func FindNewReplicaSet(deployment *apps.Deployment, rsList []*apps.ReplicaSet) *apps.ReplicaSet { … } // FindOldReplicaSets returns the old replica sets targeted by the given Deployment, with the given slice of RSes. // Note that the first set of old replica sets doesn't include the ones with no pods, and the second set of old replica sets include all old replica sets. func FindOldReplicaSets(deployment *apps.Deployment, rsList []*apps.ReplicaSet) ([]*apps.ReplicaSet, []*apps.ReplicaSet) { … } // SetFromReplicaSetTemplate sets the desired PodTemplateSpec from a replica set template to the given deployment. func SetFromReplicaSetTemplate(deployment *apps.Deployment, template v1.PodTemplateSpec) *apps.Deployment { … } // GetReplicaCountForReplicaSets returns the sum of Replicas of the given replica sets. func GetReplicaCountForReplicaSets(replicaSets []*apps.ReplicaSet) int32 { … } // GetActualReplicaCountForReplicaSets returns the sum of actual replicas of the given replica sets. func GetActualReplicaCountForReplicaSets(replicaSets []*apps.ReplicaSet) int32 { … } // GetReadyReplicaCountForReplicaSets returns the number of ready pods corresponding to the given replica sets. func GetReadyReplicaCountForReplicaSets(replicaSets []*apps.ReplicaSet) int32 { … } // GetAvailableReplicaCountForReplicaSets returns the number of available pods corresponding to the given replica sets. func GetAvailableReplicaCountForReplicaSets(replicaSets []*apps.ReplicaSet) int32 { … } // IsRollingUpdate returns true if the strategy type is a rolling update. func IsRollingUpdate(deployment *apps.Deployment) bool { … } // DeploymentComplete considers a deployment to be complete once all of its desired replicas // are updated and available, and no old pods are running. func DeploymentComplete(deployment *apps.Deployment, newStatus *apps.DeploymentStatus) bool { … } // DeploymentProgressing reports progress for a deployment. Progress is estimated by comparing the // current with the new status of the deployment that the controller is observing. More specifically, // when new pods are scaled up or become ready or available, or old pods are scaled down, then we // consider the deployment is progressing. func DeploymentProgressing(deployment *apps.Deployment, newStatus *apps.DeploymentStatus) bool { … } var nowFn … // DeploymentTimedOut considers a deployment to have timed out once its condition that reports progress // is older than progressDeadlineSeconds or a Progressing condition with a TimedOutReason reason already // exists. func DeploymentTimedOut(ctx context.Context, deployment *apps.Deployment, newStatus *apps.DeploymentStatus) bool { … } // NewRSNewReplicas calculates the number of replicas a deployment's new RS should have. // When one of the followings is true, we're rolling out the deployment; otherwise, we're scaling it. // 1) The new RS is saturated: newRS's replicas == deployment's replicas // 2) Max number of pods allowed is reached: deployment's replicas + maxSurge == all RSs' replicas func NewRSNewReplicas(deployment *apps.Deployment, allRSs []*apps.ReplicaSet, newRS *apps.ReplicaSet) (int32, error) { … } // IsSaturated checks if the new replica set is saturated by comparing its size with its deployment size. // Both the deployment and the replica set have to believe this replica set can own all of the desired // replicas in the deployment and the annotation helps in achieving that. All pods of the ReplicaSet // need to be available. func IsSaturated(deployment *apps.Deployment, rs *apps.ReplicaSet) bool { … } // WaitForObservedDeployment polls for deployment to be updated so that deployment.Status.ObservedGeneration >= desiredGeneration. // Returns error if polling timesout. func WaitForObservedDeployment(getDeploymentFunc func() (*apps.Deployment, error), desiredGeneration int64, interval, timeout time.Duration) error { … } // ResolveFenceposts resolves both maxSurge and maxUnavailable. This needs to happen in one // step. For example: // // 2 desired, max unavailable 1%, surge 0% - should scale old(-1), then new(+1), then old(-1), then new(+1) // 1 desired, max unavailable 1%, surge 0% - should scale old(-1), then new(+1) // 2 desired, max unavailable 25%, surge 1% - should scale new(+1), then old(-1), then new(+1), then old(-1) // 1 desired, max unavailable 25%, surge 1% - should scale new(+1), then old(-1) // 2 desired, max unavailable 0%, surge 1% - should scale new(+1), then old(-1), then new(+1), then old(-1) // 1 desired, max unavailable 0%, surge 1% - should scale new(+1), then old(-1) func ResolveFenceposts(maxSurge, maxUnavailable *intstrutil.IntOrString, desired int32) (int32, int32, error) { … } // HasProgressDeadline checks if the Deployment d is expected to surface the reason // "ProgressDeadlineExceeded" when the Deployment progress takes longer than expected time. func HasProgressDeadline(d *apps.Deployment) bool { … } // HasRevisionHistoryLimit checks if the Deployment d is expected to keep a specified number of // old replicaSets. These replicaSets are mainly kept with the purpose of rollback. // The RevisionHistoryLimit can start from 0 (no retained replicasSet). When set to math.MaxInt32, // the Deployment will keep all revisions. func HasRevisionHistoryLimit(d *apps.Deployment) bool { … } // GetDeploymentsForReplicaSet returns a list of Deployments that potentially // match a ReplicaSet. Only the one specified in the ReplicaSet's ControllerRef // will actually manage it. // Returns an error only if no matching Deployments are found. func GetDeploymentsForReplicaSet(deploymentLister appslisters.DeploymentLister, rs *apps.ReplicaSet) ([]*apps.Deployment, error) { … } type ReplicaSetsByRevision … func (o ReplicaSetsByRevision) Len() int { … } func (o ReplicaSetsByRevision) Swap(i, j int) { … } func (o ReplicaSetsByRevision) Less(i, j int) bool { … }