mirror of https://github.com/k3s-io/k3s
Test controller's synchronize method. Requires fake etcd client to be relocated.
parent
b6a260940c
commit
7e464aa55c
|
@ -35,7 +35,7 @@ import (
|
||||||
// with actual running pods.
|
// with actual running pods.
|
||||||
// TODO: Remove the etcd dependency and re-factor in terms of a generic watch interface
|
// TODO: Remove the etcd dependency and re-factor in terms of a generic watch interface
|
||||||
type ReplicationManager struct {
|
type ReplicationManager struct {
|
||||||
etcdClient *etcd.Client
|
etcdClient util.EtcdClient
|
||||||
kubeClient client.ClientInterface
|
kubeClient client.ClientInterface
|
||||||
podControl PodControlInterface
|
podControl PodControlInterface
|
||||||
updateLock sync.Mutex
|
updateLock sync.Mutex
|
||||||
|
@ -74,7 +74,7 @@ func (r RealPodControl) deletePod(podID string) error {
|
||||||
return r.kubeClient.DeletePod(podID)
|
return r.kubeClient.DeletePod(podID)
|
||||||
}
|
}
|
||||||
|
|
||||||
func MakeReplicationManager(etcdClient *etcd.Client, kubeClient client.ClientInterface) *ReplicationManager {
|
func MakeReplicationManager(etcdClient util.EtcdClient, kubeClient client.ClientInterface) *ReplicationManager {
|
||||||
return &ReplicationManager{
|
return &ReplicationManager{
|
||||||
kubeClient: kubeClient,
|
kubeClient: kubeClient,
|
||||||
etcdClient: etcdClient,
|
etcdClient: etcdClient,
|
||||||
|
|
|
@ -317,3 +317,79 @@ func TestHandleWatchResponse(t *testing.T) {
|
||||||
t.Errorf("Unexpected mismatch. Expected %#v, Saw: %#v", controller, controllerOut)
|
t.Errorf("Unexpected mismatch. Expected %#v, Saw: %#v", controller, controllerOut)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestSyncronize(t *testing.T) {
|
||||||
|
controllerSpec1 := api.ReplicationController{
|
||||||
|
DesiredState: api.ReplicationControllerState{
|
||||||
|
Replicas: 4,
|
||||||
|
PodTemplate: api.PodTemplate{
|
||||||
|
DesiredState: api.PodState{
|
||||||
|
Manifest: api.ContainerManifest{
|
||||||
|
Containers: []api.Container{
|
||||||
|
{
|
||||||
|
Image: "foo/bar",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
Labels: map[string]string{
|
||||||
|
"name": "foo",
|
||||||
|
"type": "production",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
controllerSpec2 := api.ReplicationController{
|
||||||
|
DesiredState: api.ReplicationControllerState{
|
||||||
|
Replicas: 3,
|
||||||
|
PodTemplate: api.PodTemplate{
|
||||||
|
DesiredState: api.PodState{
|
||||||
|
Manifest: api.ContainerManifest{
|
||||||
|
Containers: []api.Container{
|
||||||
|
{
|
||||||
|
Image: "bar/baz",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
Labels: map[string]string{
|
||||||
|
"name": "bar",
|
||||||
|
"type": "production",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
fakeEtcd := util.MakeFakeEtcdClient(t)
|
||||||
|
fakeEtcd.Data["/registry/controllers"] = util.EtcdResponseWithError{
|
||||||
|
R: &etcd.Response{
|
||||||
|
Node: &etcd.Node{
|
||||||
|
Nodes: []*etcd.Node{
|
||||||
|
{
|
||||||
|
Value: util.MakeJSONString(controllerSpec1),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
Value: util.MakeJSONString(controllerSpec2),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
fakeHandler := util.FakeHandler{
|
||||||
|
StatusCode: 200,
|
||||||
|
ResponseBody: "{}",
|
||||||
|
T: t,
|
||||||
|
}
|
||||||
|
testServer := httptest.NewTLSServer(&fakeHandler)
|
||||||
|
client := client.Client{
|
||||||
|
Host: testServer.URL,
|
||||||
|
}
|
||||||
|
manager := MakeReplicationManager(fakeEtcd, client)
|
||||||
|
fakePodControl := FakePodControl{}
|
||||||
|
manager.podControl = &fakePodControl
|
||||||
|
|
||||||
|
manager.synchronize()
|
||||||
|
|
||||||
|
validateSyncReplication(t, &fakePodControl, 7, 0)
|
||||||
|
}
|
||||||
|
|
|
@ -33,7 +33,6 @@ import (
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/api"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/api"
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/registry"
|
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/util"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/util"
|
||||||
"github.com/coreos/go-etcd/etcd"
|
"github.com/coreos/go-etcd/etcd"
|
||||||
"github.com/fsouza/go-dockerclient"
|
"github.com/fsouza/go-dockerclient"
|
||||||
|
@ -62,7 +61,7 @@ type DockerInterface interface {
|
||||||
// The main kubelet implementation
|
// The main kubelet implementation
|
||||||
type Kubelet struct {
|
type Kubelet struct {
|
||||||
Hostname string
|
Hostname string
|
||||||
Client registry.EtcdClient
|
Client util.EtcdClient
|
||||||
DockerClient DockerInterface
|
DockerClient DockerInterface
|
||||||
FileCheckFrequency time.Duration
|
FileCheckFrequency time.Duration
|
||||||
SyncFrequency time.Duration
|
SyncFrequency time.Duration
|
||||||
|
|
|
@ -21,8 +21,6 @@ import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
|
|
||||||
"github.com/coreos/go-etcd/etcd"
|
|
||||||
|
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/api"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/api"
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/labels"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/labels"
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/util"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/util"
|
||||||
|
@ -31,21 +29,9 @@ import (
|
||||||
// TODO: Need to add a reconciler loop that makes sure that things in pods are reflected into
|
// TODO: Need to add a reconciler loop that makes sure that things in pods are reflected into
|
||||||
// kubelet (and vice versa)
|
// kubelet (and vice versa)
|
||||||
|
|
||||||
// EtcdClient is an injectable interface for testing.
|
|
||||||
type EtcdClient interface {
|
|
||||||
AddChild(key, data string, ttl uint64) (*etcd.Response, error)
|
|
||||||
Get(key string, sort, recursive bool) (*etcd.Response, error)
|
|
||||||
Set(key, value string, ttl uint64) (*etcd.Response, error)
|
|
||||||
Create(key, value string, ttl uint64) (*etcd.Response, error)
|
|
||||||
Delete(key string, recursive bool) (*etcd.Response, error)
|
|
||||||
// I'd like to use directional channels here (e.g. <-chan) but this interface mimics
|
|
||||||
// the etcd client interface which doesn't, and it doesn't seem worth it to wrap the api.
|
|
||||||
Watch(prefix string, waitIndex uint64, recursive bool, receiver chan *etcd.Response, stop chan bool) (*etcd.Response, error)
|
|
||||||
}
|
|
||||||
|
|
||||||
// EtcdRegistry is an implementation of both ControllerRegistry and PodRegistry which is backed with etcd.
|
// EtcdRegistry is an implementation of both ControllerRegistry and PodRegistry which is backed with etcd.
|
||||||
type EtcdRegistry struct {
|
type EtcdRegistry struct {
|
||||||
etcdClient EtcdClient
|
etcdClient util.EtcdClient
|
||||||
machines []string
|
machines []string
|
||||||
manifestFactory ManifestFactory
|
manifestFactory ManifestFactory
|
||||||
}
|
}
|
||||||
|
@ -54,7 +40,7 @@ type EtcdRegistry struct {
|
||||||
// 'client' is the connection to etcd
|
// 'client' is the connection to etcd
|
||||||
// 'machines' is the list of machines
|
// 'machines' is the list of machines
|
||||||
// 'scheduler' is the scheduling algorithm to use.
|
// 'scheduler' is the scheduling algorithm to use.
|
||||||
func MakeEtcdRegistry(client EtcdClient, machines []string) *EtcdRegistry {
|
func MakeEtcdRegistry(client util.EtcdClient, machines []string) *EtcdRegistry {
|
||||||
registry := &EtcdRegistry{
|
registry := &EtcdRegistry{
|
||||||
etcdClient: client,
|
etcdClient: client,
|
||||||
machines: machines,
|
machines: machines,
|
||||||
|
|
|
@ -26,7 +26,7 @@ import (
|
||||||
"github.com/coreos/go-etcd/etcd"
|
"github.com/coreos/go-etcd/etcd"
|
||||||
)
|
)
|
||||||
|
|
||||||
func MakeTestEtcdRegistry(client EtcdClient, machines []string) *EtcdRegistry {
|
func MakeTestEtcdRegistry(client util.EtcdClient, machines []string) *EtcdRegistry {
|
||||||
registry := MakeEtcdRegistry(client, machines)
|
registry := MakeEtcdRegistry(client, machines)
|
||||||
registry.manifestFactory = &BasicManifestFactory{
|
registry.manifestFactory = &BasicManifestFactory{
|
||||||
serviceRegistry: &MockServiceRegistry{},
|
serviceRegistry: &MockServiceRegistry{},
|
||||||
|
|
|
@ -22,6 +22,18 @@ import (
|
||||||
"github.com/coreos/go-etcd/etcd"
|
"github.com/coreos/go-etcd/etcd"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// EtcdClient is an injectable interface for testing.
|
||||||
|
type EtcdClient interface {
|
||||||
|
AddChild(key, data string, ttl uint64) (*etcd.Response, error)
|
||||||
|
Get(key string, sort, recursive bool) (*etcd.Response, error)
|
||||||
|
Set(key, value string, ttl uint64) (*etcd.Response, error)
|
||||||
|
Create(key, value string, ttl uint64) (*etcd.Response, error)
|
||||||
|
Delete(key string, recursive bool) (*etcd.Response, error)
|
||||||
|
// I'd like to use directional channels here (e.g. <-chan) but this interface mimics
|
||||||
|
// the etcd client interface which doesn't, and it doesn't seem worth it to wrap the api.
|
||||||
|
Watch(prefix string, waitIndex uint64, recursive bool, receiver chan *etcd.Response, stop chan bool) (*etcd.Response, error)
|
||||||
|
}
|
||||||
|
|
||||||
type EtcdResponseWithError struct {
|
type EtcdResponseWithError struct {
|
||||||
R *etcd.Response
|
R *etcd.Response
|
||||||
E error
|
E error
|
||||||
|
|
Loading…
Reference in New Issue