Updating scheduler unit tests

Signed-off-by: Nishant Totla <nishanttotla@gmail.com>
This commit is contained in:
Nishant Totla 2016-03-25 14:34:17 -07:00
parent 6d2937b3ec
commit 859c710bdd
No known key found for this signature in database
GPG Key ID: 7EA5781C9B3D0C19
8 changed files with 264 additions and 210 deletions

View File

@ -4,9 +4,10 @@ import (
"testing"
"github.com/docker/engine-api/types"
containertypes "github.com/docker/engine-api/types/container"
networktypes "github.com/docker/engine-api/types/network"
"github.com/docker/swarm/cluster"
"github.com/docker/swarm/scheduler/node"
"github.com/samalba/dockerclient"
"github.com/stretchr/testify/assert"
)
@ -19,12 +20,12 @@ func TestAffinityFilter(t *testing.T) {
Name: "node-0-name",
Addr: "node-0",
Containers: []*cluster.Container{
{Container: dockerclient.Container{
Id: "container-n0-0-id",
{Container: types.Container{
ID: "container-n0-0-id",
Names: []string{"/container-n0-0-name"},
}},
{Container: dockerclient.Container{
Id: "container-n0-1-id",
{Container: types.Container{
ID: "container-n0-1-id",
Names: []string{"/container-n0-1-name"},
}},
},
@ -38,12 +39,12 @@ func TestAffinityFilter(t *testing.T) {
Name: "node-1-name",
Addr: "node-1",
Containers: []*cluster.Container{
{Container: dockerclient.Container{
Id: "container-n1-0-id",
{Container: types.Container{
ID: "container-n1-0-id",
Names: []string{"/container-n1-0-name"},
}},
{Container: dockerclient.Container{
Id: "container-n1-1-id",
{Container: types.Container{
ID: "container-n1-1-id",
Names: []string{"/container-n1-1-name"},
}},
},
@ -68,135 +69,135 @@ func TestAffinityFilter(t *testing.T) {
assert.Equal(t, result, nodes)
// Set a constraint that cannot be fulfilled and expect an error back.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container==does_not_exsits"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container==does_not_exist"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
// Set a constraint that can only be filled by a single node.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container==container-n0*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container==container-n0*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// This constraint can only be fulfilled by a subset of nodes.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container==container-*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container==container-*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
assert.NotContains(t, result, nodes[2])
// Validate by id.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container==container-n0-0-id"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container==container-n0-0-id"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// Validate by id.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container!=container-n0-0-id"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container!=container-n0-0-id"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
assert.NotContains(t, result, nodes[0])
// Validate by id.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container!=container-n0-1-id"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container!=container-n0-1-id"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
assert.NotContains(t, result, nodes[0])
// Validate by name.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container==container-n1-0-name"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container==container-n1-0-name"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
// Validate by name.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container!=container-n1-0-name"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container!=container-n1-0-name"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
assert.NotContains(t, result, nodes[1])
// Validate by name.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container!=container-n1-1-name"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container!=container-n1-1-name"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
assert.NotContains(t, result, nodes[1])
// Conflicting Constraint
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container!=container-n1-1-name", "affinity:container==container-n1-1-name"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container!=container-n1-1-name", "affinity:container==container-n1-1-name"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
// Validate images by id
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==image-0-id"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==image-0-id"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// Validate images by name
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==image-0:tag3"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==image-0:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
// Validate images by name
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image!=image-0:tag3"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image!=image-0:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
// Validate images by name
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==image-1"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==image-1"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
// Validate images by name
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image!=image-1"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image!=image-1"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
// Ensure that constraints can be chained.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container!=container-n0-1-id", "affinity:container!=container-n1-1-id"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container!=container-n0-1-id", "affinity:container!=container-n1-1-id"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[2])
// Ensure that constraints can be chained.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:container==container-n0-1-id", "affinity:container==container-n1-1-id"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:container==container-n0-1-id", "affinity:container==container-n1-1-id"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
//Tests for Soft affinity
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==~image-0:tag3"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==~image-0:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==~ima~ge-0:tag3"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==~ima~ge-0:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==~image-1:tag3"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==~image-1:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==~image-1:tag3"}}), nodes, false)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==~image-1:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, false)
assert.NoError(t, err)
assert.Len(t, result, 3)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==~image-*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==~image-*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image!=~image-*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image!=~image-*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[2])
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==~/image-\\d*/"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==~/image-\\d*/"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
// Not support = any more
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image=image-0:tag3"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image=image-0:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
// Not support =! any more
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image=!image-0:tag3"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image=!image-0:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
@ -211,8 +212,8 @@ func TestAffinityFilterLabels(t *testing.T) {
Name: "node-0-name",
Addr: "node-0",
Containers: []*cluster.Container{
{Container: dockerclient.Container{
Id: "container-n0-id",
{Container: types.Container{
ID: "container-n0-id",
Names: []string{"/container-n0-name"},
}},
},
@ -226,8 +227,8 @@ func TestAffinityFilterLabels(t *testing.T) {
Name: "node-1-name",
Addr: "node-1",
Containers: []*cluster.Container{
{Container: dockerclient.Container{
Id: "container-n1-id",
{Container: types.Container{
ID: "container-n1-id",
Names: []string{"/container-n1-name"},
}},
},
@ -241,22 +242,22 @@ func TestAffinityFilterLabels(t *testing.T) {
err error
)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==image-1"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==image-1"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image!=image-1"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image!=image-1"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Labels: map[string]string{"com.docker.swarm.affinities": "[\"image==image-1\"]"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Labels: map[string]string{"com.docker.swarm.affinities": "[\"image==image-1\"]"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Labels: map[string]string{"com.docker.swarm.affinities": "[\"image!=image-1\"]"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Labels: map[string]string{"com.docker.swarm.affinities": "[\"image!=image-1\"]"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])

View File

@ -3,9 +3,10 @@ package filter
import (
"testing"
containertypes "github.com/docker/engine-api/types/container"
networktypes "github.com/docker/engine-api/types/network"
"github.com/docker/swarm/cluster"
"github.com/docker/swarm/scheduler/node"
"github.com/samalba/dockerclient"
"github.com/stretchr/testify/assert"
)
@ -66,49 +67,49 @@ func TestConstrainteFilter(t *testing.T) {
assert.Equal(t, result, nodes)
// Set a constraint that cannot be fulfilled and expect an error back.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:does_not_exist==true"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:does_not_exist==true"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
// Set a contraint that can only be filled by a single node.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:name==node1"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:name==node1"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
// This constraint can only be fulfilled by a subset of nodes.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:group==1"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:group==1"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
assert.NotContains(t, result, nodes[2])
// Validate node pinning by id.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:node==node-2-id"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:node==node-2-id"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[2])
// Validate node pinning by name.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:node==node-1-name"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:node==node-1-name"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
// Make sure constraints are evaluated as logical ANDs.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:name==node0", "constraint:group==1"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:name==node0", "constraint:group==1"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// Check matching
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:region==us"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:region==us"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:region==us*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:region==us*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:region==*us*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:region==*us*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
}
@ -122,22 +123,22 @@ func TestConstraintNotExpr(t *testing.T) {
)
// Check not (!) expression
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:name!=node0"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:name!=node0"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 3)
// Check not does_not_exist. All should be found
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:name!=does_not_exist"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:name!=does_not_exist"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 4)
// Check name must not start with n
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:name!=n*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:name!=n*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
// Check not with globber pattern
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:region!=us*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:region!=us*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
}
@ -151,22 +152,22 @@ func TestConstraintRegExp(t *testing.T) {
)
// Check with regular expression /node\d/ matches node{0..2}
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{`constraint:name==/node\d/`}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{`constraint:name==/node\d/`}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 3)
// Check with regular expression /node\d/ matches node{0..2}
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{`constraint:name==/node[12]/`}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{`constraint:name==/node[12]/`}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
// Check with regular expression ! and regexp /node[12]/ matches node[0] and node[3]
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{`constraint:name!=/node[12]/`}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{`constraint:name!=/node[12]/`}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
// Validate node pinning by ! and regexp.
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:node!=/node-[01]-id/"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:node!=/node-[01]-id/"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
}
@ -187,19 +188,19 @@ func TestFilterRegExpCaseInsensitive(t *testing.T) {
}
// Case-sensitive, so not match
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{`constraint:name==/abcdef/`}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{`constraint:name==/abcdef/`}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
// Match with case-insensitive
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{`constraint:name==/(?i)abcdef/`}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{`constraint:name==/(?i)abcdef/`}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[3])
assert.Equal(t, result[0].Labels["name"], "aBcDeF")
// Test ! filter combined with case insensitive
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{`constraint:name!=/(?i)abc*/`}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{`constraint:name!=/(?i)abc*/`}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 3)
}
@ -213,17 +214,17 @@ func TestFilterEquals(t *testing.T) {
)
// Check == comparison
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:name==node0"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:name==node0"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
// Test == with glob
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:region==us*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:region==us*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
// Validate node name with ==
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:node==node-1-name"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:node==node-1-name"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
@ -237,11 +238,11 @@ func TestUnsupportedOperators(t *testing.T) {
err error
)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:name=node0"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:name=node0"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:name=!node0"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:name=!node0"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
}
@ -254,26 +255,26 @@ func TestFilterSoftConstraint(t *testing.T) {
err error
)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:node==~node-1-name"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:node==~node-1-name"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{`constraint:name!=~/(?i)abc*/`}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{`constraint:name!=~/(?i)abc*/`}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 4)
// Check not with globber pattern
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:region!=~us*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:region!=~us*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 2)
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:region!=~can*"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:region!=~can*"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 4)
// Check matching
result, err = f.Filter(cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"constraint:region==~us~"}}), nodes, true)
result, err = f.Filter(cluster.BuildContainerConfig(containertypes.Config{Env: []string{"constraint:region==~us~"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{}), nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)
}

View File

@ -3,9 +3,11 @@ package filter
import (
"testing"
"github.com/docker/engine-api/types"
containertypes "github.com/docker/engine-api/types/container"
networktypes "github.com/docker/engine-api/types/network"
"github.com/docker/swarm/cluster"
"github.com/docker/swarm/scheduler/node"
"github.com/samalba/dockerclient"
"github.com/stretchr/testify/assert"
)
@ -18,7 +20,7 @@ func TestDependencyFilterSimple(t *testing.T) {
Name: "node-0-name",
Addr: "node-0",
Containers: []*cluster.Container{{
Container: dockerclient.Container{Id: "c0"},
Container: types.Container{ID: "c0"},
Config: &cluster.ContainerConfig{},
}},
},
@ -28,7 +30,7 @@ func TestDependencyFilterSimple(t *testing.T) {
Name: "node-1-name",
Addr: "node-1",
Containers: []*cluster.Container{{
Container: dockerclient.Container{Id: "c1"},
Container: types.Container{ID: "c1"},
Config: &cluster.ContainerConfig{},
}},
},
@ -38,7 +40,7 @@ func TestDependencyFilterSimple(t *testing.T) {
Name: "node-2-name",
Addr: "node-2",
Containers: []*cluster.Container{{
Container: dockerclient.Container{Id: "c2"},
Container: types.Container{ID: "c2"},
Config: &cluster.ContainerConfig{},
}},
},
@ -55,54 +57,54 @@ func TestDependencyFilterSimple(t *testing.T) {
assert.Equal(t, result, nodes)
// volumes-from.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c0"},
}}}
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// volumes-from:rw
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c0:rw"},
}}}
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// volumes-from:ro
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c0:ro"},
}}}
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// link.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
Links: []string{"c1:foobar"},
}}}
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[1])
// net.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
NetworkMode: "container:c2",
}}}
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
NetworkMode: containertypes.NetworkMode("container:c2"),
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[2])
// net not prefixed by "container:" should be ignored.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
NetworkMode: "bridge",
}}}
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
NetworkMode: containertypes.NetworkMode("bridge"),
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Equal(t, result, nodes)
@ -119,11 +121,11 @@ func TestDependencyFilterMulti(t *testing.T) {
Addr: "node-0",
Containers: []*cluster.Container{
{
Container: dockerclient.Container{Id: "c0"},
Container: types.Container{ID: "c0"},
Config: &cluster.ContainerConfig{},
},
{
Container: dockerclient.Container{Id: "c1"},
Container: types.Container{ID: "c1"},
Config: &cluster.ContainerConfig{},
},
},
@ -136,7 +138,7 @@ func TestDependencyFilterMulti(t *testing.T) {
Addr: "node-1",
Containers: []*cluster.Container{
{
Container: dockerclient.Container{Id: "c2"},
Container: types.Container{ID: "c2"},
Config: &cluster.ContainerConfig{},
},
},
@ -155,36 +157,36 @@ func TestDependencyFilterMulti(t *testing.T) {
)
// Depend on c0 which is on nodes[0]
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c0"},
}}}
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// Depend on c1 which is on nodes[0]
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c1"},
}}}
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// Depend on c0 AND c1 which are both on nodes[0]
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c0", "c1"},
}}}
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// Depend on c0 AND c2 which are on different nodes.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c0", "c2"},
}}}
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.Error(t, err)
}
@ -200,11 +202,11 @@ func TestDependencyFilterChaining(t *testing.T) {
Addr: "node-0",
Containers: []*cluster.Container{
{
Container: dockerclient.Container{Id: "c0"},
Container: types.Container{ID: "c0"},
Config: &cluster.ContainerConfig{},
},
{
Container: dockerclient.Container{Id: "c1"},
Container: types.Container{ID: "c1"},
Config: &cluster.ContainerConfig{},
},
},
@ -217,7 +219,7 @@ func TestDependencyFilterChaining(t *testing.T) {
Addr: "node-1",
Containers: []*cluster.Container{
{
Container: dockerclient.Container{Id: "c2"},
Container: types.Container{ID: "c2"},
Config: &cluster.ContainerConfig{},
},
},
@ -236,26 +238,22 @@ func TestDependencyFilterChaining(t *testing.T) {
)
// Different dependencies on c0 and c1
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{
HostConfig: dockerclient.HostConfig{
VolumesFrom: []string{"c0"},
Links: []string{"c1"},
NetworkMode: "container:c1",
},
}}
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c0"},
Links: []string{"c1"},
NetworkMode: containertypes.NetworkMode("container:c1"),
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Len(t, result, 1)
assert.Equal(t, result[0], nodes[0])
// Different dependencies on c0 and c2
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{
HostConfig: dockerclient.HostConfig{
VolumesFrom: []string{"c0"},
Links: []string{"c2"},
NetworkMode: "container:c1",
},
}}
config = &cluster.ContainerConfig{containertypes.Config{}, containertypes.HostConfig{
VolumesFrom: []string{"c0"},
Links: []string{"c2"},
NetworkMode: containertypes.NetworkMode("container:c1"),
}, networktypes.NetworkingConfig{}}
result, err = f.Filter(config, nodes, true)
assert.Error(t, err)
}

View File

@ -4,9 +4,10 @@ import (
"testing"
"github.com/docker/engine-api/types"
containertypes "github.com/docker/engine-api/types/container"
networktypes "github.com/docker/engine-api/types/network"
"github.com/docker/swarm/cluster"
"github.com/docker/swarm/scheduler/node"
"github.com/samalba/dockerclient"
"github.com/stretchr/testify/assert"
)
@ -18,14 +19,18 @@ func TestApplyFilters(t *testing.T) {
Name: "node-0-name",
Addr: "node-0",
Containers: []*cluster.Container{
{Container: dockerclient.Container{
Id: "container-n0-0-id",
Names: []string{"/container-n0-0-name"},
}},
{Container: dockerclient.Container{
Id: "container-n0-1-id",
Names: []string{"/container-n0-1-name"},
}},
{
Container: types.Container{
ID: "container-n0-0-id",
Names: []string{"/container-n0-0-name"},
},
},
{
Container: types.Container{
ID: "container-n0-1-id",
Names: []string{"/container-n0-1-name"},
},
},
},
Images: []*cluster.Image{{Image: types.Image{
ID: "image-0-id",
@ -39,14 +44,14 @@ func TestApplyFilters(t *testing.T) {
Addr: "node-1",
Containers: []*cluster.Container{
{
Container: dockerclient.Container{
Id: "container-n1-0-id",
Container: types.Container{
ID: "container-n1-0-id",
Names: []string{"/container-n1-0-name"},
},
},
{
Container: dockerclient.Container{
Id: "container-n1-1-id",
Container: types.Container{
ID: "container-n1-1-id",
Names: []string{"/container-n1-1-name"},
},
},
@ -63,7 +68,7 @@ func TestApplyFilters(t *testing.T) {
)
//Tests for Soft affinity, it should be considered as last
config := cluster.BuildContainerConfig(dockerclient.ContainerConfig{Env: []string{"affinity:image==~image-0:tag3"}})
config := cluster.BuildContainerConfig(containertypes.Config{Env: []string{"affinity:image==~image-0:tag3"}}, containertypes.HostConfig{}, networktypes.NetworkingConfig{})
result, err = ApplyFilters(filters, config, nodes, true)
assert.Error(t, err)
assert.Len(t, result, 0)

View File

@ -64,7 +64,7 @@ func (p *PortFilter) filterBridge(config *cluster.ContainerConfig, nodes []*node
func (p *PortFilter) portAlreadyExposed(node *node.Node, requestedPort string) bool {
for _, c := range node.Containers {
if c.Info.HostConfig.NetworkMode == "host" {
if c.Info.HostConfig != nil && c.Info.HostConfig.NetworkMode == "host" {
for port := range c.Info.Config.ExposedPorts {
if string(port) == requestedPort {
return true
@ -89,7 +89,7 @@ func (p *PortFilter) portAlreadyInUse(node *node.Node, requested nat.PortBinding
// NetworkSettings.Port will be null and we have to check
// HostConfig.PortBindings to find out the mapping.
if p.compare(requested, c.Info.HostConfig.PortBindings) || p.compare(requested, c.Info.NetworkSettings.Ports) {
if (c.Info.HostConfig != nil && p.compare(requested, c.Info.HostConfig.PortBindings)) || (c.Info.NetworkSettings != nil && p.compare(requested, c.Info.NetworkSettings.Ports)) {
return true
}
}

View File

@ -4,21 +4,22 @@ import (
"fmt"
"testing"
"github.com/docker/engine-api/types"
containertypes "github.com/docker/engine-api/types/container"
networktypes "github.com/docker/engine-api/types/network"
"github.com/docker/go-connections/nat"
"github.com/docker/swarm/cluster"
"github.com/docker/swarm/scheduler/node"
"github.com/samalba/dockerclient"
"github.com/stretchr/testify/assert"
)
func makeBinding(ip, port string) map[string][]dockerclient.PortBinding {
return map[string][]dockerclient.PortBinding{
fmt.Sprintf("%s/tcp", port): {
{
HostIp: ip,
HostPort: port,
},
},
func makeBinding(ip, port string) nat.PortMap {
binding := nat.PortBinding{
HostIP: ip,
HostPort: port,
}
bindingMap := map[nat.Port][]nat.PortBinding{nat.Port(fmt.Sprintf("%s/tcp", port)): {binding}}
return nat.PortMap(bindingMap)
}
func TestPortFilterNoConflicts(t *testing.T) {
@ -46,18 +47,18 @@ func TestPortFilterNoConflicts(t *testing.T) {
)
// Request no ports.
config := &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
PortBindings: map[string][]dockerclient.PortBinding{},
}}}
config := &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: map[nat.Port][]nat.PortBinding{},
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// Make sure we don't filter anything out.
result, err = p.Filter(config, nodes, true)
assert.NoError(t, err)
assert.Equal(t, result, nodes)
// Request port 80.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("", "80"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// Since there are no other containers in the cluster, this shouldn't
// filter anything either.
@ -66,7 +67,13 @@ func TestPortFilterNoConflicts(t *testing.T) {
assert.Equal(t, result, nodes)
// Add a container taking a different (4242) port.
container := &cluster.Container{Container: dockerclient.Container{Id: "c1"}, Info: dockerclient.ContainerInfo{HostConfig: &dockerclient.HostConfig{PortBindings: makeBinding("", "4242")}}}
container := &cluster.Container{Container: types.Container{ID: "c1"}, Info: types.ContainerJSON{
ContainerJSONBase: &types.ContainerJSONBase{
HostConfig: &containertypes.HostConfig{
PortBindings: makeBinding("", "4242"),
},
},
}}
assert.NoError(t, nodes[0].AddContainer(container))
// Since no node is using port 80, there should be no filter
@ -100,13 +107,19 @@ func TestPortFilterSimple(t *testing.T) {
)
// Add a container taking away port 80 to nodes[0].
container := &cluster.Container{Container: dockerclient.Container{Id: "c1"}, Info: dockerclient.ContainerInfo{HostConfig: &dockerclient.HostConfig{PortBindings: makeBinding("", "80")}}}
container := &cluster.Container{Container: types.Container{ID: "c1"}, Info: types.ContainerJSON{
ContainerJSONBase: &types.ContainerJSONBase{
HostConfig: &containertypes.HostConfig{
PortBindings: makeBinding("", "80"),
},
},
}}
assert.NoError(t, nodes[0].AddContainer(container))
// Request port 80.
config := &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config := &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("", "80"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// nodes[0] should be excluded since port 80 is taken away.
result, err = p.Filter(config, nodes, true)
@ -139,13 +152,19 @@ func TestPortFilterDifferentInterfaces(t *testing.T) {
)
// Add a container taking away port 80 on every interface to nodes[0].
container := &cluster.Container{Container: dockerclient.Container{Id: "c1"}, Info: dockerclient.ContainerInfo{HostConfig: &dockerclient.HostConfig{PortBindings: makeBinding("", "80")}}}
container := &cluster.Container{Container: types.Container{ID: "c1"}, Info: types.ContainerJSON{
ContainerJSONBase: &types.ContainerJSONBase{
HostConfig: &containertypes.HostConfig{
PortBindings: makeBinding("", "80"),
},
},
}}
assert.NoError(t, nodes[0].AddContainer(container))
// Request port 80 for the local interface.
config := &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config := &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("127.0.0.1", "80"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// nodes[0] should be excluded since port 80 is taken away for every
// interface.
@ -155,12 +174,18 @@ func TestPortFilterDifferentInterfaces(t *testing.T) {
// Add a container taking away port 4242 on the local interface of
// nodes[1].
container = &cluster.Container{Container: dockerclient.Container{Id: "c1"}, Info: dockerclient.ContainerInfo{HostConfig: &dockerclient.HostConfig{PortBindings: makeBinding("127.0.0.1", "4242")}}}
container = &cluster.Container{Container: types.Container{ID: "c1"}, Info: types.ContainerJSON{
ContainerJSONBase: &types.ContainerJSONBase{
HostConfig: &containertypes.HostConfig{
PortBindings: makeBinding("127.0.0.1", "4242"),
},
},
}}
assert.NoError(t, nodes[1].AddContainer(container))
// Request port 4242 on the same interface.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("127.0.0.1", "4242"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// nodes[1] should be excluded since port 4242 is already taken on that
// interface.
result, err = p.Filter(config, nodes, true)
@ -168,27 +193,27 @@ func TestPortFilterDifferentInterfaces(t *testing.T) {
assert.NotContains(t, result, nodes[1])
// Request port 4242 on every interface.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("0.0.0.0", "4242"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// nodes[1] should still be excluded since the port is not available on the same interface.
result, err = p.Filter(config, nodes, true)
assert.NoError(t, err)
assert.NotContains(t, result, nodes[1])
// Request port 4242 on every interface using an alternative syntax.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("", "4242"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// nodes[1] should still be excluded since the port is not available on the same interface.
result, err = p.Filter(config, nodes, true)
assert.NoError(t, err)
assert.NotContains(t, result, nodes[1])
// Finally, request port 4242 on a different interface.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("192.168.1.1", "4242"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// nodes[1] should be included this time since the port is available on the
// other interface.
result, err = p.Filter(config, nodes, true)
@ -225,32 +250,42 @@ func TestPortFilterRandomAssignment(t *testing.T) {
// HostPort defined and NetworkSettings.Ports should contain the actual
// mapped port.
container := &cluster.Container{
Container: dockerclient.Container{Id: "c1"},
Info: dockerclient.ContainerInfo{HostConfig: &dockerclient.HostConfig{
PortBindings: map[string][]dockerclient.PortBinding{
"80/tcp": {
{
HostIp: "",
HostPort: "",
Container: types.Container{ID: "c1"},
Info: types.ContainerJSON{
ContainerJSONBase: &types.ContainerJSONBase{
HostConfig: &containertypes.HostConfig{
PortBindings: nat.PortMap(
map[nat.Port][]nat.PortBinding{
nat.Port("80/tcp"): {
{
HostIP: "",
HostPort: "",
},
},
},
),
}}}}
container.Info.NetworkSettings = &types.NetworkSettings{
NetworkSettingsBase: types.NetworkSettingsBase{
Ports: nat.PortMap(
map[nat.Port][]nat.PortBinding{
nat.Port("80/tcp"): {
{
HostIP: "127.0.0.1",
HostPort: "1234",
},
},
},
}},
},
}
container.Info.NetworkSettings.Ports = map[string][]dockerclient.PortBinding{
"80/tcp": {
{
HostIp: "127.0.0.1",
HostPort: "1234",
},
),
}}
assert.NoError(t, nodes[0].AddContainer(container))
// Request port 80.
config := &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config := &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("", "80"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// Since port "80" has been mapped to "1234", we should be able to request "80".
result, err = p.Filter(config, nodes, true)
@ -258,9 +293,9 @@ func TestPortFilterRandomAssignment(t *testing.T) {
assert.Equal(t, result, nodes)
// However, we should not be able to request "1234" since it has been used for a random assignment.
config = &cluster.ContainerConfig{dockerclient.ContainerConfig{HostConfig: dockerclient.HostConfig{
config = &cluster.ContainerConfig{Config: containertypes.Config{}, HostConfig: containertypes.HostConfig{
PortBindings: makeBinding("", "1234"),
}}}
}, NetworkingConfig: networktypes.NetworkingConfig{}}
result, err = p.Filter(config, nodes, true)
assert.NoError(t, err)
assert.NotContains(t, result, nodes[0])
@ -292,26 +327,26 @@ func TestPortFilterForHostMode(t *testing.T) {
// Add a container taking away port 80 in the host mode to nodes[0].
container := &cluster.Container{
Container: dockerclient.Container{Id: "c1"},
Info: dockerclient.ContainerInfo{
Config: &dockerclient.ContainerConfig{
ExposedPorts: map[string]struct{}{"80": {}},
Container: types.Container{ID: "c1"},
Info: types.ContainerJSON{
Config: &containertypes.Config{
ExposedPorts: map[nat.Port]struct{}{nat.Port("80"): {}},
},
HostConfig: &dockerclient.HostConfig{
NetworkMode: "host",
ContainerJSONBase: &types.ContainerJSONBase{
HostConfig: &containertypes.HostConfig{
NetworkMode: containertypes.NetworkMode("host"),
},
},
},
}
}}
assert.NoError(t, nodes[0].AddContainer(container))
// Request port 80 in the host mode
config := &cluster.ContainerConfig{dockerclient.ContainerConfig{
ExposedPorts: map[string]struct{}{"80": {}},
HostConfig: dockerclient.HostConfig{
NetworkMode: "host",
},
}}
config := &cluster.ContainerConfig{Config: containertypes.Config{
ExposedPorts: map[nat.Port]struct{}{nat.Port("80"): {}},
}, HostConfig: containertypes.HostConfig{
NetworkMode: containertypes.NetworkMode("host"),
}, NetworkingConfig: networktypes.NetworkingConfig{}}
// nodes[0] should be excluded since port 80 is taken away
result, err = p.Filter(config, nodes, true)

View File

@ -3,11 +3,12 @@ package scheduler
import (
"testing"
containertypes "github.com/docker/engine-api/types/container"
networktypes "github.com/docker/engine-api/types/network"
"github.com/docker/swarm/cluster"
"github.com/docker/swarm/scheduler/filter"
"github.com/docker/swarm/scheduler/node"
"github.com/docker/swarm/scheduler/strategy"
"github.com/samalba/dockerclient"
"github.com/stretchr/testify/assert"
)
@ -42,11 +43,14 @@ func TestSelectNodesForContainer(t *testing.T) {
},
}
config = cluster.BuildContainerConfig(dockerclient.ContainerConfig{
Memory: 1024 * 1024 * 1024,
CpuShares: 2,
Env: []string{"constraint:group==~1"},
})
config = cluster.BuildContainerConfig(containertypes.Config{
Env: []string{"constraint:group==~1"},
}, containertypes.HostConfig{
Resources: containertypes.Resources{
Memory: 1024 * 1024 * 1024,
CPUShares: 2,
},
}, networktypes.NetworkingConfig{})
)
candidates, err := s.SelectNodesForContainer(nodes, config)
assert.NoError(t, err)

View File

@ -4,9 +4,11 @@ import (
"fmt"
"testing"
"github.com/docker/engine-api/types"
containertypes "github.com/docker/engine-api/types/container"
networktypes "github.com/docker/engine-api/types/network"
"github.com/docker/swarm/cluster"
"github.com/docker/swarm/scheduler/node"
"github.com/samalba/dockerclient"
"github.com/stretchr/testify/assert"
)
@ -24,14 +26,22 @@ func createNode(ID string, memory int64, cpus int64) *node.Node {
}
func createConfig(memory int64, cpus int64) *cluster.ContainerConfig {
return cluster.BuildContainerConfig(dockerclient.ContainerConfig{Memory: memory * 1024 * 1024 * 1024, CpuShares: cpus})
return cluster.BuildContainerConfig(containertypes.Config{}, containertypes.HostConfig{
Resources: containertypes.Resources{
Memory: memory * 1024 * 1024 * 1024,
CPUShares: cpus,
},
}, networktypes.NetworkingConfig{})
}
func createContainer(ID string, config *cluster.ContainerConfig) *cluster.Container {
return &cluster.Container{
Container: dockerclient.Container{Id: ID},
Container: types.Container{ID: ID},
Config: config,
Info: dockerclient.ContainerInfo{Config: &config.ContainerConfig},
// FIXMEENGINEAPI - maybe Hostconfig and networkingconfig also need to be stored
Info: types.ContainerJSON{
Config: &config.Config,
},
}
}