added a e2e test that uses the staged client; made necessary changes to gcp auth plugin to pass the gke tests

This commit is contained in:
Chao Xu 2016-08-05 23:00:12 -07:00
parent adb75e1fd1
commit 51c0271e0a
4 changed files with 123 additions and 4 deletions

View File

@ -25,6 +25,7 @@ import (
"golang.org/x/oauth2"
"golang.org/x/oauth2/google"
clientreporestclient "k8s.io/client-go/1.4/rest"
"k8s.io/kubernetes/pkg/client/restclient"
)
@ -32,6 +33,9 @@ func init() {
if err := restclient.RegisterAuthProviderPlugin("gcp", newGCPAuthProvider); err != nil {
glog.Fatalf("Failed to register gcp auth plugin: %v", err)
}
if err := clientreporestclient.RegisterAuthProviderPlugin("gcp", newGCPAuthProviderForClientRepo); err != nil {
glog.Fatalf("Failed to register gcp auth plugin: %v", err)
}
}
type gcpAuthProvider struct {
@ -47,6 +51,15 @@ func newGCPAuthProvider(_ string, gcpConfig map[string]string, persister restcli
return &gcpAuthProvider{ts, persister}, nil
}
// newGCPAuthProviderForClientRepo is the same as newGCPAuthProvider, but is programmed against client-go's interface
func newGCPAuthProviderForClientRepo(_ string, gcpConfig map[string]string, persister clientreporestclient.AuthProviderConfigPersister) (clientreporestclient.AuthProvider, error) {
ts, err := newCachedTokenSource(gcpConfig["access-token"], gcpConfig["expiry"], persister)
if err != nil {
return nil, err
}
return &gcpAuthProvider{ts, persister}, nil
}
func (g *gcpAuthProvider) WrapTransport(rt http.RoundTripper) http.RoundTripper {
return &oauth2.Transport{
Source: g.tokenSource,

View File

@ -32,7 +32,7 @@ import (
"k8s.io/kubernetes/pkg/api"
gcecloud "k8s.io/kubernetes/pkg/cloudprovider/providers/gce"
"k8s.io/kubernetes/pkg/util"
"k8s.io/kubernetes/pkg/util/logs"
"k8s.io/kubernetes/pkg/util/runtime"
commontest "k8s.io/kubernetes/test/e2e/common"
"k8s.io/kubernetes/test/e2e/framework"
@ -215,8 +215,8 @@ var _ = ginkgo.SynchronizedAfterSuite(func() {
// This function is called on each Ginkgo node in parallel mode.
func RunE2ETests(t *testing.T) {
runtime.ReallyCrash = true
util.InitLogs()
defer util.FlushLogs()
logs.InitLogs()
defer logs.FlushLogs()
gomega.RegisterFailHandler(ginkgo.Fail)
// Disable skipped tests unless they are explicitly requested.

View File

@ -18,6 +18,7 @@ package framework
import (
"bytes"
"encoding/json"
"fmt"
"io/ioutil"
"reflect"
@ -25,6 +26,9 @@ import (
"sync"
"time"
release_1_4 "k8s.io/client-go/1.4/kubernetes"
"k8s.io/client-go/1.4/pkg/util/sets"
clientreporestclient "k8s.io/client-go/1.4/rest"
"k8s.io/kubernetes/federation/client/clientset_generated/federation_internalclientset"
unversionedfederation "k8s.io/kubernetes/federation/client/clientset_generated/federation_internalclientset/typed/federation/unversioned"
"k8s.io/kubernetes/federation/client/clientset_generated/federation_release_1_3"
@ -33,6 +37,7 @@ import (
apierrs "k8s.io/kubernetes/pkg/api/errors"
"k8s.io/kubernetes/pkg/client/clientset_generated/release_1_2"
"k8s.io/kubernetes/pkg/client/clientset_generated/release_1_3"
"k8s.io/kubernetes/pkg/client/restclient"
client "k8s.io/kubernetes/pkg/client/unversioned"
"k8s.io/kubernetes/pkg/fields"
"k8s.io/kubernetes/pkg/labels"
@ -57,6 +62,7 @@ type Framework struct {
Client *client.Client
Clientset_1_2 *release_1_2.Clientset
Clientset_1_3 *release_1_3.Clientset
StagingClient *release_1_4.Clientset
// TODO(mml): Remove this. We should generally use the versioned clientset.
FederationClientset *federation_internalclientset.Clientset
@ -131,6 +137,38 @@ func NewFramework(baseName string, options FrameworkOptions, client *client.Clie
return f
}
// getClientRepoConfig copies k8s.io/kubernetes/pkg/client/restclient.Config to
// a k8s.io/client-go/pkg/client/restclient.Config. It's not a deep copy. Two
// configs may share some common struct.
func getClientRepoConfig(src *restclient.Config) (dst *clientreporestclient.Config) {
skippedFields := sets.NewString("Transport", "WrapTransport", "RateLimiter", "AuthConfigPersister")
dst = &clientreporestclient.Config{}
dst.Transport = src.Transport
dst.WrapTransport = src.WrapTransport
dst.RateLimiter = src.RateLimiter
dst.AuthConfigPersister = src.AuthConfigPersister
sv := reflect.ValueOf(src).Elem()
dv := reflect.ValueOf(dst).Elem()
for i := 0; i < sv.NumField(); i++ {
if skippedFields.Has(sv.Type().Field(i).Name) {
continue
}
sf := sv.Field(i).Interface()
data, err := json.Marshal(sf)
if err != nil {
Expect(err).NotTo(HaveOccurred())
}
if !dv.Field(i).CanAddr() {
Failf("unaddressable field: %v", dv.Type().Field(i).Name)
} else {
if err := json.Unmarshal(data, dv.Field(i).Addr().Interface()); err != nil {
Expect(err).NotTo(HaveOccurred())
}
}
}
return dst
}
// BeforeEach gets a client and makes a namespace.
func (f *Framework) BeforeEach() {
// The fact that we need this feels like a bug in ginkgo.
@ -149,9 +187,11 @@ func (f *Framework) BeforeEach() {
Expect(err).NotTo(HaveOccurred())
f.Client = c
f.Clientset_1_2, err = release_1_2.NewForConfig(config)
Expect(err).NotTo(HaveOccurred())
f.Clientset_1_3, err = release_1_3.NewForConfig(config)
Expect(err).NotTo(HaveOccurred())
clientRepoConfig := getClientRepoConfig(config)
f.StagingClient, err = release_1_4.NewForConfig(clientRepoConfig)
Expect(err).NotTo(HaveOccurred())
}
if f.federated {

View File

@ -20,12 +20,15 @@ import (
"strconv"
"time"
clientapi "k8s.io/client-go/1.4/pkg/api"
clientv1 "k8s.io/client-go/1.4/pkg/api/v1"
"k8s.io/kubernetes/pkg/api"
"k8s.io/kubernetes/pkg/api/v1"
"k8s.io/kubernetes/pkg/labels"
"k8s.io/kubernetes/pkg/runtime"
"k8s.io/kubernetes/pkg/util/intstr"
"k8s.io/kubernetes/pkg/util/uuid"
"k8s.io/kubernetes/pkg/util/wait"
"k8s.io/kubernetes/pkg/watch"
"k8s.io/kubernetes/test/e2e/framework"
@ -33,6 +36,27 @@ import (
. "github.com/onsi/gomega"
)
func stagingClientPod(name, value string) clientv1.Pod {
return clientv1.Pod{
ObjectMeta: clientv1.ObjectMeta{
Name: name,
Labels: map[string]string{
"name": "foo",
"time": value,
},
},
Spec: clientv1.PodSpec{
Containers: []clientv1.Container{
{
Name: "nginx",
Image: "gcr.io/google_containers/nginx-slim:0.7",
Ports: []clientv1.ContainerPort{{ContainerPort: 80}},
},
},
},
}
}
func testingPod(name, value string) v1.Pod {
return v1.Pod{
ObjectMeta: v1.ObjectMeta{
@ -242,3 +266,45 @@ var _ = framework.KubeDescribe("Generated release_1_3 clientset", func() {
Expect(len(pods.Items)).To(Equal(0))
})
})
var _ = framework.KubeDescribe("Staging client repo client", func() {
f := framework.NewDefaultFramework("clientset")
It("should create pods, delete pods, watch pods", func() {
podClient := f.StagingClient.Core().Pods(f.Namespace.Name)
By("constructing the pod")
name := "pod" + string(uuid.NewUUID())
value := strconv.Itoa(time.Now().Nanosecond())
podCopy := stagingClientPod(name, value)
pod := &podCopy
By("verifying no pod exists before the test")
pods, err := podClient.List(clientapi.ListOptions{})
if err != nil {
framework.Failf("Failed to query for pods: %v", err)
}
Expect(len(pods.Items)).To(Equal(0))
By("creating the pod")
pod, err = podClient.Create(pod)
if err != nil {
framework.Failf("Failed to create pod: %v", err)
}
// We call defer here in case there is a problem with
// the test so we can ensure that we clean up after
// ourselves
defer podClient.Delete(pod.Name, clientapi.NewDeleteOptions(0))
By("verifying the pod is in kubernetes")
timeout := 1 * time.Minute
if err := wait.PollImmediate(time.Second, timeout, func() (bool, error) {
pods, err = podClient.List(clientapi.ListOptions{})
if err != nil {
return false, err
}
if len(pods.Items) == 1 {
return true, nil
}
return false, nil
}); err != nil {
framework.Failf("Err : %s\n. Failed to wait for 1 pod to be created", err)
}
})
})