React to moves

parent 33adf367
......@@ -27,6 +27,7 @@ import (
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
"k8s.io/client-go/rest/fake"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
"k8s.io/kubernetes/pkg/kubectl/scheme"
......@@ -420,7 +421,7 @@ func TestAnnotateErrors(t *testing.T) {
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
iostreams, _, bufOut, bufErr := genericclioptions.NewTestIOStreams()
cmd := NewCmdAnnotate("kubectl", tf, iostreams)
......@@ -449,7 +450,7 @@ func TestAnnotateErrors(t *testing.T) {
}
func TestAnnotateObject(t *testing.T) {
pods, _, _ := testData()
pods, _, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
......@@ -458,13 +459,13 @@ func TestAnnotateObject(t *testing.T) {
tf.UnstructuredClient = &fake.RESTClient{
GroupVersion: schema.GroupVersion{Group: "testgroup", Version: "v1"},
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch req.Method {
case "GET":
switch req.URL.Path {
case "/namespaces/test/pods/foo":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -472,7 +473,7 @@ func TestAnnotateObject(t *testing.T) {
case "PATCH":
switch req.URL.Path {
case "/namespaces/test/pods/foo":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -483,7 +484,7 @@ func TestAnnotateObject(t *testing.T) {
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
iostreams, _, bufOut, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdAnnotate("kubectl", tf, iostreams)
......@@ -502,7 +503,7 @@ func TestAnnotateObject(t *testing.T) {
}
func TestAnnotateObjectFromFile(t *testing.T) {
pods, _, _ := testData()
pods, _, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
......@@ -511,13 +512,13 @@ func TestAnnotateObjectFromFile(t *testing.T) {
tf.UnstructuredClient = &fake.RESTClient{
GroupVersion: schema.GroupVersion{Group: "testgroup", Version: "v1"},
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch req.Method {
case "GET":
switch req.URL.Path {
case "/namespaces/test/replicationcontrollers/cassandra":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -525,7 +526,7 @@ func TestAnnotateObjectFromFile(t *testing.T) {
case "PATCH":
switch req.URL.Path {
case "/namespaces/test/replicationcontrollers/cassandra":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -536,13 +537,13 @@ func TestAnnotateObjectFromFile(t *testing.T) {
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
iostreams, _, bufOut, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdAnnotate("kubectl", tf, iostreams)
cmd.SetOutput(bufOut)
options := NewAnnotateOptions(iostreams)
options.Filenames = []string{"../../../test/e2e/testing-manifests/statefulset/cassandra/controller.yaml"}
options.Filenames = []string{"../../../../test/e2e/testing-manifests/statefulset/cassandra/controller.yaml"}
args := []string{"a=b", "c-"}
if err := options.Complete(tf, cmd, args); err != nil {
t.Fatalf("unexpected error: %v", err)
......@@ -561,19 +562,19 @@ func TestAnnotateLocal(t *testing.T) {
tf.UnstructuredClient = &fake.RESTClient{
GroupVersion: schema.GroupVersion{Group: "testgroup", Version: "v1"},
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
t.Fatalf("unexpected request: %s %#v\n%#v", req.Method, req.URL, req)
return nil, nil
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
iostreams, _, _, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdAnnotate("kubectl", tf, iostreams)
options := NewAnnotateOptions(iostreams)
options.local = true
options.Filenames = []string{"../../../test/e2e/testing-manifests/statefulset/cassandra/controller.yaml"}
options.Filenames = []string{"../../../../test/e2e/testing-manifests/statefulset/cassandra/controller.yaml"}
args := []string{"a=b"}
if err := options.Complete(tf, cmd, args); err != nil {
t.Fatalf("unexpected error: %v", err)
......@@ -587,7 +588,7 @@ func TestAnnotateLocal(t *testing.T) {
}
func TestAnnotateMultipleObjects(t *testing.T) {
pods, _, _ := testData()
pods, _, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
......@@ -595,13 +596,13 @@ func TestAnnotateMultipleObjects(t *testing.T) {
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
GroupVersion: schema.GroupVersion{Group: "testgroup", Version: "v1"},
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch req.Method {
case "GET":
switch req.URL.Path {
case "/namespaces/test/pods":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, pods)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, pods)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -609,9 +610,9 @@ func TestAnnotateMultipleObjects(t *testing.T) {
case "PATCH":
switch req.URL.Path {
case "/namespaces/test/pods/foo":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])}, nil
case "/namespaces/test/pods/bar":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[1])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[1])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -622,7 +623,7 @@ func TestAnnotateMultipleObjects(t *testing.T) {
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
iostreams, _, _, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdAnnotate("kubectl", tf, iostreams)
......
......@@ -31,6 +31,7 @@ import (
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
restclient "k8s.io/client-go/rest"
"k8s.io/client-go/tools/remotecommand"
"k8s.io/kubernetes/pkg/kubectl/cmd/exec"
"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/polymorphichelpers"
......@@ -62,7 +63,7 @@ const (
// AttachOptions declare the arguments accepted by the Exec command
type AttachOptions struct {
StreamOptions
exec.StreamOptions
// whether to disable use of standard error when streaming output from tty
DisableStderr bool
......@@ -85,11 +86,11 @@ type AttachOptions struct {
func NewAttachOptions(streams genericclioptions.IOStreams) *AttachOptions {
return &AttachOptions{
StreamOptions: StreamOptions{
StreamOptions: exec.StreamOptions{
IOStreams: streams,
},
Attach: &DefaultRemoteAttach{},
AttachFunc: defaultAttachFunc,
AttachFunc: DefaultAttachFunc,
}
}
......@@ -119,7 +120,7 @@ type RemoteAttach interface {
Attach(method string, url *url.URL, config *restclient.Config, stdin io.Reader, stdout, stderr io.Writer, tty bool, terminalSizeQueue remotecommand.TerminalSizeQueue) error
}
func defaultAttachFunc(o *AttachOptions, containerToAttach *corev1.Container, raw bool, sizeQueue remotecommand.TerminalSizeQueue) func() error {
func DefaultAttachFunc(o *AttachOptions, containerToAttach *corev1.Container, raw bool, sizeQueue remotecommand.TerminalSizeQueue) func() error {
return func() error {
restClient, err := restclient.RESTClientFor(o.Config)
if err != nil {
......@@ -262,7 +263,7 @@ func (o *AttachOptions) Run() error {
}
// ensure we can recover the terminal while attached
t := o.setupTTY()
t := o.SetupTTY()
var sizeQueue remotecommand.TerminalSizeQueue
if t.Raw {
......
......@@ -33,6 +33,7 @@ import (
restclient "k8s.io/client-go/rest"
"k8s.io/client-go/rest/fake"
"k8s.io/client-go/tools/remotecommand"
"k8s.io/kubernetes/pkg/kubectl/cmd/exec"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
"k8s.io/kubernetes/pkg/kubectl/polymorphichelpers"
"k8s.io/kubernetes/pkg/kubectl/scheme"
......@@ -87,7 +88,7 @@ func TestPodAndContainerAttach(t *testing.T) {
},
{
name: "container in flag",
options: &AttachOptions{StreamOptions: StreamOptions{ContainerName: "bar"}, GetPodTimeout: 10000000},
options: &AttachOptions{StreamOptions: exec.StreamOptions{ContainerName: "bar"}, GetPodTimeout: 10000000},
args: []string{"foo"},
expectedPodName: "foo",
expectedContainerName: "bar",
......@@ -95,7 +96,7 @@ func TestPodAndContainerAttach(t *testing.T) {
},
{
name: "init container in flag",
options: &AttachOptions{StreamOptions: StreamOptions{ContainerName: "initfoo"}, GetPodTimeout: 30},
options: &AttachOptions{StreamOptions: exec.StreamOptions{ContainerName: "initfoo"}, GetPodTimeout: 30},
args: []string{"foo"},
expectedPodName: "foo",
expectedContainerName: "initfoo",
......@@ -103,7 +104,7 @@ func TestPodAndContainerAttach(t *testing.T) {
},
{
name: "non-existing container",
options: &AttachOptions{StreamOptions: StreamOptions{ContainerName: "wrong"}, GetPodTimeout: 10},
options: &AttachOptions{StreamOptions: exec.StreamOptions{ContainerName: "wrong"}, GetPodTimeout: 10},
args: []string{"foo"},
expectedPodName: "foo",
expectError: "container not found",
......@@ -238,11 +239,11 @@ func TestAttach(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == test.podPath && m == "GET":
body := objBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
body := cmdtesting.ObjBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
case p == test.fetchPodPath && m == "GET":
body := objBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
body := cmdtesting.ObjBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
default:
t.Errorf("%s: unexpected request: %s %#v\n%#v", p, req.Method, req.URL, req)
return nil, fmt.Errorf("unexpected request")
......@@ -256,7 +257,7 @@ func TestAttach(t *testing.T) {
remoteAttach.err = fmt.Errorf("attach error")
}
options := &AttachOptions{
StreamOptions: StreamOptions{
StreamOptions: exec.StreamOptions{
ContainerName: test.container,
IOStreams: genericclioptions.NewTestIOStreamsDiscard(),
},
......@@ -340,11 +341,11 @@ func TestAttachWarnings(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == test.podPath && m == "GET":
body := objBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
body := cmdtesting.ObjBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
case p == test.fetchPodPath && m == "GET":
body := objBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
body := cmdtesting.ObjBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
default:
t.Errorf("%s: unexpected request: %s %#v\n%#v", p, req.Method, req.URL, req)
return nil, fmt.Errorf("unexpected request")
......@@ -354,7 +355,7 @@ func TestAttachWarnings(t *testing.T) {
tf.ClientConfigVal = &restclient.Config{APIPath: "/api", ContentConfig: restclient.ContentConfig{NegotiatedSerializer: scheme.Codecs, GroupVersion: &schema.GroupVersion{Version: test.version}}}
options := &AttachOptions{
StreamOptions: StreamOptions{
StreamOptions: exec.StreamOptions{
Stdin: test.stdin,
TTY: test.tty,
ContainerName: test.container,
......
......@@ -38,6 +38,11 @@ import (
"k8s.io/kubernetes/pkg/kubectl/util/i18n"
)
const (
defaultPodLogsTimeout = 20 * time.Second
timeout = 5 * time.Minute
)
type ClusterInfoDumpOptions struct {
PrintFlags *genericclioptions.PrintFlags
PrintObj printers.ResourcePrinterFunc
......
......@@ -28,17 +28,48 @@ import (
"github.com/spf13/cobra"
"k8s.io/apimachinery/pkg/api/meta"
utilflag "k8s.io/apiserver/pkg/util/flag"
"k8s.io/client-go/tools/clientcmd"
"k8s.io/kubernetes/pkg/kubectl/cmd/annotate"
"k8s.io/kubernetes/pkg/kubectl/cmd/apiresources"
"k8s.io/kubernetes/pkg/kubectl/cmd/apply"
"k8s.io/kubernetes/pkg/kubectl/cmd/attach"
"k8s.io/kubernetes/pkg/kubectl/cmd/auth"
"k8s.io/kubernetes/pkg/kubectl/cmd/autoscale"
"k8s.io/kubernetes/pkg/kubectl/cmd/certificates"
"k8s.io/kubernetes/pkg/kubectl/cmd/clusterinfo"
"k8s.io/kubernetes/pkg/kubectl/cmd/completion"
cmdconfig "k8s.io/kubernetes/pkg/kubectl/cmd/config"
"k8s.io/kubernetes/pkg/kubectl/cmd/convert"
"k8s.io/kubernetes/pkg/kubectl/cmd/cp"
"k8s.io/kubernetes/pkg/kubectl/cmd/create"
"k8s.io/kubernetes/pkg/kubectl/cmd/delete"
"k8s.io/kubernetes/pkg/kubectl/cmd/describe"
"k8s.io/kubernetes/pkg/kubectl/cmd/diff"
"k8s.io/kubernetes/pkg/kubectl/cmd/drain"
"k8s.io/kubernetes/pkg/kubectl/cmd/edit"
cmdexec "k8s.io/kubernetes/pkg/kubectl/cmd/exec"
"k8s.io/kubernetes/pkg/kubectl/cmd/explain"
"k8s.io/kubernetes/pkg/kubectl/cmd/expose"
"k8s.io/kubernetes/pkg/kubectl/cmd/get"
"k8s.io/kubernetes/pkg/kubectl/cmd/label"
"k8s.io/kubernetes/pkg/kubectl/cmd/logs"
"k8s.io/kubernetes/pkg/kubectl/cmd/options"
"k8s.io/kubernetes/pkg/kubectl/cmd/patch"
"k8s.io/kubernetes/pkg/kubectl/cmd/plugin"
"k8s.io/kubernetes/pkg/kubectl/cmd/portforward"
"k8s.io/kubernetes/pkg/kubectl/cmd/proxy"
"k8s.io/kubernetes/pkg/kubectl/cmd/replace"
"k8s.io/kubernetes/pkg/kubectl/cmd/rollingupdate"
"k8s.io/kubernetes/pkg/kubectl/cmd/rollout"
"k8s.io/kubernetes/pkg/kubectl/cmd/run"
"k8s.io/kubernetes/pkg/kubectl/cmd/scale"
"k8s.io/kubernetes/pkg/kubectl/cmd/set"
"k8s.io/kubernetes/pkg/kubectl/cmd/taint"
"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
"k8s.io/kubernetes/pkg/kubectl/cmd/top"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/cmd/version"
"k8s.io/kubernetes/pkg/kubectl/cmd/wait"
"k8s.io/kubernetes/pkg/kubectl/util/i18n"
......@@ -416,72 +447,72 @@ func NewKubectlCommand(in io.Reader, out, err io.Writer) *cobra.Command {
Message: "Basic Commands (Beginner):",
Commands: []*cobra.Command{
create.NewCmdCreate(f, ioStreams),
NewCmdExposeService(f, ioStreams),
NewCmdRun(f, ioStreams),
expose.NewCmdExposeService(f, ioStreams),
run.NewCmdRun(f, ioStreams),
set.NewCmdSet(f, ioStreams),
deprecatedAlias("run-container", NewCmdRun(f, ioStreams)),
deprecatedAlias("run-container", run.NewCmdRun(f, ioStreams)),
},
},
{
Message: "Basic Commands (Intermediate):",
Commands: []*cobra.Command{
NewCmdExplain("kubectl", f, ioStreams),
explain.NewCmdExplain("kubectl", f, ioStreams),
get.NewCmdGet("kubectl", f, ioStreams),
NewCmdEdit(f, ioStreams),
NewCmdDelete(f, ioStreams),
edit.NewCmdEdit(f, ioStreams),
delete.NewCmdDelete(f, ioStreams),
},
},
{
Message: "Deploy Commands:",
Commands: []*cobra.Command{
rollout.NewCmdRollout(f, ioStreams),
NewCmdRollingUpdate(f, ioStreams),
NewCmdScale(f, ioStreams),
NewCmdAutoscale(f, ioStreams),
rollingupdate.NewCmdRollingUpdate(f, ioStreams),
scale.NewCmdScale(f, ioStreams),
autoscale.NewCmdAutoscale(f, ioStreams),
},
},
{
Message: "Cluster Management Commands:",
Commands: []*cobra.Command{
NewCmdCertificate(f, ioStreams),
NewCmdClusterInfo(f, ioStreams),
NewCmdTop(f, ioStreams),
NewCmdCordon(f, ioStreams),
NewCmdUncordon(f, ioStreams),
NewCmdDrain(f, ioStreams),
NewCmdTaint(f, ioStreams),
certificates.NewCmdCertificate(f, ioStreams),
clusterinfo.NewCmdClusterInfo(f, ioStreams),
top.NewCmdTop(f, ioStreams),
drain.NewCmdCordon(f, ioStreams),
drain.NewCmdUncordon(f, ioStreams),
drain.NewCmdDrain(f, ioStreams),
taint.NewCmdTaint(f, ioStreams),
},
},
{
Message: "Troubleshooting and Debugging Commands:",
Commands: []*cobra.Command{
NewCmdDescribe("kubectl", f, ioStreams),
NewCmdLogs(f, ioStreams),
NewCmdAttach(f, ioStreams),
NewCmdExec(f, ioStreams),
NewCmdPortForward(f, ioStreams),
NewCmdProxy(f, ioStreams),
NewCmdCp(f, ioStreams),
describe.NewCmdDescribe("kubectl", f, ioStreams),
logs.NewCmdLogs(f, ioStreams),
attach.NewCmdAttach(f, ioStreams),
cmdexec.NewCmdExec(f, ioStreams),
portforward.NewCmdPortForward(f, ioStreams),
proxy.NewCmdProxy(f, ioStreams),
cp.NewCmdCp(f, ioStreams),
auth.NewCmdAuth(f, ioStreams),
},
},
{
Message: "Advanced Commands:",
Commands: []*cobra.Command{
NewCmdDiff(f, ioStreams),
NewCmdApply("kubectl", f, ioStreams),
NewCmdPatch(f, ioStreams),
NewCmdReplace(f, ioStreams),
diff.NewCmdDiff(f, ioStreams),
apply.NewCmdApply("kubectl", f, ioStreams),
patch.NewCmdPatch(f, ioStreams),
replace.NewCmdReplace(f, ioStreams),
wait.NewCmdWait(f, ioStreams),
NewCmdConvert(f, ioStreams),
convert.NewCmdConvert(f, ioStreams),
},
},
{
Message: "Settings Commands:",
Commands: []*cobra.Command{
NewCmdLabel(f, ioStreams),
NewCmdAnnotate("kubectl", f, ioStreams),
NewCmdCompletion(ioStreams.Out, ""),
label.NewCmdLabel(f, ioStreams),
annotate.NewCmdAnnotate("kubectl", f, ioStreams),
completion.NewCmdCompletion(ioStreams.Out, ""),
},
},
}
......@@ -511,11 +542,11 @@ func NewKubectlCommand(in io.Reader, out, err io.Writer) *cobra.Command {
cmds.AddCommand(alpha)
cmds.AddCommand(cmdconfig.NewCmdConfig(f, clientcmd.NewDefaultPathOptions(), ioStreams))
cmds.AddCommand(NewCmdPlugin(f, ioStreams))
cmds.AddCommand(NewCmdVersion(f, ioStreams))
cmds.AddCommand(NewCmdApiVersions(f, ioStreams))
cmds.AddCommand(NewCmdApiResources(f, ioStreams))
cmds.AddCommand(NewCmdOptions(ioStreams.Out))
cmds.AddCommand(plugin.NewCmdPlugin(f, ioStreams))
cmds.AddCommand(version.NewCmdVersion(f, ioStreams))
cmds.AddCommand(apiresources.NewCmdApiVersions(f, ioStreams))
cmds.AddCommand(apiresources.NewCmdApiResources(f, ioStreams))
cmds.AddCommand(options.NewCmdOptions(ioStreams.Out))
return cmds
}
......@@ -524,10 +555,6 @@ func runHelp(cmd *cobra.Command, args []string) {
cmd.Help()
}
func printDeprecationWarning(errOut io.Writer, command, alias string) {
fmt.Fprintf(errOut, "%s is DEPRECATED and will be removed in a future version. Use %s instead.\n", alias, command)
}
// deprecatedAlias is intended to be used to create a "wrapper" command around
// an existing command. The wrapper works the same but prints a deprecation
// message before running. This command is identical functionality.
......@@ -542,5 +569,3 @@ func deprecatedAlias(deprecatedVersion string, cmd *cobra.Command) *cobra.Comman
cmd.Hidden = true
return cmd
}
var metadataAccessor = meta.NewAccessor()
......@@ -18,127 +18,19 @@ package cmd
import (
"bytes"
"encoding/json"
"fmt"
"io"
"io/ioutil"
"net/http"
"os"
"reflect"
stdstrings "strings"
"strings"
"testing"
"github.com/spf13/cobra"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/cli-runtime/pkg/genericclioptions"
restclient "k8s.io/client-go/rest"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/scheme"
)
func initTestErrorHandler(t *testing.T) {
cmdutil.BehaviorOnFatal(func(str string, code int) {
t.Errorf("Error running command (exit code %d): %s", code, str)
})
}
func defaultHeader() http.Header {
header := http.Header{}
header.Set("Content-Type", runtime.ContentTypeJSON)
return header
}
func defaultClientConfig() *restclient.Config {
return &restclient.Config{
APIPath: "/api",
ContentConfig: restclient.ContentConfig{
NegotiatedSerializer: scheme.Codecs,
ContentType: runtime.ContentTypeJSON,
GroupVersion: &corev1.SchemeGroupVersion,
},
}
}
func testData() (*corev1.PodList, *corev1.ServiceList, *corev1.ReplicationControllerList) {
grace := int64(30)
enableServiceLinks := corev1.DefaultEnableServiceLinks
pods := &corev1.PodList{
ListMeta: metav1.ListMeta{
ResourceVersion: "15",
},
Items: []corev1.Pod{
{
ObjectMeta: metav1.ObjectMeta{Name: "foo", Namespace: "test", ResourceVersion: "10"},
Spec: corev1.PodSpec{
RestartPolicy: corev1.RestartPolicyAlways,
DNSPolicy: corev1.DNSClusterFirst,
TerminationGracePeriodSeconds: &grace,
SecurityContext: &corev1.PodSecurityContext{},
EnableServiceLinks: &enableServiceLinks,
},
},
{
ObjectMeta: metav1.ObjectMeta{Name: "bar", Namespace: "test", ResourceVersion: "11"},
Spec: corev1.PodSpec{
RestartPolicy: corev1.RestartPolicyAlways,
DNSPolicy: corev1.DNSClusterFirst,
TerminationGracePeriodSeconds: &grace,
SecurityContext: &corev1.PodSecurityContext{},
EnableServiceLinks: &enableServiceLinks,
},
},
},
}
svc := &corev1.ServiceList{
ListMeta: metav1.ListMeta{
ResourceVersion: "16",
},
Items: []corev1.Service{
{
ObjectMeta: metav1.ObjectMeta{Name: "baz", Namespace: "test", ResourceVersion: "12"},
Spec: corev1.ServiceSpec{
SessionAffinity: "None",
Type: corev1.ServiceTypeClusterIP,
},
},
},
}
rc := &corev1.ReplicationControllerList{
ListMeta: metav1.ListMeta{
ResourceVersion: "17",
},
Items: []corev1.ReplicationController{
{
ObjectMeta: metav1.ObjectMeta{Name: "rc1", Namespace: "test", ResourceVersion: "18"},
Spec: corev1.ReplicationControllerSpec{
Replicas: int32ptr(1),
},
},
},
}
return pods, svc, rc
}
func int32ptr(val int) *int32 {
t := int32(val)
return &t
}
func objBody(codec runtime.Codec, obj runtime.Object) io.ReadCloser {
return ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(codec, obj))))
}
func bytesBody(bodyBytes []byte) io.ReadCloser {
return ioutil.NopCloser(bytes.NewReader(bodyBytes))
}
func stringBody(body string) io.ReadCloser {
return ioutil.NopCloser(bytes.NewReader([]byte(body)))
}
func TestNormalizationFuncGlobalExistence(t *testing.T) {
// This test can be safely deleted when we will not support multiple flag formats
root := NewKubectlCommand(os.Stdin, os.Stdout, os.Stderr)
......@@ -165,14 +57,6 @@ func TestNormalizationFuncGlobalExistence(t *testing.T) {
}
}
func genResponseWithJsonEncodedBody(bodyStruct interface{}) (*http.Response, error) {
jsonBytes, err := json.Marshal(bodyStruct)
if err != nil {
return nil, err
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: bytesBody(jsonBytes)}, nil
}
func Test_deprecatedAlias(t *testing.T) {
var correctCommandCalled bool
makeCobraCommand := func() *cobra.Command {
......@@ -190,7 +74,7 @@ func Test_deprecatedAlias(t *testing.T) {
if len(alias.Deprecated) == 0 {
t.Error("deprecatedAlias should always have a non-empty .Deprecated")
}
if !stdstrings.Contains(alias.Deprecated, "print") {
if !strings.Contains(alias.Deprecated, "print") {
t.Error("deprecatedAlias should give the name of the new function in its .Deprecated field")
}
if !alias.Hidden {
......@@ -210,7 +94,7 @@ func Test_deprecatedAlias(t *testing.T) {
alias.SetOutput(buffer)
alias.Execute()
str := buffer.String()
if !stdstrings.Contains(str, "deprecated") || !stdstrings.Contains(str, "print") {
if !strings.Contains(str, "deprecated") || !strings.Contains(str, "print") {
t.Errorf("deprecation warning %q does not include enough information", str)
}
......@@ -240,7 +124,7 @@ func TestKubectlCommandHandlesPlugins(t *testing.T) {
{
name: "test that a plugin executable is found based on command args",
args: []string{"kubectl", "foo", "--bar"},
expectPlugin: "testdata/plugin/kubectl-foo",
expectPlugin: "plugin/testdata/kubectl-foo",
expectPluginArgs: []string{"foo", "--bar"},
},
{
......@@ -252,7 +136,7 @@ func TestKubectlCommandHandlesPlugins(t *testing.T) {
for _, test := range tests {
t.Run(test.name, func(t *testing.T) {
pluginsHandler := &testPluginHandler{
pluginsDirectory: "testdata/plugin",
pluginsDirectory: "plugin/testdata",
}
_, in, out, errOut := genericclioptions.NewTestIOStreams()
......
......@@ -43,7 +43,7 @@ func TestConvertObject(t *testing.T) {
testcases := []testcase{
{
name: "apps deployment to extensions deployment",
file: "../../../test/fixtures/pkg/kubectl/cmd/convert/appsdeployment.yaml",
file: "../../../../test/fixtures/pkg/kubectl/cmd/convert/appsdeployment.yaml",
outputVersion: "extensions/v1beta1",
fields: []checkField{
{
......@@ -53,7 +53,7 @@ func TestConvertObject(t *testing.T) {
},
{
name: "extensions deployment to apps deployment",
file: "../../../test/fixtures/pkg/kubectl/cmd/convert/extensionsdeployment.yaml",
file: "../../../../test/fixtures/pkg/kubectl/cmd/convert/extensionsdeployment.yaml",
outputVersion: "apps/v1beta2",
fields: []checkField{
{
......@@ -63,7 +63,7 @@ func TestConvertObject(t *testing.T) {
},
{
name: "v1 HPA to v2beta1 HPA",
file: "../../../test/fixtures/pkg/kubectl/cmd/convert/v1HPA.yaml",
file: "../../../../test/fixtures/pkg/kubectl/cmd/convert/v1HPA.yaml",
outputVersion: "autoscaling/v2beta1",
fields: []checkField{
{
......@@ -79,7 +79,7 @@ func TestConvertObject(t *testing.T) {
},
{
name: "v2beta1 HPA to v1 HPA",
file: "../../../test/fixtures/pkg/kubectl/cmd/convert/v2beta1HPA.yaml",
file: "../../../../test/fixtures/pkg/kubectl/cmd/convert/v2beta1HPA.yaml",
outputVersion: "autoscaling/v1",
fields: []checkField{
{
......
......@@ -30,6 +30,7 @@ import (
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/client-go/kubernetes"
restclient "k8s.io/client-go/rest"
"k8s.io/kubernetes/pkg/kubectl/cmd/exec"
"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/util/i18n"
......@@ -197,8 +198,8 @@ func (o *CopyOptions) Run(args []string) error {
// pod. If the destination path does not exist or is _not_ a
// directory, an error is returned with the exit code received.
func (o *CopyOptions) checkDestinationIsDir(dest fileSpec) error {
options := &ExecOptions{
StreamOptions: StreamOptions{
options := &exec.ExecOptions{
StreamOptions: exec.StreamOptions{
IOStreams: genericclioptions.IOStreams{
Out: bytes.NewBuffer([]byte{}),
ErrOut: bytes.NewBuffer([]byte{}),
......@@ -209,7 +210,7 @@ func (o *CopyOptions) checkDestinationIsDir(dest fileSpec) error {
},
Command: []string{"test", "-d", dest.File},
Executor: &DefaultRemoteExecutor{},
Executor: &exec.DefaultRemoteExecutor{},
}
return o.execute(options)
......@@ -245,8 +246,8 @@ func (o *CopyOptions) copyToPod(src, dest fileSpec) error {
cmdArr = append(cmdArr, "-C", destDir)
}
options := &ExecOptions{
StreamOptions: StreamOptions{
options := &exec.ExecOptions{
StreamOptions: exec.StreamOptions{
IOStreams: genericclioptions.IOStreams{
In: reader,
Out: o.Out,
......@@ -259,7 +260,7 @@ func (o *CopyOptions) copyToPod(src, dest fileSpec) error {
},
Command: cmdArr,
Executor: &DefaultRemoteExecutor{},
Executor: &exec.DefaultRemoteExecutor{},
}
return o.execute(options)
}
......@@ -270,8 +271,8 @@ func (o *CopyOptions) copyFromPod(src, dest fileSpec) error {
}
reader, outStream := io.Pipe()
options := &ExecOptions{
StreamOptions: StreamOptions{
options := &exec.ExecOptions{
StreamOptions: exec.StreamOptions{
IOStreams: genericclioptions.IOStreams{
In: nil,
Out: outStream,
......@@ -284,7 +285,7 @@ func (o *CopyOptions) copyFromPod(src, dest fileSpec) error {
// TODO: Improve error messages by first testing if 'tar' is present in the container?
Command: []string{"tar", "cf", "-", src.File},
Executor: &DefaultRemoteExecutor{},
Executor: &exec.DefaultRemoteExecutor{},
}
go func() {
......@@ -460,7 +461,7 @@ func getPrefix(file string) string {
return strings.TrimLeft(file, "/")
}
func (o *CopyOptions) execute(options *ExecOptions) error {
func (o *CopyOptions) execute(options *exec.ExecOptions) error {
if len(options.Namespace) == 0 {
options.Namespace = o.Namespace
}
......
......@@ -527,11 +527,11 @@ func TestCopyToPod(t *testing.T) {
NegotiatedSerializer: ns,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
responsePod := &v1.Pod{}
return &http.Response{StatusCode: http.StatusNotFound, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(codec, responsePod))))}, nil
return &http.Response{StatusCode: http.StatusNotFound, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(codec, responsePod))))}, nil
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ioStreams, _, _, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdCp(tf, ioStreams)
......
......@@ -24,9 +24,7 @@ import (
"k8s.io/apimachinery/pkg/apis/meta/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/cli-runtime/pkg/genericclioptions"
restclient "k8s.io/client-go/rest"
"k8s.io/client-go/rest/fake"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
"k8s.io/kubernetes/pkg/kubectl/scheme"
......@@ -39,7 +37,7 @@ func TestCreateClusterRole(t *testing.T) {
defer tf.Cleanup()
tf.Client = &fake.RESTClient{}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
tests := map[string]struct {
verbs string
......@@ -514,14 +512,3 @@ func TestClusterRoleValidate(t *testing.T) {
})
}
}
func defaultClientConfig() *restclient.Config {
return &restclient.Config{
APIPath: "/api",
ContentConfig: restclient.ContentConfig{
NegotiatedSerializer: scheme.Codecs,
ContentType: runtime.ContentTypeJSON,
GroupVersion: &schema.GroupVersion{Version: "v1"},
},
}
}
......@@ -101,7 +101,7 @@ func TestCreateClusterRoleBinding(t *testing.T) {
responseBinding := &rbac.ClusterRoleBinding{}
responseBinding.Name = "fake-binding"
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(encoder, responseBinding))))}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(encoder, responseBinding))))}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -145,9 +145,3 @@ func (c *ClusterRoleBindingRESTClient) Post() *restclient.Request {
}
return restclient.NewRequest(c, "POST", &url.URL{Host: "localhost"}, c.VersionedAPIPath, config, serializers, nil, nil, 0)
}
func defaultHeader() http.Header {
header := http.Header{}
header.Set("Content-Type", runtime.ContentTypeJSON)
return header
}
......@@ -17,14 +17,10 @@ limitations under the License.
package create
import (
"bytes"
"io"
"io/ioutil"
"net/http"
"testing"
"k8s.io/api/core/v1"
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/client-go/rest/fake"
......@@ -47,7 +43,7 @@ func TestCreateConfigMap(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/configmaps" && m == "POST":
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: objBody(codec, configMap)}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, configMap)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -63,7 +59,3 @@ func TestCreateConfigMap(t *testing.T) {
t.Errorf("expected output: %s, but got: %s", expectedOutput, buf.String())
}
}
func objBody(codec runtime.Codec, obj runtime.Object) io.ReadCloser {
return ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(codec, obj))))
}
......@@ -43,7 +43,7 @@ func TestCreateNamespace(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces" && m == "POST":
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: objBody(codec, namespaceObject)}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, namespaceObject)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......
......@@ -38,7 +38,7 @@ func TestCreateRole(t *testing.T) {
defer tf.Cleanup()
tf.Client = &fake.RESTClient{}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
tests := map[string]struct {
verbs string
......@@ -358,7 +358,7 @@ func TestComplete(t *testing.T) {
defer tf.Cleanup()
tf.Client = &fake.RESTClient{}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
defaultTestResources := "pods,deployments.extensions"
......
......@@ -103,7 +103,7 @@ func TestCreateRoleBinding(t *testing.T) {
responseBinding := &rbac.RoleBinding{}
responseBinding.Name = "fake-binding"
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(encoder, responseBinding))))}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(encoder, responseBinding))))}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......
......@@ -48,7 +48,7 @@ func TestCreateSecretGeneric(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/secrets" && m == "POST":
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: objBody(codec, secretObject)}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, secretObject)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -80,7 +80,7 @@ func TestCreateSecretDockerRegistry(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/secrets" && m == "POST":
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: objBody(codec, secretObject)}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, secretObject)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......
......@@ -43,7 +43,7 @@ func TestCreateService(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/services" && m == "POST":
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: objBody(codec, service)}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, service)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -76,7 +76,7 @@ func TestCreateServiceNodePort(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/services" && m == http.MethodPost:
return &http.Response{StatusCode: http.StatusCreated, Header: defaultHeader(), Body: objBody(codec, service)}, nil
return &http.Response{StatusCode: http.StatusCreated, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, service)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -109,7 +109,7 @@ func TestCreateServiceExternalName(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/services" && m == http.MethodPost:
return &http.Response{StatusCode: http.StatusCreated, Header: defaultHeader(), Body: objBody(codec, service)}, nil
return &http.Response{StatusCode: http.StatusCreated, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, service)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......
......@@ -43,7 +43,7 @@ func TestCreateServiceAccount(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/serviceaccounts" && m == "POST":
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: objBody(codec, serviceAccountObject)}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, serviceAccountObject)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......
......@@ -20,19 +20,16 @@ import (
"net/http"
"testing"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
"k8s.io/client-go/rest/fake"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/scheme"
)
func TestExtraArgsFail(t *testing.T) {
initTestErrorHandler(t)
cmdtesting.InitTestErrorHandler(t)
f := cmdtesting.NewTestFactory()
defer f.Cleanup()
......@@ -45,8 +42,8 @@ func TestExtraArgsFail(t *testing.T) {
}
func TestCreateObject(t *testing.T) {
initTestErrorHandler(t)
_, _, rc := testData()
cmdtesting.InitTestErrorHandler(t)
_, _, rc := cmdtesting.TestData()
rc.Items[0].Name = "redis-master-controller"
tf := cmdtesting.NewTestFactory().WithNamespace("test")
......@@ -56,11 +53,11 @@ func TestCreateObject(t *testing.T) {
tf.UnstructuredClient = &fake.RESTClient{
GroupVersion: schema.GroupVersion{Version: "v1"},
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/replicationcontrollers" && m == http.MethodPost:
return &http.Response{StatusCode: http.StatusCreated, Header: defaultHeader(), Body: objBody(codec, &rc.Items[0])}, nil
return &http.Response{StatusCode: http.StatusCreated, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &rc.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -81,8 +78,8 @@ func TestCreateObject(t *testing.T) {
}
func TestCreateMultipleObject(t *testing.T) {
initTestErrorHandler(t)
_, svc, rc := testData()
cmdtesting.InitTestErrorHandler(t)
_, svc, rc := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
......@@ -91,13 +88,13 @@ func TestCreateMultipleObject(t *testing.T) {
tf.UnstructuredClient = &fake.RESTClient{
GroupVersion: schema.GroupVersion{Version: "v1"},
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/services" && m == http.MethodPost:
return &http.Response{StatusCode: http.StatusCreated, Header: defaultHeader(), Body: objBody(codec, &svc.Items[0])}, nil
return &http.Response{StatusCode: http.StatusCreated, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &svc.Items[0])}, nil
case p == "/namespaces/test/replicationcontrollers" && m == http.MethodPost:
return &http.Response{StatusCode: http.StatusCreated, Header: defaultHeader(), Body: objBody(codec, &rc.Items[0])}, nil
return &http.Response{StatusCode: http.StatusCreated, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &rc.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -119,8 +116,8 @@ func TestCreateMultipleObject(t *testing.T) {
}
func TestCreateDirectory(t *testing.T) {
initTestErrorHandler(t)
_, _, rc := testData()
cmdtesting.InitTestErrorHandler(t)
_, _, rc := cmdtesting.TestData()
rc.Items[0].Name = "name"
tf := cmdtesting.NewTestFactory().WithNamespace("test")
......@@ -130,11 +127,11 @@ func TestCreateDirectory(t *testing.T) {
tf.UnstructuredClient = &fake.RESTClient{
GroupVersion: schema.GroupVersion{Version: "v1"},
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/replicationcontrollers" && m == http.MethodPost:
return &http.Response{StatusCode: http.StatusCreated, Header: defaultHeader(), Body: objBody(codec, &rc.Items[0])}, nil
return &http.Response{StatusCode: http.StatusCreated, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &rc.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -152,69 +149,3 @@ func TestCreateDirectory(t *testing.T) {
t.Errorf("unexpected output: %s", buf.String())
}
}
var unstructuredSerializer = resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer
func initTestErrorHandler(t *testing.T) {
cmdutil.BehaviorOnFatal(func(str string, code int) {
t.Errorf("Error running command (exit code %d): %s", code, str)
})
}
func testData() (*corev1.PodList, *corev1.ServiceList, *corev1.ReplicationControllerList) {
grace := int64(30)
pods := &corev1.PodList{
ListMeta: metav1.ListMeta{
ResourceVersion: "15",
},
Items: []corev1.Pod{
{
ObjectMeta: metav1.ObjectMeta{Name: "foo", Namespace: "test", ResourceVersion: "10"},
Spec: corev1.PodSpec{
RestartPolicy: corev1.RestartPolicyAlways,
DNSPolicy: corev1.DNSClusterFirst,
TerminationGracePeriodSeconds: &grace,
SecurityContext: &corev1.PodSecurityContext{},
},
},
{
ObjectMeta: metav1.ObjectMeta{Name: "bar", Namespace: "test", ResourceVersion: "11"},
Spec: corev1.PodSpec{
RestartPolicy: corev1.RestartPolicyAlways,
DNSPolicy: corev1.DNSClusterFirst,
TerminationGracePeriodSeconds: &grace,
SecurityContext: &corev1.PodSecurityContext{},
},
},
},
}
svc := &corev1.ServiceList{
ListMeta: metav1.ListMeta{
ResourceVersion: "16",
},
Items: []corev1.Service{
{
ObjectMeta: metav1.ObjectMeta{Name: "baz", Namespace: "test", ResourceVersion: "12"},
Spec: corev1.ServiceSpec{
SessionAffinity: "None",
Type: corev1.ServiceTypeClusterIP,
},
},
},
}
one := int32(1)
rc := &corev1.ReplicationControllerList{
ListMeta: metav1.ListMeta{
ResourceVersion: "17",
},
Items: []corev1.ReplicationController{
{
ObjectMeta: metav1.ObjectMeta{Name: "rc1", Namespace: "test", ResourceVersion: "18"},
Spec: corev1.ReplicationControllerSpec{
Replicas: &one,
},
},
},
}
return pods, svc, rc
}
......@@ -24,6 +24,7 @@ import (
"k8s.io/apimachinery/pkg/api/meta"
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
"k8s.io/client-go/rest/fake"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
......@@ -45,8 +46,8 @@ func TestDescribeUnknownSchemaObject(t *testing.T) {
_, _, codec := cmdtesting.NewExternalScheme()
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
Resp: &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, cmdtesting.NewInternalType("", "", "foo"))},
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Resp: &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, cmdtesting.NewInternalType("", "", "foo"))},
}
streams, _, buf, _ := genericclioptions.NewTestIOStreams()
......@@ -77,8 +78,8 @@ func TestDescribeUnknownNamespacedSchemaObject(t *testing.T) {
_, _, codec := cmdtesting.NewExternalScheme()
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
Resp: &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, cmdtesting.NewInternalNamespacedType("", "", "foo", "non-default"))},
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Resp: &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, cmdtesting.NewInternalNamespacedType("", "", "foo", "non-default"))},
}
tf.WithNamespace("non-default")
......@@ -104,17 +105,17 @@ func TestDescribeObject(t *testing.T) {
}()
cmdutil.DescriberFn = d.describerFor
_, _, rc := testData()
_, _, rc := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/replicationcontrollers/redis-master" && m == "GET":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &rc.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &rc.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -125,7 +126,7 @@ func TestDescribeObject(t *testing.T) {
streams, _, buf, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdDescribe("kubectl", tf, streams)
cmd.Flags().Set("filename", "../../../test/e2e/testing-manifests/guestbook/legacy/redis-master-controller.yaml")
cmd.Flags().Set("filename", "../../../../test/e2e/testing-manifests/guestbook/legacy/redis-master-controller.yaml")
cmd.Run(cmd, []string{})
if d.Name != "redis-master" || d.Namespace != "test" {
......@@ -145,14 +146,14 @@ func TestDescribeListObjects(t *testing.T) {
}()
cmdutil.DescriberFn = d.describerFor
pods, _, _ := testData()
pods, _, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
Resp: &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, pods)},
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Resp: &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, pods)},
}
streams, _, buf, _ := genericclioptions.NewTestIOStreams()
......@@ -172,14 +173,14 @@ func TestDescribeObjectShowEvents(t *testing.T) {
}()
cmdutil.DescriberFn = d.describerFor
pods, _, _ := testData()
pods, _, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
Resp: &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, pods)},
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Resp: &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, pods)},
}
cmd := NewCmdDescribe("kubectl", tf, genericclioptions.NewTestIOStreamsDiscard())
......@@ -198,14 +199,14 @@ func TestDescribeObjectSkipEvents(t *testing.T) {
}()
cmdutil.DescriberFn = d.describerFor
pods, _, _ := testData()
pods, _, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
Resp: &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, pods)},
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Resp: &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, pods)},
}
cmd := NewCmdDescribe("kubectl", tf, genericclioptions.NewTestIOStreamsDiscard())
......
......@@ -34,6 +34,7 @@ import (
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
"k8s.io/kubernetes/pkg/kubectl"
"k8s.io/kubernetes/pkg/kubectl/cmd/apply"
"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/cmd/util/openapi"
......@@ -259,16 +260,16 @@ func (obj InfoObject) Merged() (runtime.Object, error) {
// This is using the patcher from apply, to keep the same behavior.
// We plan on replacing this with server-side apply when it becomes available.
patcher := &patcher{
mapping: obj.Info.Mapping,
helper: resource.NewHelper(obj.Info.Client, obj.Info.Mapping),
overwrite: true,
backOff: clockwork.NewRealClock(),
serverDryRun: true,
openapiSchema: obj.OpenAPI,
patcher := &apply.Patcher{
Mapping: obj.Info.Mapping,
Helper: resource.NewHelper(obj.Info.Client, obj.Info.Mapping),
Overwrite: true,
BackOff: clockwork.NewRealClock(),
ServerDryRun: true,
OpenapiSchema: obj.OpenAPI,
}
_, result, err := patcher.patch(obj.Info.Object, modified, obj.Info.Source, obj.Info.Namespace, obj.Info.Name, nil)
_, result, err := patcher.Patch(obj.Info.Object, modified, obj.Info.Source, obj.Info.Namespace, obj.Info.Name, nil)
return result, err
}
......
......@@ -161,9 +161,9 @@ func TestCordon(t *testing.T) {
m := &MyReq{req}
switch {
case m.isFor("GET", "/nodes/node"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, test.node)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, test.node)}, nil
case m.isFor("GET", "/nodes/bar"):
return &http.Response{StatusCode: 404, Header: defaultHeader(), Body: stringBody("nope")}, nil
return &http.Response{StatusCode: 404, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.StringBody("nope")}, nil
case m.isFor("PATCH", "/nodes/node"):
data, err := ioutil.ReadAll(req.Body)
if err != nil {
......@@ -185,14 +185,14 @@ func TestCordon(t *testing.T) {
t.Fatalf("%s: expected:\n%v\nsaw:\n%v\n", test.description, test.expected.Spec.Unschedulable, new_node.Spec.Unschedulable)
}
updated = true
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, new_node)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, new_node)}, nil
default:
t.Fatalf("%s: unexpected request: %v %#v\n%#v", test.description, req.Method, req.URL, req)
return nil, nil
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ioStreams, _, _, _ := genericclioptions.NewTestIOStreams()
cmd := test.cmd(tf, ioStreams)
......@@ -719,7 +719,7 @@ func TestDrain(t *testing.T) {
apiVersions := metav1.APIVersions{
Versions: []string{"v1"},
}
return genResponseWithJsonEncodedBody(apiVersions)
return cmdtesting.GenResponseWithJsonEncodedBody(apiVersions)
case req.Method == "GET" && req.URL.Path == "/apis":
groupList := metav1.APIGroupList{
Groups: []metav1.APIGroup{
......@@ -731,7 +731,7 @@ func TestDrain(t *testing.T) {
},
},
}
return genResponseWithJsonEncodedBody(groupList)
return cmdtesting.GenResponseWithJsonEncodedBody(groupList)
case req.Method == "GET" && req.URL.Path == "/api/v1":
resourceList := metav1.APIResourceList{
GroupVersion: "v1",
......@@ -744,21 +744,21 @@ func TestDrain(t *testing.T) {
},
}
}
return genResponseWithJsonEncodedBody(resourceList)
return cmdtesting.GenResponseWithJsonEncodedBody(resourceList)
case m.isFor("GET", "/nodes/node"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, test.node)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, test.node)}, nil
case m.isFor("GET", "/namespaces/default/replicationcontrollers/rc"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &test.rcs[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &test.rcs[0])}, nil
case m.isFor("GET", "/namespaces/default/daemonsets/ds"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &ds)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &ds)}, nil
case m.isFor("GET", "/namespaces/default/daemonsets/missing-ds"):
return &http.Response{StatusCode: 404, Header: defaultHeader(), Body: objBody(codec, &extensionsv1beta1.DaemonSet{})}, nil
return &http.Response{StatusCode: 404, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &extensionsv1beta1.DaemonSet{})}, nil
case m.isFor("GET", "/namespaces/default/jobs/job"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &job)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &job)}, nil
case m.isFor("GET", "/namespaces/default/replicasets/rs"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &test.replicaSets[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &test.replicaSets[0])}, nil
case m.isFor("GET", "/namespaces/default/pods/bar"):
return &http.Response{StatusCode: 404, Header: defaultHeader(), Body: objBody(codec, &corev1.Pod{})}, nil
return &http.Response{StatusCode: 404, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &corev1.Pod{})}, nil
case m.isFor("GET", "/pods"):
values, err := url.ParseQuery(req.URL.RawQuery)
if err != nil {
......@@ -769,9 +769,9 @@ func TestDrain(t *testing.T) {
if !reflect.DeepEqual(get_params, values) {
t.Fatalf("%s: expected:\n%v\nsaw:\n%v\n", test.description, get_params, values)
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &corev1.PodList{Items: test.pods})}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &corev1.PodList{Items: test.pods})}, nil
case m.isFor("GET", "/replicationcontrollers"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &corev1.ReplicationControllerList{Items: test.rcs})}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &corev1.ReplicationControllerList{Items: test.rcs})}, nil
case m.isFor("PATCH", "/nodes/node"):
data, err := ioutil.ReadAll(req.Body)
if err != nil {
......@@ -792,20 +792,20 @@ func TestDrain(t *testing.T) {
if !reflect.DeepEqual(test.expected.Spec, new_node.Spec) {
t.Fatalf("%s: expected:\n%v\nsaw:\n%v\n", test.description, test.expected.Spec, new_node.Spec)
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, new_node)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, new_node)}, nil
case m.isFor("DELETE", "/namespaces/default/pods/bar"):
deleted = true
return &http.Response{StatusCode: 204, Header: defaultHeader(), Body: objBody(codec, &test.pods[0])}, nil
return &http.Response{StatusCode: 204, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &test.pods[0])}, nil
case m.isFor("POST", "/namespaces/default/pods/bar/eviction"):
evicted = true
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: objBody(codec, &policyv1beta1.Eviction{})}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &policyv1beta1.Eviction{})}, nil
default:
t.Fatalf("%s: unexpected request: %v %#v\n%#v", test.description, req.Method, req.URL, req)
return nil, nil
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ioStreams, _, _, errBuf := genericclioptions.NewTestIOStreams()
cmd := NewCmdDrain(tf, ioStreams)
......
......@@ -38,6 +38,7 @@ import (
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
"k8s.io/client-go/rest/fake"
"k8s.io/kubernetes/pkg/kubectl/cmd/apply"
"k8s.io/kubernetes/pkg/kubectl/cmd/create"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
......@@ -102,13 +103,13 @@ func TestEdit(t *testing.T) {
}
}
inputFile := filepath.Join("testdata/edit", "testcase-"+name, step.Input)
inputFile := filepath.Join("testdata", "testcase-"+name, step.Input)
expectedInput, err := ioutil.ReadFile(inputFile)
if err != nil {
t.Fatalf("%s, step %d: %v", name, i, err)
}
outputFile := filepath.Join("testdata/edit", "testcase-"+name, step.Output)
outputFile := filepath.Join("testdata", "testcase-"+name, step.Output)
resultingOutput, err := ioutil.ReadFile(outputFile)
if err != nil {
t.Fatalf("%s, step %d: %v", name, i, err)
......@@ -150,7 +151,7 @@ func TestEdit(t *testing.T) {
t.Logf("If the change in input is expected, rerun tests with %s=true to update input fixtures", updateEnvVar)
}
}
return &http.Response{StatusCode: step.ResponseStatusCode, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader(resultingOutput))}, nil
return &http.Response{StatusCode: step.ResponseStatusCode, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader(resultingOutput))}, nil
}
}
......@@ -169,15 +170,15 @@ func TestEdit(t *testing.T) {
server := httptest.NewServer(handler)
defer server.Close()
os.Setenv("KUBE_EDITOR", "testdata/edit/test_editor.sh")
os.Setenv("KUBE_EDITOR", "testdata/test_editor.sh")
os.Setenv("KUBE_EDITOR_CALLBACK", server.URL+"/callback")
testcases := sets.NewString()
filepath.Walk("testdata/edit", func(path string, info os.FileInfo, err error) error {
filepath.Walk("testdata", func(path string, info os.FileInfo, err error) error {
if err != nil {
return err
}
if path == "testdata/edit" {
if path == "testdata" {
return nil
}
name := filepath.Base(path)
......@@ -199,7 +200,7 @@ func TestEdit(t *testing.T) {
i = 0
name = testcaseName
testcase = EditTestCase{}
testcaseDir := filepath.Join("testdata", "edit", "testcase-"+name)
testcaseDir := filepath.Join("testdata", "testcase-"+name)
testcaseData, err := ioutil.ReadFile(filepath.Join(testcaseDir, "test.yaml"))
if err != nil {
t.Fatalf("%s: %v", name, err)
......@@ -220,12 +221,12 @@ func TestEdit(t *testing.T) {
}
return &fake.RESTClient{
VersionedAPIPath: versionedAPIPath,
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(reqResp),
}, nil
}
tf.WithNamespace(testcase.Namespace)
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ioStreams, _, buf, errBuf := genericclioptions.NewTestIOStreams()
var cmd *cobra.Command
......@@ -236,7 +237,7 @@ func TestEdit(t *testing.T) {
cmd = create.NewCmdCreate(tf, ioStreams)
cmd.Flags().Set("edit", "true")
case "edit-last-applied":
cmd = NewCmdApplyEditLastApplied(tf, ioStreams)
cmd = apply.NewCmdApplyEditLastApplied(tf, ioStreams)
default:
t.Fatalf("%s: unexpected mode %s", name, testcase.Mode)
}
......
......@@ -212,7 +212,7 @@ func (p *ExecOptions) Validate() error {
return nil
}
func (o *StreamOptions) setupTTY() term.TTY {
func (o *StreamOptions) SetupTTY() term.TTY {
t := term.TTY{
Parent: o.InterruptParent,
Out: o.Out,
......@@ -288,7 +288,7 @@ func (p *ExecOptions) Run() error {
}
// ensure we can recover the terminal while attached
t := p.setupTTY()
t := p.SetupTTY()
var sizeQueue remotecommand.TerminalSizeQueue
if t.Raw {
......
......@@ -140,7 +140,7 @@ func TestPodAndContainer(t *testing.T) {
NegotiatedSerializer: ns,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) { return nil, nil }),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
cmd := &cobra.Command{}
options := test.p
......@@ -202,15 +202,15 @@ func TestExec(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == test.podPath && m == "GET":
body := objBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
body := cmdtesting.ObjBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
default:
t.Errorf("%s: unexpected request: %s %#v\n%#v", test.name, req.Method, req.URL, req)
return nil, fmt.Errorf("unexpected request")
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ex := &fakeRemoteExecutor{}
if test.execErr {
ex.execErr = fmt.Errorf("exec error")
......@@ -280,7 +280,7 @@ func TestSetupTTY(t *testing.T) {
TTY: true,
}
tty := o.setupTTY()
tty := o.SetupTTY()
if o.In != nil {
t.Errorf("don't attach stdin: o.In should be nil")
......@@ -304,7 +304,7 @@ func TestSetupTTY(t *testing.T) {
o.In = &bytes.Buffer{}
o.TTY = false
tty = o.setupTTY()
tty = o.SetupTTY()
if o.In == nil {
t.Errorf("attach stdin, no TTY: o.In should not be nil")
......@@ -328,7 +328,7 @@ func TestSetupTTY(t *testing.T) {
o.ErrOut = stderr
o.TTY = true
tty = o.setupTTY()
tty = o.SetupTTY()
if o.In == nil {
t.Errorf("attach stdin, TTY, not a terminal: o.In should not be nil")
......@@ -363,7 +363,7 @@ func TestSetupTTY(t *testing.T) {
return true
}
tty = o.setupTTY()
tty = o.SetupTTY()
if o.In != overrideStdin {
t.Errorf("attach stdin, TTY, is a terminal: o.In should equal overrideStdin")
......
......@@ -306,7 +306,7 @@ func TestRunExposeService(t *testing.T) {
Selector: map[string]string{"app": "go"},
},
},
flags: map[string]string{"filename": "../../../test/e2e/testing-manifests/guestbook/redis-master-service.yaml", "selector": "func=stream", "protocol": "UDP", "port": "14", "name": "foo", "labels": "svc=test", "dry-run": "true"},
flags: map[string]string{"filename": "../../../../test/e2e/testing-manifests/guestbook/redis-master-service.yaml", "selector": "func=stream", "protocol": "UDP", "port": "14", "name": "foo", "labels": "svc=test", "dry-run": "true"},
output: &corev1.Service{
ObjectMeta: metav1.ObjectMeta{Name: "foo", Labels: map[string]string{"svc": "test"}},
Spec: corev1.ServiceSpec{
......@@ -610,7 +610,7 @@ func TestRunExposeService(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == test.calls[m] && m == "GET":
return &http.Response{StatusCode: test.status, Header: defaultHeader(), Body: objBody(codec, test.input)}, nil
return &http.Response{StatusCode: test.status, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, test.input)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......
......@@ -27,6 +27,7 @@ import (
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
"k8s.io/client-go/rest/fake"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
"k8s.io/kubernetes/pkg/kubectl/scheme"
......@@ -324,7 +325,7 @@ func TestLabelErrors(t *testing.T) {
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ioStreams, _, _, _ := genericclioptions.NewTestIOStreams()
buf := bytes.NewBuffer([]byte{})
......@@ -354,20 +355,20 @@ func TestLabelErrors(t *testing.T) {
}
func TestLabelForResourceFromFile(t *testing.T) {
pods, _, _ := testData()
pods, _, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch req.Method {
case "GET":
switch req.URL.Path {
case "/namespaces/test/replicationcontrollers/cassandra":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -375,7 +376,7 @@ func TestLabelForResourceFromFile(t *testing.T) {
case "PATCH":
switch req.URL.Path {
case "/namespaces/test/replicationcontrollers/cassandra":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -386,12 +387,12 @@ func TestLabelForResourceFromFile(t *testing.T) {
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ioStreams, _, buf, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdLabel(tf, ioStreams)
opts := NewLabelOptions(ioStreams)
opts.Filenames = []string{"../../../test/e2e/testing-manifests/statefulset/cassandra/controller.yaml"}
opts.Filenames = []string{"../../../../test/e2e/testing-manifests/statefulset/cassandra/controller.yaml"}
err := opts.Complete(tf, cmd, []string{"a=b"})
if err == nil {
err = opts.Validate()
......@@ -412,18 +413,18 @@ func TestLabelLocal(t *testing.T) {
defer tf.Cleanup()
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
t.Fatalf("unexpected request: %s %#v\n%#v", req.Method, req.URL, req)
return nil, nil
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ioStreams, _, buf, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdLabel(tf, ioStreams)
opts := NewLabelOptions(ioStreams)
opts.Filenames = []string{"../../../test/e2e/testing-manifests/statefulset/cassandra/controller.yaml"}
opts.Filenames = []string{"../../../../test/e2e/testing-manifests/statefulset/cassandra/controller.yaml"}
opts.local = true
err := opts.Complete(tf, cmd, []string{"a=b"})
if err == nil {
......@@ -441,20 +442,20 @@ func TestLabelLocal(t *testing.T) {
}
func TestLabelMultipleObjects(t *testing.T) {
pods, _, _ := testData()
pods, _, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch req.Method {
case "GET":
switch req.URL.Path {
case "/namespaces/test/pods":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, pods)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, pods)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -462,9 +463,9 @@ func TestLabelMultipleObjects(t *testing.T) {
case "PATCH":
switch req.URL.Path {
case "/namespaces/test/pods/foo":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])}, nil
case "/namespaces/test/pods/bar":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &pods.Items[1])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[1])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -475,7 +476,7 @@ func TestLabelMultipleObjects(t *testing.T) {
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ioStreams, _, buf, _ := genericclioptions.NewTestIOStreams()
opts := NewLabelOptions(ioStreams)
......
......@@ -75,6 +75,10 @@ var (
logsUsageErrStr = fmt.Sprintf("expected '%s'.\nPOD or TYPE/NAME is a required argument for the logs command", logsUsageStr)
)
const (
defaultPodLogsTimeout = 20 * time.Second
)
type LogsOptions struct {
Namespace string
ResourceArg string
......@@ -126,7 +130,7 @@ func NewCmdLogs(f cmdutil.Factory, streams genericclioptions.IOStreams) *cobra.C
Example: logsExample,
PreRun: func(cmd *cobra.Command, args []string) {
if len(os.Args) > 1 && os.Args[1] == "log" {
printDeprecationWarning(o.ErrOut, "logs", "log")
fmt.Fprintf(o.ErrOut, "%s is DEPRECATED and will be removed in a future version. Use %s instead.\n", "log", "logs")
}
},
Run: func(cmd *cobra.Command, args []string) {
......
......@@ -22,13 +22,14 @@ import (
"testing"
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
"k8s.io/client-go/rest/fake"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
"k8s.io/kubernetes/pkg/kubectl/scheme"
)
func TestPatchObject(t *testing.T) {
_, svc, _ := testData()
_, svc, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
......@@ -36,7 +37,7 @@ func TestPatchObject(t *testing.T) {
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/services/frontend" && (m == "PATCH" || m == "GET"):
......@@ -47,7 +48,7 @@ func TestPatchObject(t *testing.T) {
if m == "PATCH" {
obj.Spec.Type = "NodePort"
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &obj)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &obj)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -69,7 +70,7 @@ func TestPatchObject(t *testing.T) {
}
func TestPatchObjectFromFile(t *testing.T) {
_, svc, _ := testData()
_, svc, _ := cmdtesting.TestData()
tf := cmdtesting.NewTestFactory().WithNamespace("test")
defer tf.Cleanup()
......@@ -77,11 +78,11 @@ func TestPatchObjectFromFile(t *testing.T) {
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/services/frontend" && (m == "PATCH" || m == "GET"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &svc.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &svc.Items[0])}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -94,7 +95,7 @@ func TestPatchObjectFromFile(t *testing.T) {
cmd.Flags().Set("namespace", "test")
cmd.Flags().Set("patch", `{"spec":{"type":"NodePort"}}`)
cmd.Flags().Set("output", "name")
cmd.Flags().Set("filename", "../../../test/e2e/testing-manifests/guestbook/frontend-service.yaml")
cmd.Flags().Set("filename", "../../../../test/e2e/testing-manifests/guestbook/frontend-service.yaml")
cmd.Run(cmd, []string{})
// uses the name from the response
......@@ -104,7 +105,7 @@ func TestPatchObjectFromFile(t *testing.T) {
}
func TestPatchNoop(t *testing.T) {
_, svc, _ := testData()
_, svc, _ := cmdtesting.TestData()
getObject := &svc.Items[0]
patchObject := &svc.Items[0]
......@@ -114,13 +115,13 @@ func TestPatchNoop(t *testing.T) {
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/services/frontend" && m == "PATCH":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, patchObject)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, patchObject)}, nil
case p == "/namespaces/test/services/frontend" && m == "GET":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, getObject)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, getObject)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -147,7 +148,7 @@ func TestPatchNoop(t *testing.T) {
}
func TestPatchObjectFromFileOutput(t *testing.T) {
_, svc, _ := testData()
_, svc, _ := cmdtesting.TestData()
svcCopy := svc.Items[0].DeepCopy()
if svcCopy.Labels == nil {
......@@ -161,13 +162,13 @@ func TestPatchObjectFromFileOutput(t *testing.T) {
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
tf.UnstructuredClient = &fake.RESTClient{
NegotiatedSerializer: unstructuredSerializer,
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/services/frontend" && m == "GET":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, &svc.Items[0])}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &svc.Items[0])}, nil
case p == "/namespaces/test/services/frontend" && m == "PATCH":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, svcCopy)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, svcCopy)}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -180,7 +181,7 @@ func TestPatchObjectFromFileOutput(t *testing.T) {
cmd.Flags().Set("namespace", "test")
cmd.Flags().Set("patch", `{"spec":{"type":"NodePort"}}`)
cmd.Flags().Set("output", "yaml")
cmd.Flags().Set("filename", "../../../test/e2e/testing-manifests/guestbook/frontend-service.yaml")
cmd.Flags().Set("filename", "../../../../test/e2e/testing-manifests/guestbook/frontend-service.yaml")
cmd.Run(cmd, []string{})
t.Log(buf.String())
......
......@@ -26,6 +26,7 @@ import (
"github.com/spf13/cobra"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/apimachinery/pkg/util/intstr"
"k8s.io/cli-runtime/pkg/genericclioptions"
......@@ -85,15 +86,15 @@ func testPortForward(t *testing.T, flags map[string]string, args []string) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == test.podPath && m == "GET":
body := objBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
body := cmdtesting.ObjBody(codec, test.pod)
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
default:
t.Errorf("%s: unexpected request: %#v\n%#v", test.name, req.URL, req)
return nil, nil
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
ff := &fakePortForwarder{}
if test.pfErr {
ff.pfErr = fmt.Errorf("pf error")
......@@ -354,3 +355,21 @@ func TestTranslateServicePortToTargetPort(t *testing.T) {
}
}
}
func execPod() *corev1.Pod {
return &corev1.Pod{
ObjectMeta: metav1.ObjectMeta{Name: "foo", Namespace: "test", ResourceVersion: "10"},
Spec: corev1.PodSpec{
RestartPolicy: corev1.RestartPolicyAlways,
DNSPolicy: corev1.DNSClusterFirst,
Containers: []corev1.Container{
{
Name: "bar",
},
},
},
Status: corev1.PodStatus{
Phase: corev1.PodRunning,
},
}
}
......@@ -33,6 +33,7 @@ import (
"k8s.io/cli-runtime/pkg/genericclioptions"
"k8s.io/cli-runtime/pkg/genericclioptions/resource"
"k8s.io/kubernetes/pkg/kubectl"
"k8s.io/kubernetes/pkg/kubectl/cmd/delete"
"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/scheme"
......@@ -67,10 +68,10 @@ var (
type ReplaceOptions struct {
PrintFlags *genericclioptions.PrintFlags
DeleteFlags *DeleteFlags
RecordFlags *genericclioptions.RecordFlags
DeleteOptions *DeleteOptions
DeleteFlags *delete.DeleteFlags
DeleteOptions *delete.DeleteOptions
PrintObj func(obj runtime.Object) error
......@@ -92,7 +93,7 @@ type ReplaceOptions struct {
func NewReplaceOptions(streams genericclioptions.IOStreams) *ReplaceOptions {
return &ReplaceOptions{
PrintFlags: genericclioptions.NewPrintFlags("replaced"),
DeleteFlags: NewDeleteFlags("to use to replace the resource."),
DeleteFlags: delete.NewDeleteFlags("to use to replace the resource."),
IOStreams: streams,
}
......
......@@ -72,10 +72,10 @@ var (
kubectl rolling-update frontend-v1 frontend-v2 --rollback`))
)
var (
updatePeriod, _ = time.ParseDuration("1m0s")
timeout, _ = time.ParseDuration("5m0s")
pollInterval, _ = time.ParseDuration("3s")
const (
updatePeriod = 1 * time.Minute
timeout = 5 * time.Minute
pollInterval = 3 * time.Second
)
type RollingUpdateOptions struct {
......
......@@ -53,7 +53,7 @@ func TestRolloutPause(t *testing.T) {
responseDeployment := &extensionsv1beta1.Deployment{}
responseDeployment.Name = deploymentName
body := ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(encoder, responseDeployment))))
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: body}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: body}, nil
default:
t.Fatalf("unexpected request: %#v\n%#v", req.URL, req)
return nil, nil
......@@ -113,9 +113,3 @@ func (c *RolloutPauseRESTClient) Patch(pt types.PatchType) *restclient.Request {
}
return restclient.NewRequest(c, "PATCH", &url.URL{Host: "localhost"}, c.VersionedAPIPath, config, serializers, nil, nil, 0)
}
func defaultHeader() http.Header {
header := http.Header{}
header.Set("Content-Type", runtime.ContentTypeJSON)
return header
}
......@@ -39,6 +39,10 @@ import (
corev1client "k8s.io/client-go/kubernetes/typed/core/v1"
watchtools "k8s.io/client-go/tools/watch"
"k8s.io/kubernetes/pkg/kubectl"
"k8s.io/kubernetes/pkg/kubectl/cmd/attach"
"k8s.io/kubernetes/pkg/kubectl/cmd/delete"
"k8s.io/kubernetes/pkg/kubectl/cmd/exec"
"k8s.io/kubernetes/pkg/kubectl/cmd/logs"
"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/polymorphichelpers"
......@@ -92,16 +96,23 @@ var (
kubectl run pi --schedule="0/5 * * * ?" --image=perl --restart=OnFailure -- perl -Mbignum=bpi -wle 'print bpi(2000)'`))
)
const (
defaultPodAttachTimeout = 60 * time.Second
)
var metadataAccessor = meta.NewAccessor()
type RunObject struct {
Object runtime.Object
Mapping *meta.RESTMapping
}
type RunOptions struct {
PrintFlags *genericclioptions.PrintFlags
DeleteFlags *DeleteFlags
DeleteOptions *DeleteOptions
RecordFlags *genericclioptions.RecordFlags
PrintFlags *genericclioptions.PrintFlags
RecordFlags *genericclioptions.RecordFlags
DeleteFlags *delete.DeleteFlags
DeleteOptions *delete.DeleteOptions
DryRun bool
......@@ -128,7 +139,7 @@ type RunOptions struct {
func NewRunOptions(streams genericclioptions.IOStreams) *RunOptions {
return &RunOptions{
PrintFlags: genericclioptions.NewPrintFlags("created").WithTypeSetter(scheme.Scheme),
DeleteFlags: NewDeleteFlags("to use to replace the resource."),
DeleteFlags: delete.NewDeleteFlags("to use to replace the resource."),
RecordFlags: genericclioptions.NewRecordFlags(),
Recorder: genericclioptions.NoopRecorder{},
......@@ -369,8 +380,8 @@ func (o *RunOptions) Run(f cmdutil.Factory, cmd *cobra.Command, args []string) e
defer o.removeCreatedObjects(f, createdObjects)
}
opts := &AttachOptions{
StreamOptions: StreamOptions{
opts := &attach.AttachOptions{
StreamOptions: exec.StreamOptions{
IOStreams: o.IOStreams,
Stdin: o.Interactive,
TTY: o.TTY,
......@@ -379,14 +390,14 @@ func (o *RunOptions) Run(f cmdutil.Factory, cmd *cobra.Command, args []string) e
GetPodTimeout: timeout,
CommandName: cmd.Parent().CommandPath() + " attach",
Attach: &DefaultRemoteAttach{},
Attach: &attach.DefaultRemoteAttach{},
}
config, err := f.ToRESTConfig()
if err != nil {
return err
}
opts.Config = config
opts.AttachFunc = defaultAttachFunc
opts.AttachFunc = attach.DefaultAttachFunc
clientset, err := kubernetes.NewForConfig(config)
if err != nil {
......@@ -504,7 +515,7 @@ func waitForPod(podClient corev1client.PodsGetter, ns, name string, exitConditio
return result, err
}
func handleAttachPod(f cmdutil.Factory, podClient corev1client.PodsGetter, ns, name string, opts *AttachOptions) error {
func handleAttachPod(f cmdutil.Factory, podClient corev1client.PodsGetter, ns, name string, opts *attach.AttachOptions) error {
pod, err := waitForPod(podClient, ns, name, kubectl.PodRunningAndReady)
if err != nil && err != kubectl.ErrPodCompleted {
return err
......@@ -519,7 +530,7 @@ func handleAttachPod(f cmdutil.Factory, podClient corev1client.PodsGetter, ns, n
opts.Namespace = ns
if opts.AttachFunc == nil {
opts.AttachFunc = defaultAttachFunc
opts.AttachFunc = attach.DefaultAttachFunc
}
if err := opts.Run(); err != nil {
......@@ -530,7 +541,7 @@ func handleAttachPod(f cmdutil.Factory, podClient corev1client.PodsGetter, ns, n
}
// logOpts logs output from opts to the pods log.
func logOpts(restClientGetter genericclioptions.RESTClientGetter, pod *corev1.Pod, opts *AttachOptions) error {
func logOpts(restClientGetter genericclioptions.RESTClientGetter, pod *corev1.Pod, opts *attach.AttachOptions) error {
ctrName, err := opts.GetContainerName(pod)
if err != nil {
return err
......@@ -541,7 +552,7 @@ func logOpts(restClientGetter genericclioptions.RESTClientGetter, pod *corev1.Po
return err
}
for _, request := range requests {
if err := DefaultConsumeRequest(request, opts.Out); err != nil {
if err := logs.DefaultConsumeRequest(request, opts.Out); err != nil {
return err
}
}
......
......@@ -36,6 +36,7 @@ import (
"k8s.io/cli-runtime/pkg/genericclioptions"
restclient "k8s.io/client-go/rest"
"k8s.io/client-go/rest/fake"
"k8s.io/kubernetes/pkg/kubectl/cmd/delete"
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/scheme"
......@@ -174,7 +175,7 @@ func TestRunArgsFollowDashRules(t *testing.T) {
NegotiatedSerializer: ns,
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
if req.URL.Path == "/namespaces/test/replicationcontrollers" {
return &http.Response{StatusCode: 201, Header: defaultHeader(), Body: objBody(codec, rc)}, nil
return &http.Response{StatusCode: 201, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, rc)}, nil
}
return &http.Response{
StatusCode: http.StatusOK,
......@@ -196,7 +197,7 @@ func TestRunArgsFollowDashRules(t *testing.T) {
return
}
deleteFlags := NewDeleteFlags("to use to replace the resource.")
deleteFlags := delete.NewDeleteFlags("to use to replace the resource.")
opts := &RunOptions{
PrintFlags: printFlags,
DeleteOptions: deleteFlags.ToOptions(nil, genericclioptions.NewTestIOStreamsDiscard()),
......@@ -328,7 +329,7 @@ func TestGenerateService(t *testing.T) {
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
ns := scheme.Codecs
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
tf.Client = &fake.RESTClient{
GroupVersion: corev1.SchemeGroupVersion,
NegotiatedSerializer: ns,
......@@ -336,7 +337,7 @@ func TestGenerateService(t *testing.T) {
switch p, m := req.URL.Path, req.Method; {
case test.expectPOST && m == "POST" && p == "/namespaces/test/services":
sawPOST = true
body := objBody(codec, &test.service)
body := cmdtesting.ObjBody(codec, &test.service)
data, err := ioutil.ReadAll(req.Body)
if err != nil {
t.Fatalf("unexpected error: %v", err)
......@@ -352,7 +353,7 @@ func TestGenerateService(t *testing.T) {
if !apiequality.Semantic.DeepEqual(&test.service, svc) {
t.Errorf("expected:\n%v\nsaw:\n%v\n", &test.service, svc)
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
default:
t.Errorf("%s: unexpected request: %s %#v\n%#v", test.name, req.Method, req.URL, req)
return nil, fmt.Errorf("unexpected request")
......@@ -368,7 +369,7 @@ func TestGenerateService(t *testing.T) {
}
ioStreams, _, buff, _ := genericclioptions.NewTestIOStreams()
deleteFlags := NewDeleteFlags("to use to replace the resource.")
deleteFlags := delete.NewDeleteFlags("to use to replace the resource.")
opts := &RunOptions{
PrintFlags: printFlags,
DeleteOptions: deleteFlags.ToOptions(nil, genericclioptions.NewTestIOStreamsDiscard()),
......@@ -506,9 +507,9 @@ func TestRunValidations(t *testing.T) {
_, _, codec := cmdtesting.NewExternalScheme()
tf.Client = &fake.RESTClient{
NegotiatedSerializer: scheme.Codecs,
Resp: &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, cmdtesting.NewInternalType("", "", ""))},
Resp: &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, cmdtesting.NewInternalType("", "", ""))},
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
streams, _, _, bufErr := genericclioptions.NewTestIOStreams()
cmdutil.BehaviorOnFatal(func(str string, code int) {
......
......@@ -64,6 +64,10 @@ var (
kubectl scale --replicas=3 statefulset/web`))
)
const (
timeout = 5 * time.Minute
)
type ScaleOptions struct {
FilenameOptions resource.FilenameOptions
RecordFlags *genericclioptions.RecordFlags
......
......@@ -452,7 +452,7 @@ func TestSetEnvRemote(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == input.path && m == http.MethodGet:
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(input.object)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(input.object)}, nil
case p == input.path && m == http.MethodPatch:
stream, err := req.GetBody()
if err != nil {
......@@ -463,7 +463,7 @@ func TestSetEnvRemote(t *testing.T) {
return nil, err
}
assert.Contains(t, string(bytes), `"value":`+`"`+"prod"+`"`, fmt.Sprintf("env not updated for %#v", input.object))
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(input.object)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(input.object)}, nil
default:
t.Errorf("%s: unexpected request: %s %#v\n%#v", "image", req.Method, req.URL, req)
return nil, fmt.Errorf("unexpected request")
......@@ -587,11 +587,11 @@ func TestSetEnvFromResource(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == "/namespaces/test/configmaps/testconfigmap" && m == http.MethodGet:
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(mockConfigMap)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(mockConfigMap)}, nil
case p == "/namespaces/test/secrets/testsecret" && m == http.MethodGet:
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(mockSecret)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(mockSecret)}, nil
case p == "/namespaces/test/deployments/nginx" && m == http.MethodGet:
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(mockDeployment)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(mockDeployment)}, nil
case p == "/namespaces/test/deployments/nginx" && m == http.MethodPatch:
stream, err := req.GetBody()
if err != nil {
......@@ -607,7 +607,7 @@ func TestSetEnvFromResource(t *testing.T) {
for _, exclude := range input.assertExcludes {
assert.NotContains(t, string(bytes), exclude)
}
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(mockDeployment)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(mockDeployment)}, nil
default:
t.Errorf("%s: unexpected request: %#v\n%#v", input.name, req.URL, req)
return nil, nil
......
......@@ -535,7 +535,7 @@ func TestSetImageRemote(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == input.path && m == http.MethodGet:
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(input.object)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(input.object)}, nil
case p == input.path && m == http.MethodPatch:
stream, err := req.GetBody()
if err != nil {
......@@ -546,7 +546,7 @@ func TestSetImageRemote(t *testing.T) {
return nil, err
}
assert.Contains(t, string(bytes), `"image":`+`"`+"thingy"+`"`, fmt.Sprintf("image not updated for %#v", input.object))
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(input.object)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(input.object)}, nil
default:
t.Errorf("%s: unexpected request: %s %#v\n%#v", "image", req.Method, req.URL, req)
return nil, fmt.Errorf("unexpected request")
......
......@@ -475,7 +475,7 @@ func TestSetResourcesRemote(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == input.path && m == http.MethodGet:
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(input.object)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(input.object)}, nil
case p == input.path && m == http.MethodPatch:
stream, err := req.GetBody()
if err != nil {
......@@ -486,7 +486,7 @@ func TestSetResourcesRemote(t *testing.T) {
return nil, err
}
assert.Contains(t, string(bytes), "200m", fmt.Sprintf("resources not updated for %#v", input.object))
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(input.object)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(input.object)}, nil
default:
t.Errorf("%s: unexpected request: %s %#v\n%#v", "resources", req.Method, req.URL, req)
return nil, fmt.Errorf("unexpected request")
......
......@@ -17,7 +17,6 @@ limitations under the License.
package set
import (
"bytes"
"fmt"
"io"
"io/ioutil"
......@@ -327,7 +326,7 @@ func TestSetServiceAccountRemote(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m := req.URL.Path, req.Method; {
case p == input.path && m == http.MethodGet:
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(input.object)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(input.object)}, nil
case p == input.path && m == http.MethodPatch:
stream, err := req.GetBody()
if err != nil {
......@@ -338,7 +337,7 @@ func TestSetServiceAccountRemote(t *testing.T) {
return nil, err
}
assert.Contains(t, string(bytes), `"serviceAccountName":`+`"`+serviceAccount+`"`, fmt.Sprintf("serviceaccount not updated for %#v", input.object))
return &http.Response{StatusCode: http.StatusOK, Header: defaultHeader(), Body: objBody(input.object)}, nil
return &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: objBody(input.object)}, nil
default:
t.Errorf("%s: unexpected request: %s %#v\n%#v", "serviceaccount", req.Method, req.URL, req)
return nil, fmt.Errorf("unexpected request")
......@@ -403,15 +402,5 @@ func TestServiceAccountValidation(t *testing.T) {
}
func objBody(obj runtime.Object) io.ReadCloser {
return bytesBody([]byte(runtime.EncodeOrDie(scheme.DefaultJSONEncoder(), obj)))
}
func defaultHeader() http.Header {
header := http.Header{}
header.Set("Content-Type", runtime.ContentTypeJSON)
return header
}
func bytesBody(bodyBytes []byte) io.ReadCloser {
return ioutil.NopCloser(bytes.NewReader(bodyBytes))
return cmdtesting.BytesBody([]byte(runtime.EncodeOrDie(scheme.DefaultJSONEncoder(), obj)))
}
......@@ -20,6 +20,7 @@ import (
"io/ioutil"
"net/http"
"reflect"
"strings"
"testing"
"time"
......@@ -251,9 +252,9 @@ func TestTaint(t *testing.T) {
m := &MyReq{req}
switch {
case m.isFor("GET", "/nodes"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, oldNode)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, oldNode)}, nil
case m.isFor("GET", "/nodes/node-name"):
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, oldNode)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, oldNode)}, nil
case m.isFor("PATCH", "/nodes/node-name"):
tainted = true
data, err := ioutil.ReadAll(req.Body)
......@@ -279,7 +280,7 @@ func TestTaint(t *testing.T) {
if !equalTaints(expectNewNode.Spec.Taints, new_node.Spec.Taints) {
t.Fatalf("%s: expected:\n%v\nsaw:\n%v\n", test.description, expectNewNode.Spec.Taints, new_node.Spec.Taints)
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, new_node)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, new_node)}, nil
case m.isFor("PUT", "/nodes/node-name"):
tainted = true
data, err := ioutil.ReadAll(req.Body)
......@@ -293,14 +294,14 @@ func TestTaint(t *testing.T) {
if !equalTaints(expectNewNode.Spec.Taints, new_node.Spec.Taints) {
t.Fatalf("%s: expected:\n%v\nsaw:\n%v\n", test.description, expectNewNode.Spec.Taints, new_node.Spec.Taints)
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: objBody(codec, new_node)}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, new_node)}, nil
default:
t.Fatalf("%s: unexpected request: %v %#v\n%#v", test.description, req.Method, req.URL, req)
return nil, nil
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
cmd := NewCmdTaint(tf, genericclioptions.NewTestIOStreamsDiscard())
......@@ -386,3 +387,16 @@ func TestValidateFlags(t *testing.T) {
}
}
}
type MyReq struct {
Request *http.Request
}
func (m *MyReq) isFor(method string, path string) bool {
req := m.Request
return method == req.Method && (req.URL.Path == path ||
req.URL.Path == strings.Join([]string{"/api/v1", path}, "") ||
req.URL.Path == strings.Join([]string{"/apis/extensions/v1beta1", path}, "") ||
req.URL.Path == strings.Join([]string{"/apis/batch/v1", path}, ""))
}
/*
Copyright 2018 The Kubernetes Authors.
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 testing
import (
"bytes"
"encoding/json"
"io"
"io/ioutil"
"net/http"
"testing"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
runtime "k8s.io/apimachinery/pkg/runtime"
restclient "k8s.io/client-go/rest"
cmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
"k8s.io/kubernetes/pkg/kubectl/scheme"
)
var (
grace = int64(30)
enableServiceLinks = corev1.DefaultEnableServiceLinks
)
func DefaultHeader() http.Header {
header := http.Header{}
header.Set("Content-Type", runtime.ContentTypeJSON)
return header
}
func DefaultClientConfig() *restclient.Config {
return &restclient.Config{
APIPath: "/api",
ContentConfig: restclient.ContentConfig{
NegotiatedSerializer: scheme.Codecs,
ContentType: runtime.ContentTypeJSON,
GroupVersion: &corev1.SchemeGroupVersion,
},
}
}
func ObjBody(codec runtime.Codec, obj runtime.Object) io.ReadCloser {
return ioutil.NopCloser(bytes.NewReader([]byte(runtime.EncodeOrDie(codec, obj))))
}
func BytesBody(bodyBytes []byte) io.ReadCloser {
return ioutil.NopCloser(bytes.NewReader(bodyBytes))
}
func StringBody(body string) io.ReadCloser {
return ioutil.NopCloser(bytes.NewReader([]byte(body)))
}
func TestData() (*corev1.PodList, *corev1.ServiceList, *corev1.ReplicationControllerList) {
pods := &corev1.PodList{
ListMeta: metav1.ListMeta{
ResourceVersion: "15",
},
Items: []corev1.Pod{
{
ObjectMeta: metav1.ObjectMeta{Name: "foo", Namespace: "test", ResourceVersion: "10"},
Spec: corev1.PodSpec{
RestartPolicy: corev1.RestartPolicyAlways,
DNSPolicy: corev1.DNSClusterFirst,
TerminationGracePeriodSeconds: &grace,
SecurityContext: &corev1.PodSecurityContext{},
EnableServiceLinks: &enableServiceLinks,
},
},
{
ObjectMeta: metav1.ObjectMeta{Name: "bar", Namespace: "test", ResourceVersion: "11"},
Spec: corev1.PodSpec{
RestartPolicy: corev1.RestartPolicyAlways,
DNSPolicy: corev1.DNSClusterFirst,
TerminationGracePeriodSeconds: &grace,
SecurityContext: &corev1.PodSecurityContext{},
EnableServiceLinks: &enableServiceLinks,
},
},
},
}
svc := &corev1.ServiceList{
ListMeta: metav1.ListMeta{
ResourceVersion: "16",
},
Items: []corev1.Service{
{
ObjectMeta: metav1.ObjectMeta{Name: "baz", Namespace: "test", ResourceVersion: "12"},
Spec: corev1.ServiceSpec{
SessionAffinity: "None",
Type: corev1.ServiceTypeClusterIP,
},
},
},
}
one := int32(1)
rc := &corev1.ReplicationControllerList{
ListMeta: metav1.ListMeta{
ResourceVersion: "17",
},
Items: []corev1.ReplicationController{
{
ObjectMeta: metav1.ObjectMeta{Name: "rc1", Namespace: "test", ResourceVersion: "18"},
Spec: corev1.ReplicationControllerSpec{
Replicas: &one,
},
},
},
}
return pods, svc, rc
}
func GenResponseWithJsonEncodedBody(bodyStruct interface{}) (*http.Response, error) {
jsonBytes, err := json.Marshal(bodyStruct)
if err != nil {
return nil, err
}
return &http.Response{StatusCode: 200, Header: DefaultHeader(), Body: BytesBody(jsonBytes)}, nil
}
func InitTestErrorHandler(t *testing.T) {
cmdutil.BehaviorOnFatal(func(str string, code int) {
t.Errorf("Error running command (exit code %d): %s", code, str)
})
}
func Int32ptr(val int) *int32 {
t := int32(val)
return &t
}
......@@ -142,7 +142,7 @@ func TestTopPod(t *testing.T) {
containers: true,
},
}
initTestErrorHandler(t)
cmdtesting.InitTestErrorHandler(t)
for _, testCase := range testCases {
t.Run(testCase.name, func(t *testing.T) {
t.Logf("Running test case: %s", testCase.name)
......@@ -183,15 +183,15 @@ func TestTopPod(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m, q := req.URL.Path, req.Method, req.URL.RawQuery; {
case p == "/api":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apibody)))}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apibody)))}, nil
case p == "/apis":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apisbody)))}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apisbody)))}, nil
case p == testCase.expectedPath && m == "GET" && (testCase.expectedQuery == "" || q == testCase.expectedQuery):
body, err := marshallBody(response)
if err != nil {
t.Errorf("%s: unexpected error: %v", testCase.name, err)
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
default:
t.Fatalf("%s: unexpected request: %#v\nGot URL: %#v\nExpected path: %#v\nExpected query: %#v",
testCase.name, req, req.URL, testCase.expectedPath, testCase.expectedQuery)
......@@ -199,7 +199,7 @@ func TestTopPod(t *testing.T) {
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
streams, _, buf, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdTopPod(tf, nil, streams)
......@@ -284,7 +284,7 @@ func TestTopPodWithMetricsServer(t *testing.T) {
containers: true,
},
}
initTestErrorHandler(t)
cmdtesting.InitTestErrorHandler(t)
for _, testCase := range testCases {
t.Run(testCase.name, func(t *testing.T) {
metricsList := testV1beta1PodMetricsData()
......@@ -330,9 +330,9 @@ func TestTopPodWithMetricsServer(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p := req.URL.Path; {
case p == "/api":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apibody)))}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apibody)))}, nil
case p == "/apis":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apisbodyWithMetrics)))}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apisbodyWithMetrics)))}, nil
default:
t.Fatalf("%s: unexpected request: %#v\nGot URL: %#v",
testCase.name, req, req.URL)
......@@ -340,7 +340,7 @@ func TestTopPodWithMetricsServer(t *testing.T) {
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
streams, _, buf, _ := genericclioptions.NewTestIOStreams()
cmd := NewCmdTopPod(tf, nil, streams)
......@@ -487,7 +487,7 @@ func TestTopPodCustomDefaults(t *testing.T) {
containers: true,
},
}
initTestErrorHandler(t)
cmdtesting.InitTestErrorHandler(t)
for _, testCase := range testCases {
t.Run(testCase.name, func(t *testing.T) {
t.Logf("Running test case: %s", testCase.name)
......@@ -528,15 +528,15 @@ func TestTopPodCustomDefaults(t *testing.T) {
Client: fake.CreateHTTPClient(func(req *http.Request) (*http.Response, error) {
switch p, m, q := req.URL.Path, req.Method, req.URL.RawQuery; {
case p == "/api":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apibody)))}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apibody)))}, nil
case p == "/apis":
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apisbody)))}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: ioutil.NopCloser(bytes.NewReader([]byte(apisbody)))}, nil
case p == testCase.expectedPath && m == "GET" && (testCase.expectedQuery == "" || q == testCase.expectedQuery):
body, err := marshallBody(response)
if err != nil {
t.Errorf("%s: unexpected error: %v", testCase.name, err)
}
return &http.Response{StatusCode: 200, Header: defaultHeader(), Body: body}, nil
return &http.Response{StatusCode: 200, Header: cmdtesting.DefaultHeader(), Body: body}, nil
default:
t.Fatalf("%s: unexpected request: %#v\nGot URL: %#v\nExpected path: %#v\nExpected query: %#v",
testCase.name, req, req.URL, testCase.expectedPath, testCase.expectedQuery)
......@@ -544,7 +544,7 @@ func TestTopPodCustomDefaults(t *testing.T) {
}
}),
}
tf.ClientConfigVal = defaultClientConfig()
tf.ClientConfigVal = cmdtesting.DefaultClientConfig()
streams, _, buf, _ := genericclioptions.NewTestIOStreams()
opts := &TopPodOptions{
......
......@@ -42,7 +42,7 @@ const (
)
func TestTopSubcommandsExist(t *testing.T) {
initTestErrorHandler(t)
cmdtesting.InitTestErrorHandler(t)
f := cmdtesting.NewTestFactory()
defer f.Cleanup()
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment