2016-07-25 21:39:31 +00:00
|
|
|
/*
|
|
|
|
Copyright 2016 The Kubernetes Authors.
|
|
|
|
|
|
|
|
Licensed under the Apache License, Version 2.0 (the "License");
|
|
|
|
you may not use this file except in compliance with the License.
|
|
|
|
You may obtain a copy of the License at
|
|
|
|
|
|
|
|
http://www.apache.org/licenses/LICENSE-2.0
|
|
|
|
|
|
|
|
Unless required by applicable law or agreed to in writing, software
|
|
|
|
distributed under the License is distributed on an "AS IS" BASIS,
|
|
|
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
|
|
See the License for the specific language governing permissions and
|
|
|
|
limitations under the License.
|
|
|
|
*/
|
|
|
|
|
|
|
|
package dockershim
|
|
|
|
|
|
|
|
import (
|
2016-11-02 03:20:13 +00:00
|
|
|
"errors"
|
2016-10-29 00:14:33 +00:00
|
|
|
"testing"
|
2016-08-30 00:40:28 +00:00
|
|
|
"time"
|
|
|
|
|
2017-02-03 02:28:19 +00:00
|
|
|
"github.com/blang/semver"
|
|
|
|
dockertypes "github.com/docker/engine-api/types"
|
2016-11-02 03:20:13 +00:00
|
|
|
"github.com/golang/mock/gomock"
|
|
|
|
"github.com/stretchr/testify/assert"
|
2017-02-03 02:28:19 +00:00
|
|
|
"github.com/stretchr/testify/require"
|
2016-11-02 03:20:13 +00:00
|
|
|
|
2017-01-23 18:37:22 +00:00
|
|
|
"k8s.io/client-go/util/clock"
|
2016-11-30 07:27:27 +00:00
|
|
|
runtimeapi "k8s.io/kubernetes/pkg/kubelet/api/v1alpha1/runtime"
|
2016-10-14 18:52:18 +00:00
|
|
|
containertest "k8s.io/kubernetes/pkg/kubelet/container/testing"
|
2016-07-25 21:39:31 +00:00
|
|
|
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
2016-10-29 00:14:33 +00:00
|
|
|
"k8s.io/kubernetes/pkg/kubelet/network"
|
|
|
|
"k8s.io/kubernetes/pkg/kubelet/network/mock_network"
|
2017-02-03 02:28:19 +00:00
|
|
|
"k8s.io/kubernetes/pkg/kubelet/util/cache"
|
2016-07-25 21:39:31 +00:00
|
|
|
)
|
|
|
|
|
2016-10-29 00:14:33 +00:00
|
|
|
// newTestNetworkPlugin returns a mock plugin that implements network.NetworkPlugin
|
|
|
|
func newTestNetworkPlugin(t *testing.T) *mock_network.MockNetworkPlugin {
|
|
|
|
ctrl := gomock.NewController(t)
|
|
|
|
return mock_network.NewMockNetworkPlugin(ctrl)
|
|
|
|
}
|
|
|
|
|
2016-09-27 22:13:27 +00:00
|
|
|
func newTestDockerService() (*dockerService, *dockertools.FakeDockerClient, *clock.FakeClock) {
|
2016-08-30 00:40:28 +00:00
|
|
|
fakeClock := clock.NewFakeClock(time.Time{})
|
2017-02-03 02:28:19 +00:00
|
|
|
c := dockertools.NewFakeDockerClient().WithClock(fakeClock).WithVersion("1.11.2", "1.23")
|
2017-01-31 02:57:29 +00:00
|
|
|
return &dockerService{client: c, os: &containertest.FakeOS{}, networkPlugin: &network.NoopNetworkPlugin{},
|
|
|
|
legacyCleanup: legacyCleanupFlag{done: 1}, checkpointHandler: NewTestPersistentCheckpointHandler()}, c, fakeClock
|
2016-07-25 21:39:31 +00:00
|
|
|
}
|
2016-11-02 03:20:13 +00:00
|
|
|
|
2017-02-03 02:28:19 +00:00
|
|
|
func newTestDockerServiceWithVersionCache() (*dockerService, *dockertools.FakeDockerClient, *clock.FakeClock) {
|
|
|
|
ds, c, fakeClock := newTestDockerService()
|
|
|
|
ds.versionCache = cache.NewObjectCache(
|
|
|
|
func() (interface{}, error) {
|
|
|
|
return ds.getDockerVersion()
|
|
|
|
},
|
|
|
|
time.Hour*10,
|
|
|
|
)
|
|
|
|
return ds, c, fakeClock
|
|
|
|
}
|
|
|
|
|
2016-11-02 03:20:13 +00:00
|
|
|
// TestStatus tests the runtime status logic.
|
|
|
|
func TestStatus(t *testing.T) {
|
|
|
|
ds, fDocker, _ := newTestDockerService()
|
|
|
|
|
2016-11-30 07:27:27 +00:00
|
|
|
assertStatus := func(expected map[string]bool, status *runtimeapi.RuntimeStatus) {
|
2016-11-02 03:20:13 +00:00
|
|
|
conditions := status.GetConditions()
|
|
|
|
assert.Equal(t, len(expected), len(conditions))
|
|
|
|
for k, v := range expected {
|
|
|
|
for _, c := range conditions {
|
2017-01-20 01:55:37 +00:00
|
|
|
if k == c.Type {
|
|
|
|
assert.Equal(t, v, c.Status)
|
2016-11-02 03:20:13 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Should report ready status if version returns no error.
|
|
|
|
status, err := ds.Status()
|
|
|
|
assert.NoError(t, err)
|
|
|
|
assertStatus(map[string]bool{
|
2016-11-30 07:27:27 +00:00
|
|
|
runtimeapi.RuntimeReady: true,
|
|
|
|
runtimeapi.NetworkReady: true,
|
2016-11-02 03:20:13 +00:00
|
|
|
}, status)
|
|
|
|
|
|
|
|
// Should not report ready status if version returns error.
|
|
|
|
fDocker.InjectError("version", errors.New("test error"))
|
|
|
|
status, err = ds.Status()
|
|
|
|
assert.NoError(t, err)
|
|
|
|
assertStatus(map[string]bool{
|
2016-11-30 07:27:27 +00:00
|
|
|
runtimeapi.RuntimeReady: false,
|
|
|
|
runtimeapi.NetworkReady: true,
|
2016-11-02 03:20:13 +00:00
|
|
|
}, status)
|
2016-11-03 01:23:57 +00:00
|
|
|
|
|
|
|
// Should not report ready status is network plugin returns error.
|
|
|
|
mockPlugin := newTestNetworkPlugin(t)
|
|
|
|
ds.networkPlugin = mockPlugin
|
|
|
|
defer mockPlugin.Finish()
|
|
|
|
mockPlugin.EXPECT().Status().Return(errors.New("network error"))
|
|
|
|
status, err = ds.Status()
|
|
|
|
assert.NoError(t, err)
|
|
|
|
assertStatus(map[string]bool{
|
2016-11-30 07:27:27 +00:00
|
|
|
runtimeapi.RuntimeReady: true,
|
|
|
|
runtimeapi.NetworkReady: false,
|
2016-11-03 01:23:57 +00:00
|
|
|
}, status)
|
2016-11-02 03:20:13 +00:00
|
|
|
}
|
2017-02-03 02:28:19 +00:00
|
|
|
|
|
|
|
func TestVersion(t *testing.T) {
|
|
|
|
ds, _, _ := newTestDockerService()
|
|
|
|
|
|
|
|
expectedVersion := &dockertypes.Version{Version: "1.11.2", APIVersion: "1.23.0"}
|
|
|
|
v, err := ds.getDockerVersion()
|
|
|
|
require.NoError(t, err)
|
|
|
|
assert.Equal(t, expectedVersion, v)
|
|
|
|
|
|
|
|
expectedAPIVersion := &semver.Version{Major: 1, Minor: 23, Patch: 0}
|
|
|
|
apiVersion, err := ds.getDockerAPIVersion()
|
|
|
|
require.NoError(t, err)
|
|
|
|
assert.Equal(t, expectedAPIVersion, apiVersion)
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestAPIVersionWithCache(t *testing.T) {
|
|
|
|
ds, _, _ := newTestDockerServiceWithVersionCache()
|
|
|
|
|
|
|
|
expected := &semver.Version{Major: 1, Minor: 23, Patch: 0}
|
|
|
|
version, err := ds.getDockerAPIVersion()
|
|
|
|
require.NoError(t, err)
|
|
|
|
assert.Equal(t, expected, version)
|
|
|
|
}
|