Use single table for all ContainerImagePullPolicy tests

- Cleans up assertions
 - Centralizes and simplifies handler functions

Signed-off-by: Zander Mackie <zmackie@gmail.com>
This commit is contained in:
Zander Mackie 2019-03-07 07:34:26 -05:00 committed by Brian Goff
parent ffba7659cc
commit 483c53ad9d
1 changed files with 58 additions and 131 deletions

View File

@ -18,7 +18,6 @@ import (
"github.com/docker/docker/api/types/container" "github.com/docker/docker/api/types/container"
"github.com/docker/docker/api/types/network" "github.com/docker/docker/api/types/network"
"github.com/google/go-cmp/cmp" "github.com/google/go-cmp/cmp"
"github.com/pkg/errors"
"gotest.tools/assert" "gotest.tools/assert"
is "gotest.tools/assert/cmp" is "gotest.tools/assert/cmp"
"gotest.tools/fs" "gotest.tools/fs"
@ -76,154 +75,82 @@ func TestCIDFileCloseWithWrite(t *testing.T) {
assert.NilError(t, err) assert.NilError(t, err)
} }
func TestCreateContainerPullsImageIfMissing(t *testing.T) { func TestCreateContainerImagePullPolicy(t *testing.T) {
imageName := "does-not-exist-locally" imageName := "does-not-exist-locally"
responseCounter := 0
containerID := "abcdef" containerID := "abcdef"
client := &fakeClient{
createContainerFunc: func(
config *container.Config,
hostConfig *container.HostConfig,
networkingConfig *network.NetworkingConfig,
containerName string,
) (container.ContainerCreateCreatedBody, error) {
defer func() { responseCounter++ }()
switch responseCounter {
case 0:
return container.ContainerCreateCreatedBody{}, fakeNotFound{}
case 1:
return container.ContainerCreateCreatedBody{ID: containerID}, nil
default:
return container.ContainerCreateCreatedBody{}, errors.New("unexpected")
}
},
imageCreateFunc: func(parentReference string, options types.ImageCreateOptions) (io.ReadCloser, error) {
return ioutil.NopCloser(strings.NewReader("")), nil
},
infoFunc: func() (types.Info, error) {
return types.Info{IndexServerAddress: "http://indexserver"}, nil
},
}
cli := test.NewFakeCli(client)
config := &containerConfig{ config := &containerConfig{
Config: &container.Config{ Config: &container.Config{
Image: imageName, Image: imageName,
}, },
HostConfig: &container.HostConfig{}, HostConfig: &container.HostConfig{},
} }
body, err := createContainer(context.Background(), cli, config, &createOptions{
name: "name",
platform: runtime.GOOS,
untrusted: true,
pull: PullImageMissing,
})
assert.NilError(t, err)
expected := container.ContainerCreateCreatedBody{ID: containerID}
assert.Check(t, is.DeepEqual(expected, *body))
stderr := cli.ErrBuffer().String()
assert.Check(t, is.Contains(stderr, "Unable to find image 'does-not-exist-locally:latest' locally"))
}
func TestCreateContainerNeverPullsImage(t *testing.T) { cases := []struct {
imageName := "does-not-exist-locally" PullPolicy string
responseCounter := 0 ExpectedPulls int
pullCounter := 0 ExpectedBody container.ContainerCreateCreatedBody
ExpectedErrMsg string
client := &fakeClient{ ResponseCounter int
createContainerFunc: func( }{
config *container.Config, {
hostConfig *container.HostConfig, PullPolicy: PullImageMissing,
networkingConfig *network.NetworkingConfig, ExpectedPulls: 1,
containerName string, ExpectedBody: container.ContainerCreateCreatedBody{ID: containerID},
) (container.ContainerCreateCreatedBody, error) { }, {
defer func() { responseCounter++ }() PullPolicy: PullImageAlways,
switch responseCounter { ExpectedPulls: 1,
case 0: ExpectedBody: container.ContainerCreateCreatedBody{ID: containerID},
return container.ContainerCreateCreatedBody{}, fakeNotFound{} ResponseCounter: 1, // This lets us return a container on the first pull
default: }, {
return container.ContainerCreateCreatedBody{}, errors.New("unexpected") PullPolicy: PullImageNever,
} ExpectedPulls: 0,
ExpectedErrMsg: "error fake not found",
}, },
imageCreateFunc: func(parentReference string, options types.ImageCreateOptions) (io.ReadCloser, error) { }
defer func() { pullCounter++ }() for _, c := range cases {
switch pullCounter { pullCounter := 0
case 0:
client := &fakeClient{
createContainerFunc: func(
config *container.Config,
hostConfig *container.HostConfig,
networkingConfig *network.NetworkingConfig,
containerName string,
) (container.ContainerCreateCreatedBody, error) {
defer func() { c.ResponseCounter++ }()
switch c.ResponseCounter {
case 0:
return container.ContainerCreateCreatedBody{}, fakeNotFound{}
default:
return container.ContainerCreateCreatedBody{ID: containerID}, nil
}
},
imageCreateFunc: func(parentReference string, options types.ImageCreateOptions) (io.ReadCloser, error) {
defer func() { pullCounter++ }()
return ioutil.NopCloser(strings.NewReader("")), nil return ioutil.NopCloser(strings.NewReader("")), nil
default: },
return nil, errors.New("unexpected pull") infoFunc: func() (types.Info, error) {
} return types.Info{IndexServerAddress: "http://indexserver"}, nil
}, },
infoFunc: func() (types.Info, error) { }
return types.Info{IndexServerAddress: "http://indexserver"}, nil cli := test.NewFakeCli(client)
},
}
cli := test.NewFakeCli(client)
config := &containerConfig{
Config: &container.Config{
Image: imageName,
},
HostConfig: &container.HostConfig{},
}
_, err := createContainer(context.Background(), cli, config, &createOptions{
name: "name",
platform: runtime.GOOS,
untrusted: true,
pull: PullImageNever,
})
assert.ErrorContains(t, err, "fake not found")
}
func TestCreateContainerAlwaysPullsImage(t *testing.T) {
imageName := "does-not-exist-locally"
pullTries := 7
responseCounter := 0
pullCounter := 0
containerID := "abcdef"
client := &fakeClient{
createContainerFunc: func(
config *container.Config,
hostConfig *container.HostConfig,
networkingConfig *network.NetworkingConfig,
containerName string,
) (container.ContainerCreateCreatedBody, error) {
defer func() { responseCounter++ }()
switch responseCounter {
default:
return container.ContainerCreateCreatedBody{ID: containerID}, nil
}
},
imageCreateFunc: func(parentReference string, options types.ImageCreateOptions) (io.ReadCloser, error) {
defer func() { pullCounter++ }()
return ioutil.NopCloser(strings.NewReader("")), nil
},
infoFunc: func() (types.Info, error) {
return types.Info{IndexServerAddress: "http://indexserver"}, nil
},
}
cli := test.NewFakeCli(client)
config := &containerConfig{
Config: &container.Config{
Image: imageName,
},
HostConfig: &container.HostConfig{},
}
for i := 0; i < pullTries; i++ {
body, err := createContainer(context.Background(), cli, config, &createOptions{ body, err := createContainer(context.Background(), cli, config, &createOptions{
name: "name", name: "name",
platform: runtime.GOOS, platform: runtime.GOOS,
untrusted: true, untrusted: true,
pull: PullImageAlways, pull: c.PullPolicy,
}) })
assert.NilError(t, err)
expected := container.ContainerCreateCreatedBody{ID: containerID} if c.ExpectedErrMsg != "" {
assert.Check(t, is.DeepEqual(expected, *body)) assert.ErrorContains(t, err, c.ExpectedErrMsg)
} else {
assert.NilError(t, err)
assert.Check(t, is.DeepEqual(c.ExpectedBody, *body))
}
assert.Check(t, is.Equal(c.ExpectedPulls, pullCounter))
} }
assert.Check(t, is.Equal(responseCounter, pullCounter))
} }
func TestNewCreateCommandWithContentTrustErrors(t *testing.T) { func TestNewCreateCommandWithContentTrustErrors(t *testing.T) {
testCases := []struct { testCases := []struct {
name string name string