Skip to content

Commit

Permalink
Merge branch 'realloc-unit-test' into 'master'
Browse files Browse the repository at this point in the history
Realloc unit test

See merge request !138
  • Loading branch information
CMGS committed Aug 25, 2017
2 parents 678dd1f + 1a4fac5 commit 1a626c9
Show file tree
Hide file tree
Showing 3 changed files with 260 additions and 47 deletions.
27 changes: 1 addition & 26 deletions cluster/calcium/create_container_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,32 +11,6 @@ import (
"gitlab.ricebook.net/platform/core/types"
)

var (
specs = types.Specs{
Appname: "root",
Entrypoints: map[string]types.Entrypoint{
"test": types.Entrypoint{
Command: "sleep 9999",
Ports: []types.Port{"6006/tcp"},
HealthCheckPort: 6006,
HealthCheckUrl: "",
HealthCheckExpectedCode: 200,
},
},
Build: []string{""},
Base: image,
}
opts = &types.DeployOptions{
Appname: "root",
Image: image,
Podname: podname,
Entrypoint: "test",
Count: 3,
Memory: 268435456,
CPUQuota: 1,
}
)

func TestPullImage(t *testing.T) {
initMockConfig()

Expand All @@ -63,6 +37,7 @@ func TestCreateContainerWithMemPrior(t *testing.T) {
ids = append(ids, msg.ContainerID)
fmt.Printf("Get Container ID: %s\n", msg.ContainerID)
}
assert.Equal(t, opts.Count, len(ids))

// get containers
clnt, _ := client.NewClient("http://127.0.0.1", "v1.29", mockDockerHTTPClient(), nil)
Expand Down
121 changes: 100 additions & 21 deletions cluster/calcium/mock_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,13 +25,15 @@ import (
)

const (
podname = "dev_pod"
desc = "dev pod with one node"
nodename = "node1"
image = "hub.testhub.com/base/alpine:base-2017.03.14"
APIVersion = "v1.29"
mockMemory = int64(8589934592)
mockID = "f1f9da344e8f8f90f73899ddad02da6cdf2218bbe52413af2bcfef4fba2d22de"
podname = "dev_pod"
desc = "dev pod with one node"
nodename = "node1"
updatenodename = "node4"
image = "hub.testhub.com/base/alpine:base-2017.03.14"
APIVersion = "v1.29"
mockMemory = int64(8589934592) // 8G
mockID = "f1f9da344e8f8f90f73899ddad02da6cdf2218bbe52413af2bcfef4fba2d22de"
appmemory = 268435456 // 0.25 G
)

var (
Expand All @@ -55,6 +57,34 @@ var (
mockStore *mockstore.MockStore
err error
mockTimeoutError bool
specs = coretypes.Specs{
Appname: "root",
Entrypoints: map[string]coretypes.Entrypoint{
"test": coretypes.Entrypoint{
Command: "sleep 9999",
Ports: []coretypes.Port{"6006/tcp"},
HealthCheckPort: 6006,
HealthCheckUrl: "",
HealthCheckExpectedCode: 200,
},
},
Build: []string{""},
Base: image,
}
opts = &coretypes.DeployOptions{
Appname: "root",
Image: image,
Podname: podname,
Entrypoint: "test",
Count: 5,
Memory: appmemory,
CPUQuota: 1,
}
ToUpdateContainerIDs = []string{
"f1f9da344e8f8f90f73899ddad02da6cdf2218bbe52413af2bcfef4fba2d22de",
"f1f9da344e8f8f90f73899ddad02da6cdf2218bbe52413af2bcfef4fba2d22df",
"f1f9da344e8f8f90f73899ddad02da6cdf2218bbe52413af2bcfef4fba2d22dg",
}
)

func testlogF(format interface{}, a ...interface{}) {
Expand Down Expand Up @@ -186,6 +216,9 @@ func mockDockerDoer(r *http.Request) (*http.Response, error) {
b, err = json.Marshal(container.ContainerCreateCreatedBody{
ID: mockContainerID(),
})
case fmt.Sprintf("/containers/%s/update", containerID):
testlogF("update container %s", containerID)
b, err = json.Marshal(container.ContainerUpdateOKBody{})
case fmt.Sprintf("/containers/%s", containerID):
testlogF("remove container %s", containerID)
b = []byte("body")
Expand Down Expand Up @@ -221,6 +254,12 @@ func mockDockerDoer(r *http.Request) (*http.Response, error) {
ID: containerID,
Image: "image:latest",
Name: "name",
HostConfig: &container.HostConfig{
Resources: container.Resources{
CPUQuota: utils.CpuPeriodBase,
Memory: appmemory,
},
},
},
Config: &container.Config{
Labels: nil,
Expand Down Expand Up @@ -323,17 +362,41 @@ func initMockConfig() {
Available: true,
Engine: clnt,
}
n3 := &coretypes.Node{
Name: "node3",
Podname: podname,
Endpoint: "tcp://10.0.0.2:2376",
CPU: mockCPU,
MemCap: mockMemory,
Available: true,
Engine: clnt,
}
n4 := &coretypes.Node{
Name: updatenodename,
Podname: podname,
Endpoint: "tcp://10.0.0.2:2376",
CPU: mockCPU,
MemCap: mockMemory - appmemory*3,
Available: true,
Engine: clnt,
}

pod := &coretypes.Pod{Name: podname, Desc: desc, Favor: "MEM"}
mockStringType := mock.AnythingOfType("string")
mockCPUMapType := mock.AnythingOfType("types.CPUMap")
mockNodeType := mock.AnythingOfType("*types.Node")
mockStore.On("GetPod", mockStringType).Return(pod, nil)
mockStore.On("GetNodesByPod", mockStringType).Return([]*coretypes.Node{n1, n2}, nil)
mockStore.On("GetAllNodes").Return([]*coretypes.Node{n1, n2}, nil)
mockStore.On("GetAllNodes").Return([]*coretypes.Node{n1, n2, n3}, nil)
mockStore.On("GetNode", podname, "node1").Return(n1, nil)
mockStore.On("GetNode", podname, "node2").Return(n2, nil)
mockStore.On("GetNode", podname, "node3").Return(n3, nil)
mockStore.On("GetNode", podname, updatenodename).Return(n4, nil)
mockStore.On("GetNode", "", "").Return(n2, nil)

mockStore.On("UpdateNodeMem", podname, mockStringType, mock.AnythingOfType("int64"), mockStringType).Return(nil)
mockStore.On("UpdateNodeCPU", podname, mockStringType, mockCPUMapType, mockStringType).Return(nil)
mockStore.On("UpdateNode", mockNodeType).Return(nil)

lk := mockstore.MockLock{}
lk.Mock.On("Lock").Return(nil)
Expand All @@ -346,30 +409,29 @@ func initMockConfig() {

mockStore.On("RemovePod", mockStringType).Return(nil)

// 模拟集群上有5个旧容器的情况.
deployNodeInfo := []coretypes.NodeInfo{
coretypes.NodeInfo{
Name: "node1",
CPURate: 400000,
Count: 0,
Deploy: 2,
Count: 3,
Deploy: 0,
CPUAndMem: coretypes.CPUAndMem{CpuMap: coretypes.CPUMap{"0": 10, "1": 10, "2": 10, "3": 10}, MemCap: 8589934592},
},
coretypes.NodeInfo{
Name: "node2",
CPURate: 400000,
Count: 0,
Deploy: 1,
Count: 1,
Deploy: 0,
CPUAndMem: coretypes.CPUAndMem{CpuMap: coretypes.CPUMap{"0": 10, "1": 10, "2": 10, "3": 10}, MemCap: 8589934592},
},
coretypes.NodeInfo{
Name: "node3",
CPURate: 400000,
Count: 1,
Deploy: 0,
CPUAndMem: coretypes.CPUAndMem{CpuMap: coretypes.CPUMap{"0": 10, "1": 10, "2": 10, "3": 10}, MemCap: 8589934592},
},
}
opts := &coretypes.DeployOptions{
Appname: "root",
Image: image,
Podname: podname,
Entrypoint: "test",
Count: 3,
Memory: 268435456,
CPUQuota: 1,
}

// make plan
Expand All @@ -383,5 +445,22 @@ func initMockConfig() {
Nodename: nodename,
Name: "hello_hi_123",
}

mockStore.On("GetContainer", mockID).Return(rContainer, nil)

// GetContainers
rContainers := []*coretypes.Container{}
for _, mID := range ToUpdateContainerIDs {
rContainer := &coretypes.Container{
ID: mID,
Engine: clnt,
Podname: podname,
Nodename: updatenodename,
Name: "hello_hi_123",
CPU: coretypes.CPUMap{"0": 10},
Memory: appmemory,
}
rContainers = append(rContainers, rContainer)
}
mockStore.On("GetContainers", ToUpdateContainerIDs).Return(rContainers, nil)
}
159 changes: 159 additions & 0 deletions cluster/calcium/realloc_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,159 @@
package calcium

import (
"sync"
"testing"

"github.com/stretchr/testify/assert"
"gitlab.ricebook.net/platform/core/types"
)

func TestReallocWithCPUPrior(t *testing.T) {
initMockConfig()
containersInfo := map[*types.Pod]NodeContainers{}
pod, _ := mockc.GetPod("pod1")
containersInfo[pod] = NodeContainers{}
node, _ := mockc.GetNode(pod.Name, updatenodename)
cpuContainersInfo := map[*types.Pod]CPUNodeContainers{}
cpuContainersInfo[pod] = CPUNodeContainers{}

containers, _ := mockc.GetContainers(ToUpdateContainerIDs)
for _, container := range containers {
containersInfo[pod][node] = append(containersInfo[pod][node], container)
}

// 扩容
cpu := 0.1
CPURate := mockc.calculateCPUUsage(containers[0])
newCPURequire := CPURate + cpu
cpuContainersInfo[pod][newCPURequire] = NodeContainers{}
cpuContainersInfo[pod][newCPURequire][node] = []*types.Container{}
for _, container := range containers {
cpuContainersInfo[pod][newCPURequire][node] = append(cpuContainersInfo[pod][newCPURequire][node], container)
}

ch1 := make(chan *types.ReallocResourceMessage)
go func() {
defer close(ch1)
wg := sync.WaitGroup{}
wg.Add(len(containersInfo))
for pod, _ := range containersInfo {
nodeCPUContainersInfo := cpuContainersInfo[pod]
go func(pod *types.Pod, nodeCPUContainersInfo CPUNodeContainers) {
defer wg.Done()
mockc.reallocContainersWithCPUPrior(ch1, pod, nodeCPUContainersInfo, cpu, 0)
}(pod, nodeCPUContainersInfo)
}
wg.Wait()
}()
for msg := range ch1 {
assert.True(t, msg.Success)
}

// 缩容
cpu = -0.1
newCPURequire = CPURate + cpu
cpuContainersInfo[pod][newCPURequire] = NodeContainers{}
cpuContainersInfo[pod][newCPURequire][node] = containers
ch2 := make(chan *types.ReallocResourceMessage)
go func() {
defer close(ch2)
wg := sync.WaitGroup{}
wg.Add(len(containersInfo))
go func(pod *types.Pod, nodeCPUContainersInfo CPUNodeContainers) {
defer wg.Done()
mockc.reallocContainersWithCPUPrior(ch2, pod, nodeCPUContainersInfo, cpu, 0)
}(pod, cpuContainersInfo[pod])

}()
for msg := range ch2 {
assert.True(t, msg.Success)
}

}

func TestReallocWithMemoryPrior(t *testing.T) {
initMockConfig()
containersInfo := map[*types.Pod]NodeContainers{}
pod, _ := mockc.GetPod("pod1")
containersInfo[pod] = NodeContainers{}
node, _ := mockc.GetNode(pod.Name, updatenodename)

containers, _ := mockc.GetContainers(ToUpdateContainerIDs)
for _, container := range containers {
containersInfo[pod][node] = append(containersInfo[pod][node], container)
}

ch1 := make(chan *types.ReallocResourceMessage)
go func() {
defer close(ch1)
wg := sync.WaitGroup{}
wg.Add(len(containersInfo))
for pod, nodeContainers := range containersInfo {
go func(pod *types.Pod, nodeContainers NodeContainers) {
defer wg.Done()
mockc.reallocContainerWithMemoryPrior(ch1, pod, nodeContainers, 0.2, 100000)
}(pod, nodeContainers)
}
wg.Wait()
}()

for msg := range ch1 {
assert.True(t, msg.Success)
}

ch2 := make(chan *types.ReallocResourceMessage)
go func() {
defer close(ch2)
wg := sync.WaitGroup{}
wg.Add(len(containersInfo))
for pod, nodeContainers := range containersInfo {
go func(pod *types.Pod, nodeContainers NodeContainers) {
defer wg.Done()
mockc.reallocContainerWithMemoryPrior(ch2, pod, nodeContainers, -0.2, -100000)
}(pod, nodeContainers)
}
wg.Wait()
}()

for msg := range ch2 {
assert.True(t, msg.Success)
}

ch3 := make(chan *types.ReallocResourceMessage)
go func() {
defer close(ch3)
wg := sync.WaitGroup{}
wg.Add(len(containersInfo))
for pod, nodeContainers := range containersInfo {
go func(pod *types.Pod, nodeContainers NodeContainers) {
defer wg.Done()
mockc.reallocContainerWithMemoryPrior(ch3, pod, nodeContainers, 0, 2600000000)
}(pod, nodeContainers)
}
wg.Wait()
}()

for msg := range ch3 {
assert.False(t, msg.Success)
}

ch4 := make(chan *types.ReallocResourceMessage)
go func() {
defer close(ch4)
wg := sync.WaitGroup{}
wg.Add(len(containersInfo))
for pod, nodeContainers := range containersInfo {
go func(pod *types.Pod, nodeContainers NodeContainers) {
defer wg.Done()
mockc.reallocContainerWithMemoryPrior(ch4, pod, nodeContainers, 0, -268400000)
}(pod, nodeContainers)
}
wg.Wait()
}()

for msg := range ch4 {
assert.False(t, msg.Success)
}

}

0 comments on commit 1a626c9

Please sign in to comment.