mirror of
https://github.com/k3s-io/kubernetes.git
synced 2025-07-23 11:50:44 +00:00
First part of improved rolling update, allow dynamic next replication controller generation.
This commit is contained in:
parent
e8b28c59c6
commit
217e6ff0d0
@ -405,11 +405,20 @@ _kubectl_rolling-update()
|
|||||||
flags_with_completion=()
|
flags_with_completion=()
|
||||||
flags_completion=()
|
flags_completion=()
|
||||||
|
|
||||||
|
flags+=("--deployment-label-key=")
|
||||||
|
flags+=("--dry-run")
|
||||||
flags+=("--filename=")
|
flags+=("--filename=")
|
||||||
two_word_flags+=("-f")
|
two_word_flags+=("-f")
|
||||||
flags+=("--help")
|
flags+=("--help")
|
||||||
flags+=("-h")
|
flags+=("-h")
|
||||||
|
flags+=("--image=")
|
||||||
|
flags+=("--no-headers")
|
||||||
|
flags+=("--output=")
|
||||||
|
two_word_flags+=("-o")
|
||||||
|
flags+=("--output-version=")
|
||||||
flags+=("--poll-interval=")
|
flags+=("--poll-interval=")
|
||||||
|
flags+=("--template=")
|
||||||
|
two_word_flags+=("-t")
|
||||||
flags+=("--timeout=")
|
flags+=("--timeout=")
|
||||||
flags+=("--update-period=")
|
flags+=("--update-period=")
|
||||||
|
|
||||||
|
@ -66,4 +66,4 @@ kubectl
|
|||||||
* [kubectl update](kubectl_update.md) - Update a resource by filename or stdin.
|
* [kubectl update](kubectl_update.md) - Update a resource by filename or stdin.
|
||||||
* [kubectl version](kubectl_version.md) - Print the client and server version information.
|
* [kubectl version](kubectl_version.md) - Print the client and server version information.
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.406236586 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.641615471 +0000 UTC
|
||||||
|
@ -50,4 +50,4 @@ kubectl api-versions
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.405815046 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.640579424 +0000 UTC
|
||||||
|
@ -50,4 +50,4 @@ kubectl cluster-info
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.405639667 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.640382538 +0000 UTC
|
||||||
|
@ -63,4 +63,4 @@ kubectl config SUBCOMMAND
|
|||||||
* [kubectl config use-context](kubectl_config_use-context.md) - Sets the current-context in a kubeconfig file
|
* [kubectl config use-context](kubectl_config_use-context.md) - Sets the current-context in a kubeconfig file
|
||||||
* [kubectl config view](kubectl_config_view.md) - displays Merged kubeconfig settings or a specified kubeconfig file.
|
* [kubectl config view](kubectl_config_view.md) - displays Merged kubeconfig settings or a specified kubeconfig file.
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.405466384 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.640154327 +0000 UTC
|
||||||
|
@ -65,4 +65,4 @@ $ kubectl config set-cluster e2e --insecure-skip-tls-verify=true
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.404357726 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.638291301 +0000 UTC
|
||||||
|
@ -58,4 +58,4 @@ $ kubectl config set-context gce --user=cluster-admin
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.40472172 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.638842283 +0000 UTC
|
||||||
|
@ -78,4 +78,4 @@ $ kubectl set-credentials cluster-admin --client-certificate=~/.kube/admin.crt -
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.40454463 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.638596132 +0000 UTC
|
||||||
|
@ -52,4 +52,4 @@ kubectl config set PROPERTY_NAME PROPERTY_VALUE
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.404916515 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.639475859 +0000 UTC
|
||||||
|
@ -51,4 +51,4 @@ kubectl config unset PROPERTY_NAME
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.405094144 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.639702273 +0000 UTC
|
||||||
|
@ -50,4 +50,4 @@ kubectl config use-context CONTEXT_NAME
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.405277784 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.639928664 +0000 UTC
|
||||||
|
@ -73,4 +73,4 @@ $ kubectl config view -o template --template='{{range .users}}{{ if eq .name "e2
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
* [kubectl config](kubectl_config.md) - config modifies kubeconfig files
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.404151238 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.638011058 +0000 UTC
|
||||||
|
@ -63,4 +63,4 @@ $ cat pod.json | kubectl create -f -
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.400230448 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.633893126 +0000 UTC
|
||||||
|
@ -81,4 +81,4 @@ $ kubectl delete pods --all
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.400618492 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.634491315 +0000 UTC
|
||||||
|
@ -63,4 +63,4 @@ $ kubectl describe pods/nginx
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 21:21:05.485819349 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.633584776 +0000 UTC
|
||||||
|
@ -64,4 +64,4 @@ $ kubectl exec -p 123456-7890 -c ruby-container -i -t -- bash -il
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.401622652 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.636226358 +0000 UTC
|
||||||
|
@ -82,4 +82,4 @@ $ kubectl expose streamer --port=4100 --protocol=udp --service-name=video-stream
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.403631642 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.637486796 +0000 UTC
|
||||||
|
@ -85,4 +85,4 @@ $ kubectl get rc/web service/frontend pods/web-pod-13je7
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.399795546 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.633184922 +0000 UTC
|
||||||
|
@ -81,4 +81,4 @@ $ kubectl label pods foo bar-
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.403876136 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.637727935 +0000 UTC
|
||||||
|
@ -62,4 +62,4 @@ $ kubectl log -f 123456-7890 ruby-container
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.400998066 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.634970712 +0000 UTC
|
||||||
|
@ -53,4 +53,4 @@ kubectl namespace [namespace]
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.400806182 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.634703492 +0000 UTC
|
||||||
|
@ -68,4 +68,4 @@ $ kubectl port-forward -p mypod 0:5000
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.40181203 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.636454335 +0000 UTC
|
||||||
|
@ -65,4 +65,4 @@ $ kubectl proxy --api-prefix=k8s-api
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.402034031 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.636689051 +0000 UTC
|
||||||
|
@ -68,4 +68,4 @@ $ kubectl resize --current-replicas=2 --replicas=3 replicationcontrollers foo
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.401412855 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.635916597 +0000 UTC
|
||||||
|
@ -23,14 +23,25 @@ $ kubectl rolling-update frontend-v1 -f frontend-v2.json
|
|||||||
|
|
||||||
// Update pods of frontend-v1 using JSON data passed into stdin.
|
// Update pods of frontend-v1 using JSON data passed into stdin.
|
||||||
$ cat frontend-v2.json | kubectl rolling-update frontend-v1 -f -
|
$ cat frontend-v2.json | kubectl rolling-update frontend-v1 -f -
|
||||||
|
|
||||||
|
// Update the pods of frontend-v1 to frontend-v2 by just changing the image
|
||||||
|
$ kubectl rolling-update frontend-v1 frontend-v2 --image=image:v2
|
||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
### Options
|
### Options
|
||||||
|
|
||||||
```
|
```
|
||||||
|
--deployment-label-key="deployment": The key to use to differentiate between two different controllers, default 'deployment'. Only relevant when --image is specified, ignored otherwise
|
||||||
|
--dry-run=false: If true, print out the changes that would be made, but don't actually make them.
|
||||||
-f, --filename="": Filename or URL to file to use to create the new controller.
|
-f, --filename="": Filename or URL to file to use to create the new controller.
|
||||||
-h, --help=false: help for rolling-update
|
-h, --help=false: help for rolling-update
|
||||||
|
--image="": Image to upgrade the controller to. Can not be used with --filename/-f
|
||||||
|
--no-headers=false: When using the default output, don't print headers.
|
||||||
|
-o, --output="": Output format. One of: json|yaml|template|templatefile.
|
||||||
|
--output-version="": Output the formatted object with the given version (default api-version).
|
||||||
--poll-interval="3s": Time delay between polling controller status after update. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
--poll-interval="3s": Time delay between polling controller status after update. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
||||||
|
-t, --template="": Template string or path to template file to use when -o=template or -o=templatefile. The template format is golang templates [http://golang.org/pkg/text/template/#pkg-overview]
|
||||||
--timeout="5m0s": Max time to wait for a controller to update before giving up. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
--timeout="5m0s": Max time to wait for a controller to update before giving up. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
||||||
--update-period="1m0s": Time to wait between updating pods. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
--update-period="1m0s": Time to wait between updating pods. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
||||||
```
|
```
|
||||||
@ -68,4 +79,4 @@ $ cat frontend-v2.json | kubectl rolling-update frontend-v1 -f -
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.401210692 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-24 04:16:19.186748349 +0000 UTC
|
||||||
|
@ -78,4 +78,4 @@ $ kubectl run-container nginx --image=nginx --overrides='{ "apiVersion": "v1beta
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.402296924 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.636970945 +0000 UTC
|
||||||
|
@ -72,4 +72,4 @@ $ kubectl stop -f path/to/resources
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.402507426 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.637194082 +0000 UTC
|
||||||
|
@ -67,4 +67,4 @@ $ kubectl update pods my-pod --patch='{ "apiVersion": "v1beta1", "desiredState":
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.400435658 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.634205944 +0000 UTC
|
||||||
|
@ -51,4 +51,4 @@ kubectl version
|
|||||||
### SEE ALSO
|
### SEE ALSO
|
||||||
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
* [kubectl](kubectl.md) - kubectl controls the Kubernetes cluster manager
|
||||||
|
|
||||||
###### Auto generated by spf13/cobra at 2015-04-23 00:47:55.405995955 +0000 UTC
|
###### Auto generated by spf13/cobra at 2015-04-23 23:29:05.640847018 +0000 UTC
|
||||||
|
@ -22,6 +22,14 @@ existing controller and overwrite at least one (common) label in its replicaSele
|
|||||||
|
|
||||||
|
|
||||||
.SH OPTIONS
|
.SH OPTIONS
|
||||||
|
.PP
|
||||||
|
\fB\-\-deployment\-label\-key\fP="deployment"
|
||||||
|
The key to use to differentiate between two different controllers, default 'deployment'. Only relevant when \-\-image is specified, ignored otherwise
|
||||||
|
|
||||||
|
.PP
|
||||||
|
\fB\-\-dry\-run\fP=false
|
||||||
|
If true, print out the changes that would be made, but don't actually make them.
|
||||||
|
|
||||||
.PP
|
.PP
|
||||||
\fB\-f\fP, \fB\-\-filename\fP=""
|
\fB\-f\fP, \fB\-\-filename\fP=""
|
||||||
Filename or URL to file to use to create the new controller.
|
Filename or URL to file to use to create the new controller.
|
||||||
@ -30,10 +38,31 @@ existing controller and overwrite at least one (common) label in its replicaSele
|
|||||||
\fB\-h\fP, \fB\-\-help\fP=false
|
\fB\-h\fP, \fB\-\-help\fP=false
|
||||||
help for rolling\-update
|
help for rolling\-update
|
||||||
|
|
||||||
|
.PP
|
||||||
|
\fB\-\-image\fP=""
|
||||||
|
Image to upgrade the controller to. Can not be used with \-\-filename/\-f
|
||||||
|
|
||||||
|
.PP
|
||||||
|
\fB\-\-no\-headers\fP=false
|
||||||
|
When using the default output, don't print headers.
|
||||||
|
|
||||||
|
.PP
|
||||||
|
\fB\-o\fP, \fB\-\-output\fP=""
|
||||||
|
Output format. One of: json|yaml|template|templatefile.
|
||||||
|
|
||||||
|
.PP
|
||||||
|
\fB\-\-output\-version\fP=""
|
||||||
|
Output the formatted object with the given version (default api\-version).
|
||||||
|
|
||||||
.PP
|
.PP
|
||||||
\fB\-\-poll\-interval\fP="3s"
|
\fB\-\-poll\-interval\fP="3s"
|
||||||
Time delay between polling controller status after update. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
Time delay between polling controller status after update. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
||||||
|
|
||||||
|
.PP
|
||||||
|
\fB\-t\fP, \fB\-\-template\fP=""
|
||||||
|
Template string or path to template file to use when \-o=template or \-o=templatefile. The template format is golang templates [
|
||||||
|
\[la]http://golang.org/pkg/text/template/#pkg-overview\[ra]]
|
||||||
|
|
||||||
.PP
|
.PP
|
||||||
\fB\-\-timeout\fP="5m0s"
|
\fB\-\-timeout\fP="5m0s"
|
||||||
Max time to wait for a controller to update before giving up. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
Max time to wait for a controller to update before giving up. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".
|
||||||
@ -156,6 +185,10 @@ $ kubectl rolling\-update frontend\-v1 \-f frontend\-v2.json
|
|||||||
// Update pods of frontend\-v1 using JSON data passed into stdin.
|
// Update pods of frontend\-v1 using JSON data passed into stdin.
|
||||||
$ cat frontend\-v2.json | kubectl rolling\-update frontend\-v1 \-f \-
|
$ cat frontend\-v2.json | kubectl rolling\-update frontend\-v1 \-f \-
|
||||||
|
|
||||||
|
// Update the pods of frontend\-v1 to frontend\-v2 by just changing the image
|
||||||
|
$ kubectl rolling\-update frontend\-v1 frontend\-v2 \-\-image=image:v2
|
||||||
|
|
||||||
|
|
||||||
.fi
|
.fi
|
||||||
.RE
|
.RE
|
||||||
|
|
||||||
|
@ -17,14 +17,22 @@ limitations under the License.
|
|||||||
package cmd
|
package cmd
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"bytes"
|
||||||
|
"crypto/md5"
|
||||||
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"os"
|
"os"
|
||||||
|
"time"
|
||||||
|
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/api"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/api"
|
||||||
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/client"
|
||||||
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/fields"
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/kubectl"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/kubectl"
|
||||||
cmdutil "github.com/GoogleCloudPlatform/kubernetes/pkg/kubectl/cmd/util"
|
cmdutil "github.com/GoogleCloudPlatform/kubernetes/pkg/kubectl/cmd/util"
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/kubectl/resource"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/kubectl/resource"
|
||||||
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/labels"
|
||||||
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/runtime"
|
||||||
"github.com/spf13/cobra"
|
"github.com/spf13/cobra"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -41,7 +49,11 @@ existing controller and overwrite at least one (common) label in its replicaSele
|
|||||||
$ kubectl rolling-update frontend-v1 -f frontend-v2.json
|
$ kubectl rolling-update frontend-v1 -f frontend-v2.json
|
||||||
|
|
||||||
// Update pods of frontend-v1 using JSON data passed into stdin.
|
// Update pods of frontend-v1 using JSON data passed into stdin.
|
||||||
$ cat frontend-v2.json | kubectl rolling-update frontend-v1 -f -`
|
$ cat frontend-v2.json | kubectl rolling-update frontend-v1 -f -
|
||||||
|
|
||||||
|
// Update the pods of frontend-v1 to frontend-v2 by just changing the image
|
||||||
|
$ kubectl rolling-update frontend-v1 frontend-v2 --image=image:v2
|
||||||
|
`
|
||||||
)
|
)
|
||||||
|
|
||||||
func NewCmdRollingUpdate(f *cmdutil.Factory, out io.Writer) *cobra.Command {
|
func NewCmdRollingUpdate(f *cmdutil.Factory, out io.Writer) *cobra.Command {
|
||||||
@ -61,33 +73,70 @@ func NewCmdRollingUpdate(f *cmdutil.Factory, out io.Writer) *cobra.Command {
|
|||||||
cmd.Flags().String("poll-interval", pollInterval, `Time delay between polling controller status after update. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".`)
|
cmd.Flags().String("poll-interval", pollInterval, `Time delay between polling controller status after update. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".`)
|
||||||
cmd.Flags().String("timeout", timeout, `Max time to wait for a controller to update before giving up. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".`)
|
cmd.Flags().String("timeout", timeout, `Max time to wait for a controller to update before giving up. Valid time units are "ns", "us" (or "µs"), "ms", "s", "m", "h".`)
|
||||||
cmd.Flags().StringP("filename", "f", "", "Filename or URL to file to use to create the new controller.")
|
cmd.Flags().StringP("filename", "f", "", "Filename or URL to file to use to create the new controller.")
|
||||||
|
cmd.Flags().String("image", "", "Image to upgrade the controller to. Can not be used with --filename/-f")
|
||||||
|
cmd.Flags().String("deployment-label-key", "deployment", "The key to use to differentiate between two different controllers, default 'deployment'. Only relevant when --image is specified, ignored otherwise")
|
||||||
|
cmd.Flags().Bool("dry-run", false, "If true, print out the changes that would be made, but don't actually make them.")
|
||||||
|
cmdutil.AddPrinterFlags(cmd)
|
||||||
return cmd
|
return cmd
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func validateArguments(cmd *cobra.Command, args []string) (deploymentKey, filename, image, oldName string, err error) {
|
||||||
|
deploymentKey = cmdutil.GetFlagString(cmd, "deployment-label-key")
|
||||||
|
filename = cmdutil.GetFlagString(cmd, "filename")
|
||||||
|
image = cmdutil.GetFlagString(cmd, "image")
|
||||||
|
|
||||||
|
if len(deploymentKey) == 0 {
|
||||||
|
return "", "", "", "", cmdutil.UsageError(cmd, "--deployment-label-key can not be empty")
|
||||||
|
}
|
||||||
|
if len(filename) == 0 && len(image) == 0 {
|
||||||
|
return "", "", "", "", cmdutil.UsageError(cmd, "Must specify --filename or --image for new controller")
|
||||||
|
}
|
||||||
|
if len(filename) != 0 && len(image) != 0 {
|
||||||
|
return "", "", "", "", cmdutil.UsageError(cmd, "--filename and --image can not both be specified")
|
||||||
|
}
|
||||||
|
if len(image) > 0 && len(args) < 2 {
|
||||||
|
return "", "", "", "", cmdutil.UsageError(cmd, "You must specify a name for your new controller")
|
||||||
|
}
|
||||||
|
if len(args) < 1 {
|
||||||
|
return "", "", "", "", cmdutil.UsageError(cmd, "Must specify the controller to update")
|
||||||
|
}
|
||||||
|
|
||||||
|
return deploymentKey, filename, image, args[0], nil
|
||||||
|
}
|
||||||
|
|
||||||
func RunRollingUpdate(f *cmdutil.Factory, out io.Writer, cmd *cobra.Command, args []string) error {
|
func RunRollingUpdate(f *cmdutil.Factory, out io.Writer, cmd *cobra.Command, args []string) error {
|
||||||
if os.Args[1] == "rollingupdate" {
|
if os.Args[1] == "rollingupdate" {
|
||||||
printDeprecationWarning("rolling-update", "rollingupdate")
|
printDeprecationWarning("rolling-update", "rollingupdate")
|
||||||
}
|
}
|
||||||
|
deploymentKey, filename, image, oldName, err := validateArguments(cmd, args)
|
||||||
filename := cmdutil.GetFlagString(cmd, "filename")
|
if err != nil {
|
||||||
if len(filename) == 0 {
|
return err
|
||||||
return cmdutil.UsageError(cmd, "Must specify filename for new controller")
|
|
||||||
}
|
}
|
||||||
period := cmdutil.GetFlagDuration(cmd, "update-period")
|
period := cmdutil.GetFlagDuration(cmd, "update-period")
|
||||||
interval := cmdutil.GetFlagDuration(cmd, "poll-interval")
|
interval := cmdutil.GetFlagDuration(cmd, "poll-interval")
|
||||||
timeout := cmdutil.GetFlagDuration(cmd, "timeout")
|
timeout := cmdutil.GetFlagDuration(cmd, "timeout")
|
||||||
if len(args) != 1 {
|
dryrun := cmdutil.GetFlagBool(cmd, "dry-run")
|
||||||
return cmdutil.UsageError(cmd, "Must specify the controller to update")
|
|
||||||
}
|
|
||||||
oldName := args[0]
|
|
||||||
|
|
||||||
cmdNamespace, err := f.DefaultNamespace()
|
cmdNamespace, err := f.DefaultNamespace()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
client, err := f.Client()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// fetch rc
|
||||||
|
oldRc, err := client.ReplicationControllers(cmdNamespace).Get(oldName)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
mapper, typer := f.Object()
|
mapper, typer := f.Object()
|
||||||
// TODO: use resource.Builder instead
|
var newRc *api.ReplicationController
|
||||||
|
|
||||||
|
if len(filename) != 0 {
|
||||||
obj, err := resource.NewBuilder(mapper, typer, f.ClientMapperForCommand()).
|
obj, err := resource.NewBuilder(mapper, typer, f.ClientMapperForCommand()).
|
||||||
NamespaceParam(cmdNamespace).RequireNamespace().
|
NamespaceParam(cmdNamespace).RequireNamespace().
|
||||||
FilenameParam(filename).
|
FilenameParam(filename).
|
||||||
@ -96,29 +145,53 @@ func RunRollingUpdate(f *cmdutil.Factory, out io.Writer, cmd *cobra.Command, arg
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
newRc, ok := obj.(*api.ReplicationController)
|
var ok bool
|
||||||
|
newRc, ok = obj.(*api.ReplicationController)
|
||||||
if !ok {
|
if !ok {
|
||||||
return cmdutil.UsageError(cmd, "%s does not specify a valid ReplicationController", filename)
|
return cmdutil.UsageError(cmd, "%s does not specify a valid ReplicationController", filename)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
if len(image) != 0 {
|
||||||
|
newName := args[1]
|
||||||
|
var err error
|
||||||
|
// load the old RC into the "new" RC
|
||||||
|
if newRc, err = client.ReplicationControllers(cmdNamespace).Get(oldName); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(newRc.Spec.Template.Spec.Containers) > 1 {
|
||||||
|
// TODO: support multi-container image update.
|
||||||
|
return errors.New("Image update is not supported for multi-container pods")
|
||||||
|
}
|
||||||
|
if len(newRc.Spec.Template.Spec.Containers) == 0 {
|
||||||
|
return cmdutil.UsageError(cmd, "Pod has no containers! (%v)", newRc)
|
||||||
|
}
|
||||||
|
newRc.Spec.Template.Spec.Containers[0].Image = image
|
||||||
|
|
||||||
|
newHash, err := hashObject(newRc, client.Codec)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
newRc.Name = newName
|
||||||
|
|
||||||
|
newRc.Spec.Selector[deploymentKey] = newHash
|
||||||
|
newRc.Spec.Template.Labels[deploymentKey] = newHash
|
||||||
|
newRc.ResourceVersion = ""
|
||||||
|
|
||||||
|
if _, found := oldRc.Spec.Selector[deploymentKey]; !found {
|
||||||
|
if err := addDeploymentKeyToReplicationController(oldRc, client, deploymentKey, cmdNamespace, out); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
newName := newRc.Name
|
newName := newRc.Name
|
||||||
if oldName == newName {
|
if oldName == newName {
|
||||||
return cmdutil.UsageError(cmd, "%s cannot have the same name as the existing ReplicationController %s",
|
return cmdutil.UsageError(cmd, "%s cannot have the same name as the existing ReplicationController %s",
|
||||||
filename, oldName)
|
filename, oldName)
|
||||||
}
|
}
|
||||||
|
|
||||||
client, err := f.Client()
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
updater := kubectl.NewRollingUpdater(newRc.Namespace, kubectl.NewRollingUpdaterClient(client))
|
updater := kubectl.NewRollingUpdater(newRc.Namespace, kubectl.NewRollingUpdaterClient(client))
|
||||||
|
|
||||||
// fetch rc
|
|
||||||
oldRc, err := client.ReplicationControllers(newRc.Namespace).Get(oldName)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
var hasLabel bool
|
var hasLabel bool
|
||||||
for key, oldValue := range oldRc.Spec.Selector {
|
for key, oldValue := range oldRc.Spec.Selector {
|
||||||
if newValue, ok := newRc.Spec.Selector[key]; ok && newValue != oldValue {
|
if newValue, ok := newRc.Spec.Selector[key]; ok && newValue != oldValue {
|
||||||
@ -134,6 +207,18 @@ func RunRollingUpdate(f *cmdutil.Factory, out io.Writer, cmd *cobra.Command, arg
|
|||||||
if newRc.Spec.Replicas == 0 {
|
if newRc.Spec.Replicas == 0 {
|
||||||
newRc.Spec.Replicas = oldRc.Spec.Replicas
|
newRc.Spec.Replicas = oldRc.Spec.Replicas
|
||||||
}
|
}
|
||||||
|
if dryrun {
|
||||||
|
oldRcData := &bytes.Buffer{}
|
||||||
|
if err := f.PrintObject(cmd, oldRc, oldRcData); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
newRcData := &bytes.Buffer{}
|
||||||
|
if err := f.PrintObject(cmd, newRc, newRcData); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
fmt.Fprintf(out, "Rolling from:\n%s\nTo:\n%s\n", string(oldRcData.Bytes()), string(newRcData.Bytes()))
|
||||||
|
return nil
|
||||||
|
}
|
||||||
err = updater.Update(&kubectl.RollingUpdaterConfig{
|
err = updater.Update(&kubectl.RollingUpdaterConfig{
|
||||||
Out: out,
|
Out: out,
|
||||||
OldRc: oldRc,
|
OldRc: oldRc,
|
||||||
@ -150,3 +235,68 @@ func RunRollingUpdate(f *cmdutil.Factory, out io.Writer, cmd *cobra.Command, arg
|
|||||||
fmt.Fprintf(out, "%s\n", newName)
|
fmt.Fprintf(out, "%s\n", newName)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func hashObject(obj runtime.Object, codec runtime.Codec) (string, error) {
|
||||||
|
data, err := codec.Encode(obj)
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
return fmt.Sprintf("%x", md5.Sum(data)), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
const MaxRetries = 3
|
||||||
|
|
||||||
|
func addDeploymentKeyToReplicationController(oldRc *api.ReplicationController, client *client.Client, deploymentKey, namespace string, out io.Writer) error {
|
||||||
|
oldHash, err := hashObject(oldRc, client.Codec)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
// Update all labels to include the new hash, so they are correctly adopted
|
||||||
|
// TODO: extract the code from the label command and re-use it here.
|
||||||
|
podList, err := client.Pods(namespace).List(labels.SelectorFromSet(oldRc.Spec.Selector), fields.Everything())
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
for ix := range podList.Items {
|
||||||
|
pod := &podList.Items[ix]
|
||||||
|
if pod.Labels == nil {
|
||||||
|
pod.Labels = map[string]string{
|
||||||
|
deploymentKey: oldHash,
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
pod.Labels[deploymentKey] = oldHash
|
||||||
|
}
|
||||||
|
err = nil
|
||||||
|
delay := 3
|
||||||
|
for i := 0; i < MaxRetries; i++ {
|
||||||
|
_, err = client.Pods(namespace).Update(pod)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Fprint(out, "Error updating pod (%v), retrying after %d seconds", err, delay)
|
||||||
|
time.Sleep(time.Second * time.Duration(delay))
|
||||||
|
delay *= delay
|
||||||
|
} else {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if oldRc.Spec.Selector == nil {
|
||||||
|
oldRc.Spec.Selector = map[string]string{}
|
||||||
|
}
|
||||||
|
if oldRc.Spec.Template.Labels == nil {
|
||||||
|
oldRc.Spec.Template.Labels = map[string]string{}
|
||||||
|
}
|
||||||
|
oldRc.Spec.Selector[deploymentKey] = oldHash
|
||||||
|
oldRc.Spec.Template.Labels[deploymentKey] = oldHash
|
||||||
|
|
||||||
|
if _, err := client.ReplicationControllers(namespace).Update(oldRc); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
// Note there is still a race here, if a pod was created during the update phase.
|
||||||
|
// It's unlikely, but it could happen, and if it does, we'll create extra pods.
|
||||||
|
// TODO: Clean up orphaned pods here.
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
177
pkg/kubectl/cmd/rollingupdate_test.go
Normal file
177
pkg/kubectl/cmd/rollingupdate_test.go
Normal file
@ -0,0 +1,177 @@
|
|||||||
|
/*
|
||||||
|
Copyright 2014 Google Inc. All rights reserved.
|
||||||
|
|
||||||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
you may not use this file except in compliance with the License.
|
||||||
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
Unless required by applicable law or agreed to in writing, software
|
||||||
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
See the License for the specific language governing permissions and
|
||||||
|
limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package cmd
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"net/http"
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/api"
|
||||||
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/api/latest"
|
||||||
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/client"
|
||||||
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/util"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestValidateArgs(t *testing.T) {
|
||||||
|
f, _, _ := NewAPIFactory()
|
||||||
|
|
||||||
|
tests := []struct {
|
||||||
|
flags map[string]string
|
||||||
|
args []string
|
||||||
|
expectErr bool
|
||||||
|
testName string
|
||||||
|
}{
|
||||||
|
{
|
||||||
|
expectErr: true,
|
||||||
|
testName: "nothing",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
flags: map[string]string{},
|
||||||
|
args: []string{"foo"},
|
||||||
|
expectErr: true,
|
||||||
|
testName: "no file, no image",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
flags: map[string]string{
|
||||||
|
"filename": "bar.yaml",
|
||||||
|
},
|
||||||
|
args: []string{"foo"},
|
||||||
|
testName: "valid file example",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
flags: map[string]string{
|
||||||
|
"image": "foo:v2",
|
||||||
|
},
|
||||||
|
args: []string{"foo"},
|
||||||
|
expectErr: true,
|
||||||
|
testName: "missing second image name",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
flags: map[string]string{
|
||||||
|
"image": "foo:v2",
|
||||||
|
},
|
||||||
|
args: []string{"foo", "foo-v2"},
|
||||||
|
testName: "valid image example",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
flags: map[string]string{
|
||||||
|
"image": "foo:v2",
|
||||||
|
"filename": "bar.yaml",
|
||||||
|
},
|
||||||
|
args: []string{"foo", "foo-v2"},
|
||||||
|
expectErr: true,
|
||||||
|
testName: "both filename and image example",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
for _, test := range tests {
|
||||||
|
out := &bytes.Buffer{}
|
||||||
|
cmd := NewCmdRollingUpdate(f, out)
|
||||||
|
|
||||||
|
if test.flags != nil {
|
||||||
|
for key, val := range test.flags {
|
||||||
|
cmd.Flags().Set(key, val)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_, _, _, _, err := validateArguments(cmd, test.args)
|
||||||
|
if err != nil && !test.expectErr {
|
||||||
|
t.Errorf("unexpected error: %v (%s)", err, test.testName)
|
||||||
|
}
|
||||||
|
if err == nil && test.expectErr {
|
||||||
|
t.Error("unexpected non-error (%s)", test.testName)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestAddDeploymentHash(t *testing.T) {
|
||||||
|
buf := &bytes.Buffer{}
|
||||||
|
f, tf, codec := NewAPIFactory()
|
||||||
|
rc := &api.ReplicationController{
|
||||||
|
ObjectMeta: api.ObjectMeta{Name: "rc"},
|
||||||
|
Spec: api.ReplicationControllerSpec{
|
||||||
|
Selector: map[string]string{
|
||||||
|
"foo": "bar",
|
||||||
|
},
|
||||||
|
Template: &api.PodTemplateSpec{
|
||||||
|
ObjectMeta: api.ObjectMeta{
|
||||||
|
Labels: map[string]string{
|
||||||
|
"foo": "bar",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
podList := &api.PodList{
|
||||||
|
Items: []api.Pod{
|
||||||
|
{ObjectMeta: api.ObjectMeta{Name: "foo"}},
|
||||||
|
{ObjectMeta: api.ObjectMeta{Name: "bar"}},
|
||||||
|
{ObjectMeta: api.ObjectMeta{Name: "baz"}},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
seen := util.StringSet{}
|
||||||
|
updatedRc := false
|
||||||
|
tf.Client = &client.FakeRESTClient{
|
||||||
|
Codec: codec,
|
||||||
|
Client: client.HTTPClientFunc(func(req *http.Request) (*http.Response, error) {
|
||||||
|
switch p, m := req.URL.Path, req.Method; {
|
||||||
|
case p == "/api/v1beta3/namespaces/default/pods" && m == "GET":
|
||||||
|
if req.URL.RawQuery != "labelSelector=foo%3Dbar" {
|
||||||
|
t.Errorf("Unexpected query string: %s", req.URL.RawQuery)
|
||||||
|
}
|
||||||
|
return &http.Response{StatusCode: 200, Body: objBody(codec, podList)}, nil
|
||||||
|
case p == "/api/v1beta3/namespaces/default/pods/foo" && m == "PUT":
|
||||||
|
seen.Insert("foo")
|
||||||
|
return &http.Response{StatusCode: 200, Body: objBody(codec, &podList.Items[0])}, nil
|
||||||
|
case p == "/api/v1beta3/namespaces/default/pods/bar" && m == "PUT":
|
||||||
|
seen.Insert("bar")
|
||||||
|
return &http.Response{StatusCode: 200, Body: objBody(codec, &podList.Items[1])}, nil
|
||||||
|
case p == "/api/v1beta3/namespaces/default/pods/baz" && m == "PUT":
|
||||||
|
seen.Insert("baz")
|
||||||
|
return &http.Response{StatusCode: 200, Body: objBody(codec, &podList.Items[2])}, nil
|
||||||
|
case p == "/api/v1beta3/namespaces/default/replicationcontrollers/rc" && m == "PUT":
|
||||||
|
updatedRc = true
|
||||||
|
return &http.Response{StatusCode: 200, Body: objBody(codec, rc)}, nil
|
||||||
|
default:
|
||||||
|
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
|
||||||
|
return nil, nil
|
||||||
|
}
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
tf.ClientConfig = &client.Config{Version: latest.Version}
|
||||||
|
tf.Namespace = "test"
|
||||||
|
|
||||||
|
client, err := f.Client()
|
||||||
|
if err != nil {
|
||||||
|
t.Errorf("unexpected error: %v", err)
|
||||||
|
t.Fail()
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := addDeploymentKeyToReplicationController(rc, client, "hash", api.NamespaceDefault, buf); err != nil {
|
||||||
|
t.Errorf("unexpected error: %v", err)
|
||||||
|
}
|
||||||
|
for _, pod := range podList.Items {
|
||||||
|
if !seen.Has(pod.Name) {
|
||||||
|
t.Errorf("Missing update for pod: %s", pod.Name)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if !updatedRc {
|
||||||
|
t.Errorf("Failed to update replication controller with new labels")
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user