Move container manager into a separate package.
Inject container manager into Kubelet. This lets us stub out container manager during integration testing.
This commit is contained in:
parent
129dbc734c
commit
4ad3d6f5fe
@ -49,6 +49,7 @@ import (
|
|||||||
replicationcontroller "k8s.io/kubernetes/pkg/controller/replication"
|
replicationcontroller "k8s.io/kubernetes/pkg/controller/replication"
|
||||||
"k8s.io/kubernetes/pkg/fields"
|
"k8s.io/kubernetes/pkg/fields"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
||||||
|
"k8s.io/kubernetes/pkg/kubelet/cm"
|
||||||
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
||||||
kubetypes "k8s.io/kubernetes/pkg/kubelet/types"
|
kubetypes "k8s.io/kubernetes/pkg/kubelet/types"
|
||||||
@ -216,7 +217,7 @@ func startComponents(firstManifestURL, secondManifestURL string) (string, string
|
|||||||
configFilePath := integration.MakeTempDirOrDie("config", testRootDir)
|
configFilePath := integration.MakeTempDirOrDie("config", testRootDir)
|
||||||
glog.Infof("Using %s as root dir for kubelet #1", testRootDir)
|
glog.Infof("Using %s as root dir for kubelet #1", testRootDir)
|
||||||
fakeDocker1.VersionInfo = docker.Env{"ApiVersion=1.20"}
|
fakeDocker1.VersionInfo = docker.Env{"ApiVersion=1.20"}
|
||||||
|
cm := cm.NewStubContainerManager()
|
||||||
kcfg := kubeletapp.SimpleKubelet(
|
kcfg := kubeletapp.SimpleKubelet(
|
||||||
cl,
|
cl,
|
||||||
&fakeDocker1,
|
&fakeDocker1,
|
||||||
@ -238,7 +239,8 @@ func startComponents(firstManifestURL, secondManifestURL string) (string, string
|
|||||||
10*time.Second, /* MinimumGCAge */
|
10*time.Second, /* MinimumGCAge */
|
||||||
3*time.Second, /* NodeStatusUpdateFrequency */
|
3*time.Second, /* NodeStatusUpdateFrequency */
|
||||||
10*time.Second, /* SyncFrequency */
|
10*time.Second, /* SyncFrequency */
|
||||||
40 /* MaxPods */)
|
40, /* MaxPods */
|
||||||
|
cm)
|
||||||
|
|
||||||
kubeletapp.RunKubelet(kcfg)
|
kubeletapp.RunKubelet(kcfg)
|
||||||
// Kubelet (machine)
|
// Kubelet (machine)
|
||||||
@ -270,7 +272,8 @@ func startComponents(firstManifestURL, secondManifestURL string) (string, string
|
|||||||
3*time.Second, /* NodeStatusUpdateFrequency */
|
3*time.Second, /* NodeStatusUpdateFrequency */
|
||||||
10*time.Second, /* SyncFrequency */
|
10*time.Second, /* SyncFrequency */
|
||||||
|
|
||||||
40 /* MaxPods */)
|
40, /* MaxPods */
|
||||||
|
cm)
|
||||||
|
|
||||||
kubeletapp.RunKubelet(kcfg)
|
kubeletapp.RunKubelet(kcfg)
|
||||||
return apiServer.URL, configFilePath
|
return apiServer.URL, configFilePath
|
||||||
|
@ -44,6 +44,7 @@ import (
|
|||||||
"k8s.io/kubernetes/pkg/healthz"
|
"k8s.io/kubernetes/pkg/healthz"
|
||||||
"k8s.io/kubernetes/pkg/kubelet"
|
"k8s.io/kubernetes/pkg/kubelet"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
||||||
|
"k8s.io/kubernetes/pkg/kubelet/cm"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/config"
|
"k8s.io/kubernetes/pkg/kubelet/config"
|
||||||
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
||||||
@ -409,6 +410,7 @@ func (s *KubeletServer) UnsecuredKubeletConfig() (*KubeletConfig, error) {
|
|||||||
ClusterDomain: s.ClusterDomain,
|
ClusterDomain: s.ClusterDomain,
|
||||||
ConfigFile: s.Config,
|
ConfigFile: s.Config,
|
||||||
ConfigureCBR0: s.ConfigureCBR0,
|
ConfigureCBR0: s.ConfigureCBR0,
|
||||||
|
ContainerManager: nil,
|
||||||
ContainerRuntime: s.ContainerRuntime,
|
ContainerRuntime: s.ContainerRuntime,
|
||||||
CPUCFSQuota: s.CPUCFSQuota,
|
CPUCFSQuota: s.CPUCFSQuota,
|
||||||
DiskSpacePolicy: diskSpacePolicy,
|
DiskSpacePolicy: diskSpacePolicy,
|
||||||
@ -474,6 +476,7 @@ func (s *KubeletServer) UnsecuredKubeletConfig() (*KubeletConfig, error) {
|
|||||||
// Otherwise, the caller is assumed to have set up the KubeletConfig object and all defaults
|
// Otherwise, the caller is assumed to have set up the KubeletConfig object and all defaults
|
||||||
// will be ignored.
|
// will be ignored.
|
||||||
func (s *KubeletServer) Run(kcfg *KubeletConfig) error {
|
func (s *KubeletServer) Run(kcfg *KubeletConfig) error {
|
||||||
|
var err error
|
||||||
if kcfg == nil {
|
if kcfg == nil {
|
||||||
cfg, err := s.UnsecuredKubeletConfig()
|
cfg, err := s.UnsecuredKubeletConfig()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -498,11 +501,17 @@ func (s *KubeletServer) Run(kcfg *KubeletConfig) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if kcfg.CAdvisorInterface == nil {
|
if kcfg.CAdvisorInterface == nil {
|
||||||
ca, err := cadvisor.New(s.CAdvisorPort)
|
kcfg.CAdvisorInterface, err = cadvisor.New(s.CAdvisorPort)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if kcfg.ContainerManager == nil {
|
||||||
|
kcfg.ContainerManager, err = cm.NewContainerManager(kcfg.Mounter, kcfg.CAdvisorInterface)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
kcfg.CAdvisorInterface = ca
|
|
||||||
}
|
}
|
||||||
|
|
||||||
util.ReallyCrash = s.ReallyCrashForTesting
|
util.ReallyCrash = s.ReallyCrashForTesting
|
||||||
@ -670,7 +679,7 @@ func SimpleKubelet(client *client.Client,
|
|||||||
osInterface kubecontainer.OSInterface,
|
osInterface kubecontainer.OSInterface,
|
||||||
fileCheckFrequency, httpCheckFrequency, minimumGCAge, nodeStatusUpdateFrequency, syncFrequency time.Duration,
|
fileCheckFrequency, httpCheckFrequency, minimumGCAge, nodeStatusUpdateFrequency, syncFrequency time.Duration,
|
||||||
maxPods int,
|
maxPods int,
|
||||||
) *KubeletConfig {
|
containerManager cm.ContainerManager) *KubeletConfig {
|
||||||
imageGCPolicy := kubelet.ImageGCPolicy{
|
imageGCPolicy := kubelet.ImageGCPolicy{
|
||||||
HighThresholdPercent: 90,
|
HighThresholdPercent: 90,
|
||||||
LowThresholdPercent: 80,
|
LowThresholdPercent: 80,
|
||||||
@ -686,6 +695,7 @@ func SimpleKubelet(client *client.Client,
|
|||||||
CgroupRoot: "",
|
CgroupRoot: "",
|
||||||
Cloud: cloud,
|
Cloud: cloud,
|
||||||
ConfigFile: configFilePath,
|
ConfigFile: configFilePath,
|
||||||
|
ContainerManager: containerManager,
|
||||||
ContainerRuntime: "docker",
|
ContainerRuntime: "docker",
|
||||||
CPUCFSQuota: false,
|
CPUCFSQuota: false,
|
||||||
DiskSpacePolicy: diskSpacePolicy,
|
DiskSpacePolicy: diskSpacePolicy,
|
||||||
@ -724,8 +734,8 @@ func SimpleKubelet(client *client.Client,
|
|||||||
SyncFrequency: syncFrequency,
|
SyncFrequency: syncFrequency,
|
||||||
SystemContainer: "",
|
SystemContainer: "",
|
||||||
TLSOptions: tlsOptions,
|
TLSOptions: tlsOptions,
|
||||||
Writer: &io.StdWriter{},
|
|
||||||
VolumePlugins: volumePlugins,
|
VolumePlugins: volumePlugins,
|
||||||
|
Writer: &io.StdWriter{},
|
||||||
}
|
}
|
||||||
return &kcfg
|
return &kcfg
|
||||||
}
|
}
|
||||||
@ -864,6 +874,7 @@ type KubeletConfig struct {
|
|||||||
ClusterDomain string
|
ClusterDomain string
|
||||||
ConfigFile string
|
ConfigFile string
|
||||||
ConfigureCBR0 bool
|
ConfigureCBR0 bool
|
||||||
|
ContainerManager cm.ContainerManager
|
||||||
ContainerRuntime string
|
ContainerRuntime string
|
||||||
CPUCFSQuota bool
|
CPUCFSQuota bool
|
||||||
DiskSpacePolicy kubelet.DiskSpacePolicy
|
DiskSpacePolicy kubelet.DiskSpacePolicy
|
||||||
@ -1004,6 +1015,7 @@ func CreateAndInitKubelet(kc *KubeletConfig) (k KubeletBootstrap, pc *config.Pod
|
|||||||
daemonEndpoints,
|
daemonEndpoints,
|
||||||
kc.OOMAdjuster,
|
kc.OOMAdjuster,
|
||||||
kc.SerializeImagePulls,
|
kc.SerializeImagePulls,
|
||||||
|
kc.ContainerManager,
|
||||||
)
|
)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -27,6 +27,7 @@ import (
|
|||||||
client "k8s.io/kubernetes/pkg/client/unversioned"
|
client "k8s.io/kubernetes/pkg/client/unversioned"
|
||||||
"k8s.io/kubernetes/pkg/client/unversioned/clientcmd"
|
"k8s.io/kubernetes/pkg/client/unversioned/clientcmd"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
||||||
|
"k8s.io/kubernetes/pkg/kubelet/cm"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
||||||
"k8s.io/kubernetes/pkg/kubemark"
|
"k8s.io/kubernetes/pkg/kubemark"
|
||||||
proxyconfig "k8s.io/kubernetes/pkg/proxy/config"
|
proxyconfig "k8s.io/kubernetes/pkg/proxy/config"
|
||||||
@ -93,6 +94,7 @@ func main() {
|
|||||||
|
|
||||||
if config.Morph == "kubelet" {
|
if config.Morph == "kubelet" {
|
||||||
cadvisorInterface := new(cadvisor.Fake)
|
cadvisorInterface := new(cadvisor.Fake)
|
||||||
|
containerManager := cm.NewStubContainerManager()
|
||||||
|
|
||||||
fakeDockerClient := &dockertools.FakeDockerClient{}
|
fakeDockerClient := &dockertools.FakeDockerClient{}
|
||||||
fakeDockerClient.VersionInfo = docker.Env{"ApiVersion=1.18"}
|
fakeDockerClient.VersionInfo = docker.Env{"ApiVersion=1.18"}
|
||||||
@ -106,6 +108,7 @@ func main() {
|
|||||||
fakeDockerClient,
|
fakeDockerClient,
|
||||||
config.KubeletPort,
|
config.KubeletPort,
|
||||||
config.KubeletReadOnlyPort,
|
config.KubeletReadOnlyPort,
|
||||||
|
containerManager,
|
||||||
)
|
)
|
||||||
hollowKubelet.Run()
|
hollowKubelet.Run()
|
||||||
}
|
}
|
||||||
|
@ -36,6 +36,7 @@ import (
|
|||||||
client "k8s.io/kubernetes/pkg/client/unversioned"
|
client "k8s.io/kubernetes/pkg/client/unversioned"
|
||||||
"k8s.io/kubernetes/pkg/fields"
|
"k8s.io/kubernetes/pkg/fields"
|
||||||
"k8s.io/kubernetes/pkg/kubelet"
|
"k8s.io/kubernetes/pkg/kubelet"
|
||||||
|
"k8s.io/kubernetes/pkg/kubelet/cm"
|
||||||
kconfig "k8s.io/kubernetes/pkg/kubelet/config"
|
kconfig "k8s.io/kubernetes/pkg/kubelet/config"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
||||||
kubetypes "k8s.io/kubernetes/pkg/kubelet/types"
|
kubetypes "k8s.io/kubernetes/pkg/kubelet/types"
|
||||||
@ -151,7 +152,6 @@ func (s *KubeletExecutorServer) runKubelet(execUpdates <-chan kubetypes.PodUpdat
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return k, pc, err
|
return k, pc, err
|
||||||
}
|
}
|
||||||
|
|
||||||
klet := k.(*kubelet.Kubelet)
|
klet := k.(*kubelet.Kubelet)
|
||||||
|
|
||||||
s.kletLock.Lock()
|
s.kletLock.Lock()
|
||||||
@ -187,6 +187,11 @@ func (s *KubeletExecutorServer) runKubelet(execUpdates <-chan kubetypes.PodUpdat
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
kcfg.CAdvisorInterface = cAdvisorInterface
|
kcfg.CAdvisorInterface = cAdvisorInterface
|
||||||
|
kcfg.ContainerManager, err = cm.NewContainerManager(kcfg.Mounter, cAdvisorInterface)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
go func() {
|
go func() {
|
||||||
for ni := range nodeInfos {
|
for ni := range nodeInfos {
|
||||||
// TODO(sttts): implement with MachineAllocable mechanism when https://github.com/kubernetes/kubernetes/issues/13984 is finished
|
// TODO(sttts): implement with MachineAllocable mechanism when https://github.com/kubernetes/kubernetes/issues/13984 is finished
|
||||||
|
35
pkg/kubelet/cadvisor/util.go
Normal file
35
pkg/kubelet/cadvisor/util.go
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
/*
|
||||||
|
Copyright 2015 The Kubernetes Authors All rights reserved.
|
||||||
|
|
||||||
|
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 cadvisor
|
||||||
|
|
||||||
|
import (
|
||||||
|
cadvisorApi "github.com/google/cadvisor/info/v1"
|
||||||
|
"k8s.io/kubernetes/pkg/api"
|
||||||
|
"k8s.io/kubernetes/pkg/api/resource"
|
||||||
|
)
|
||||||
|
|
||||||
|
func CapacityFromMachineInfo(info *cadvisorApi.MachineInfo) api.ResourceList {
|
||||||
|
c := api.ResourceList{
|
||||||
|
api.ResourceCPU: *resource.NewMilliQuantity(
|
||||||
|
int64(info.NumCores*1000),
|
||||||
|
resource.DecimalSI),
|
||||||
|
api.ResourceMemory: *resource.NewQuantity(
|
||||||
|
info.MemoryCapacity,
|
||||||
|
resource.BinarySI),
|
||||||
|
}
|
||||||
|
return c
|
||||||
|
}
|
@ -14,20 +14,26 @@ See the License for the specific language governing permissions and
|
|||||||
limitations under the License.
|
limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package kubelet
|
package cm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"k8s.io/kubernetes/pkg/api"
|
"k8s.io/kubernetes/pkg/api"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Manages the containers running on a machine.
|
// Manages the containers running on a machine.
|
||||||
type containerManager interface {
|
type ContainerManager interface {
|
||||||
// Runs the container manager's housekeeping.
|
// Runs the container manager's housekeeping.
|
||||||
// - Ensures that the Docker daemon is in a container.
|
// - Ensures that the Docker daemon is in a container.
|
||||||
// - Creates the system container where all non-containerized processes run.
|
// - Creates the system container where all non-containerized processes run.
|
||||||
Start() error
|
Start(NodeConfig) error
|
||||||
|
|
||||||
// Returns resources allocated to system containers in the machine.
|
// Returns resources allocated to system containers in the machine.
|
||||||
// These containers include the system and Kubernetes services.
|
// These containers include the system and Kubernetes services.
|
||||||
SystemContainersLimit() api.ResourceList
|
SystemContainersLimit() api.ResourceList
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type NodeConfig struct {
|
||||||
|
DockerDaemonContainerName string
|
||||||
|
SystemContainerName string
|
||||||
|
KubeletContainerName string
|
||||||
|
}
|
@ -16,7 +16,7 @@ See the License for the specific language governing permissions and
|
|||||||
limitations under the License.
|
limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package kubelet
|
package cm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
@ -73,21 +73,15 @@ func newSystemContainer(containerName string) *systemContainer {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
type nodeConfig struct {
|
|
||||||
dockerDaemonContainerName string
|
|
||||||
systemContainerName string
|
|
||||||
kubeletContainerName string
|
|
||||||
}
|
|
||||||
|
|
||||||
type containerManagerImpl struct {
|
type containerManagerImpl struct {
|
||||||
cadvisorInterface cadvisor.Interface
|
cadvisorInterface cadvisor.Interface
|
||||||
mountUtil mount.Interface
|
mountUtil mount.Interface
|
||||||
nodeConfig
|
NodeConfig
|
||||||
// External containers being managed.
|
// External containers being managed.
|
||||||
systemContainers []*systemContainer
|
systemContainers []*systemContainer
|
||||||
}
|
}
|
||||||
|
|
||||||
var _ containerManager = &containerManagerImpl{}
|
var _ ContainerManager = &containerManagerImpl{}
|
||||||
|
|
||||||
// checks if the required cgroups subsystems are mounted.
|
// checks if the required cgroups subsystems are mounted.
|
||||||
// As of now, only 'cpu' and 'memory' are required.
|
// As of now, only 'cpu' and 'memory' are required.
|
||||||
@ -120,15 +114,11 @@ func validateSystemRequirements(mountUtil mount.Interface) error {
|
|||||||
// TODO(vmarmol): Add limits to the system containers.
|
// TODO(vmarmol): Add limits to the system containers.
|
||||||
// Takes the absolute name of the specified containers.
|
// Takes the absolute name of the specified containers.
|
||||||
// Empty container name disables use of the specified container.
|
// Empty container name disables use of the specified container.
|
||||||
func newContainerManager(mountUtil mount.Interface, cadvisorInterface cadvisor.Interface, dockerDaemonContainerName, systemContainerName, kubeletContainerName string) (containerManager, error) {
|
func NewContainerManager(mountUtil mount.Interface, cadvisorInterface cadvisor.Interface) (ContainerManager, error) {
|
||||||
return &containerManagerImpl{
|
return &containerManagerImpl{
|
||||||
cadvisorInterface: cadvisorInterface,
|
cadvisorInterface: cadvisorInterface,
|
||||||
mountUtil: mountUtil,
|
mountUtil: mountUtil,
|
||||||
nodeConfig: nodeConfig{
|
NodeConfig: NodeConfig{},
|
||||||
dockerDaemonContainerName: dockerDaemonContainerName,
|
|
||||||
systemContainerName: systemContainerName,
|
|
||||||
kubeletContainerName: kubeletContainerName,
|
|
||||||
},
|
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -197,26 +187,26 @@ func (cm *containerManagerImpl) setupNode() error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
systemContainers := []*systemContainer{}
|
systemContainers := []*systemContainer{}
|
||||||
if cm.dockerDaemonContainerName != "" {
|
if cm.DockerDaemonContainerName != "" {
|
||||||
cont := newSystemContainer(cm.dockerDaemonContainerName)
|
cont := newSystemContainer(cm.DockerDaemonContainerName)
|
||||||
|
|
||||||
info, err := cm.cadvisorInterface.MachineInfo()
|
info, err := cm.cadvisorInterface.MachineInfo()
|
||||||
var capacity = api.ResourceList{}
|
var capacity = api.ResourceList{}
|
||||||
if err != nil {
|
if err != nil {
|
||||||
} else {
|
} else {
|
||||||
capacity = CapacityFromMachineInfo(info)
|
capacity = cadvisor.CapacityFromMachineInfo(info)
|
||||||
}
|
}
|
||||||
memoryLimit := (int64(capacity.Memory().Value() * DockerMemoryLimitThresholdPercent / 100))
|
memoryLimit := (int64(capacity.Memory().Value() * DockerMemoryLimitThresholdPercent / 100))
|
||||||
if memoryLimit < MinDockerMemoryLimit {
|
if memoryLimit < MinDockerMemoryLimit {
|
||||||
glog.Warningf("Memory limit %d for container %s is too small, reset it to %d", memoryLimit, cm.dockerDaemonContainerName, MinDockerMemoryLimit)
|
glog.Warningf("Memory limit %d for container %s is too small, reset it to %d", memoryLimit, cm.DockerDaemonContainerName, MinDockerMemoryLimit)
|
||||||
memoryLimit = MinDockerMemoryLimit
|
memoryLimit = MinDockerMemoryLimit
|
||||||
}
|
}
|
||||||
|
|
||||||
glog.V(2).Infof("Configure resource-only container %s with memory limit: %d", cm.dockerDaemonContainerName, memoryLimit)
|
glog.V(2).Infof("Configure resource-only container %s with memory limit: %d", cm.DockerDaemonContainerName, memoryLimit)
|
||||||
|
|
||||||
dockerContainer := &fs.Manager{
|
dockerContainer := &fs.Manager{
|
||||||
Cgroups: &configs.Cgroup{
|
Cgroups: &configs.Cgroup{
|
||||||
Name: cm.dockerDaemonContainerName,
|
Name: cm.DockerDaemonContainerName,
|
||||||
Memory: memoryLimit,
|
Memory: memoryLimit,
|
||||||
MemorySwap: -1,
|
MemorySwap: -1,
|
||||||
AllowAllDevices: true,
|
AllowAllDevices: true,
|
||||||
@ -228,8 +218,8 @@ func (cm *containerManagerImpl) setupNode() error {
|
|||||||
systemContainers = append(systemContainers, cont)
|
systemContainers = append(systemContainers, cont)
|
||||||
}
|
}
|
||||||
|
|
||||||
if cm.systemContainerName != "" {
|
if cm.SystemContainerName != "" {
|
||||||
if cm.systemContainerName == "/" {
|
if cm.SystemContainerName == "/" {
|
||||||
return fmt.Errorf("system container cannot be root (\"/\")")
|
return fmt.Errorf("system container cannot be root (\"/\")")
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -238,23 +228,25 @@ func (cm *containerManagerImpl) setupNode() error {
|
|||||||
Name: "/",
|
Name: "/",
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
manager := createManager(cm.systemContainerName)
|
manager := createManager(cm.SystemContainerName)
|
||||||
|
|
||||||
err := ensureSystemContainer(rootContainer, manager)
|
err := ensureSystemContainer(rootContainer, manager)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
systemContainers = append(systemContainers, newSystemContainer(cm.systemContainerName))
|
systemContainers = append(systemContainers, newSystemContainer(cm.SystemContainerName))
|
||||||
}
|
}
|
||||||
|
|
||||||
if cm.kubeletContainerName != "" {
|
if cm.KubeletContainerName != "" {
|
||||||
systemContainers = append(systemContainers, newSystemContainer(cm.kubeletContainerName))
|
systemContainers = append(systemContainers, newSystemContainer(cm.KubeletContainerName))
|
||||||
}
|
}
|
||||||
cm.systemContainers = systemContainers
|
cm.systemContainers = systemContainers
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cm *containerManagerImpl) Start() error {
|
func (cm *containerManagerImpl) Start(nodeConfig NodeConfig) error {
|
||||||
|
cm.NodeConfig = nodeConfig
|
||||||
|
|
||||||
// Setup the node
|
// Setup the node
|
||||||
if err := cm.setupNode(); err != nil {
|
if err := cm.setupNode(); err != nil {
|
||||||
return err
|
return err
|
@ -16,7 +16,7 @@ See the License for the specific language governing permissions and
|
|||||||
limitations under the License.
|
limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package kubelet
|
package cm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
39
pkg/kubelet/cm/container_manager_stub.go
Normal file
39
pkg/kubelet/cm/container_manager_stub.go
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
/*
|
||||||
|
Copyright 2015 The Kubernetes Authors All rights reserved.
|
||||||
|
|
||||||
|
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 cm
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/golang/glog"
|
||||||
|
"k8s.io/kubernetes/pkg/api"
|
||||||
|
)
|
||||||
|
|
||||||
|
type containerManagerStub struct{}
|
||||||
|
|
||||||
|
var _ ContainerManager = &containerManagerStub{}
|
||||||
|
|
||||||
|
func (cm *containerManagerStub) Start(_ NodeConfig) error {
|
||||||
|
glog.V(2).Infof("Starting stub container manager")
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (cm *containerManagerStub) SystemContainersLimit() api.ResourceList {
|
||||||
|
return api.ResourceList{}
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewStubContainerManager() ContainerManager {
|
||||||
|
return &containerManagerStub{}
|
||||||
|
}
|
@ -16,7 +16,7 @@ See the License for the specific language governing permissions and
|
|||||||
limitations under the License.
|
limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package kubelet
|
package cm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
@ -29,9 +29,9 @@ import (
|
|||||||
type unsupportedContainerManager struct {
|
type unsupportedContainerManager struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
var _ containerManager = &unsupportedContainerManager{}
|
var _ ContainerManager = &unsupportedContainerManager{}
|
||||||
|
|
||||||
func (unsupportedContainerManager) Start() error {
|
func (unsupportedContainerManager) Start(_ NodeConfig) error {
|
||||||
return fmt.Errorf("Container Manager is unsupported in this build")
|
return fmt.Errorf("Container Manager is unsupported in this build")
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -39,6 +39,6 @@ func (unsupportedContainerManager) SystemContainersLimit() api.ResourceList {
|
|||||||
return api.ResourceList{}
|
return api.ResourceList{}
|
||||||
}
|
}
|
||||||
|
|
||||||
func newContainerManager(mounter mount.Interface, cadvisorInterface cadvisor.Interface, dockerDaemonContainer, systemContainer, kubeletContainer string) (containerManager, error) {
|
func NewContainerManager(mounter mount.Interface, cadvisorInterface cadvisor.Interface) (ContainerManager, error) {
|
||||||
return &unsupportedContainerManager{}, nil
|
return &unsupportedContainerManager{}, nil
|
||||||
}
|
}
|
@ -16,7 +16,7 @@ See the License for the specific language governing permissions and
|
|||||||
limitations under the License.
|
limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package kubelet
|
package cm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
@ -48,6 +48,7 @@ import (
|
|||||||
"k8s.io/kubernetes/pkg/fieldpath"
|
"k8s.io/kubernetes/pkg/fieldpath"
|
||||||
"k8s.io/kubernetes/pkg/fields"
|
"k8s.io/kubernetes/pkg/fields"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
||||||
|
"k8s.io/kubernetes/pkg/kubelet/cm"
|
||||||
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/envvars"
|
"k8s.io/kubernetes/pkg/kubelet/envvars"
|
||||||
@ -195,7 +196,9 @@ func NewMainKubelet(
|
|||||||
daemonEndpoints *api.NodeDaemonEndpoints,
|
daemonEndpoints *api.NodeDaemonEndpoints,
|
||||||
oomAdjuster *oom.OOMAdjuster,
|
oomAdjuster *oom.OOMAdjuster,
|
||||||
serializeImagePulls bool,
|
serializeImagePulls bool,
|
||||||
|
containerManager cm.ContainerManager,
|
||||||
) (*Kubelet, error) {
|
) (*Kubelet, error) {
|
||||||
|
|
||||||
if rootDirectory == "" {
|
if rootDirectory == "" {
|
||||||
return nil, fmt.Errorf("invalid root directory %q", rootDirectory)
|
return nil, fmt.Errorf("invalid root directory %q", rootDirectory)
|
||||||
}
|
}
|
||||||
@ -302,6 +305,7 @@ func NewMainKubelet(
|
|||||||
resolverConfig: resolverConfig,
|
resolverConfig: resolverConfig,
|
||||||
cpuCFSQuota: cpuCFSQuota,
|
cpuCFSQuota: cpuCFSQuota,
|
||||||
daemonEndpoints: daemonEndpoints,
|
daemonEndpoints: daemonEndpoints,
|
||||||
|
containerManager: containerManager,
|
||||||
}
|
}
|
||||||
|
|
||||||
if plug, err := network.InitNetworkPlugin(networkPlugins, networkPluginName, &networkHost{klet}); err != nil {
|
if plug, err := network.InitNetworkPlugin(networkPlugins, networkPluginName, &networkHost{klet}); err != nil {
|
||||||
@ -390,12 +394,11 @@ func NewMainKubelet(
|
|||||||
|
|
||||||
// Setup container manager, can fail if the devices hierarchy is not mounted
|
// Setup container manager, can fail if the devices hierarchy is not mounted
|
||||||
// (it is required by Docker however).
|
// (it is required by Docker however).
|
||||||
containerManager, err := newContainerManager(mounter, cadvisorInterface, dockerDaemonContainer, systemContainer, resourceContainer)
|
klet.nodeConfig = cm.NodeConfig{
|
||||||
if err != nil {
|
DockerDaemonContainerName: dockerDaemonContainer,
|
||||||
return nil, fmt.Errorf("failed to create the Container Manager: %v", err)
|
SystemContainerName: systemContainer,
|
||||||
|
KubeletContainerName: resourceContainer,
|
||||||
}
|
}
|
||||||
klet.containerManager = containerManager
|
|
||||||
|
|
||||||
klet.runtimeState.setRuntimeSync(time.Now())
|
klet.runtimeState.setRuntimeSync(time.Now())
|
||||||
|
|
||||||
klet.runner = klet.containerRuntime
|
klet.runner = klet.containerRuntime
|
||||||
@ -575,7 +578,8 @@ type Kubelet struct {
|
|||||||
writer kubeio.Writer
|
writer kubeio.Writer
|
||||||
|
|
||||||
// Manager of non-Runtime containers.
|
// Manager of non-Runtime containers.
|
||||||
containerManager containerManager
|
containerManager cm.ContainerManager
|
||||||
|
nodeConfig cm.NodeConfig
|
||||||
|
|
||||||
// Whether or not kubelet should take responsibility for keeping cbr0 in
|
// Whether or not kubelet should take responsibility for keeping cbr0 in
|
||||||
// the correct state.
|
// the correct state.
|
||||||
@ -813,7 +817,7 @@ func (kl *Kubelet) preRun() error {
|
|||||||
return fmt.Errorf("Failed to start CAdvisor %v", err)
|
return fmt.Errorf("Failed to start CAdvisor %v", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := kl.containerManager.Start(); err != nil {
|
if err := kl.containerManager.Start(kl.nodeConfig); err != nil {
|
||||||
return fmt.Errorf("Failed to start ContainerManager %v", err)
|
return fmt.Errorf("Failed to start ContainerManager %v", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1971,7 +1975,7 @@ func (kl *Kubelet) hasInsufficientfFreeResources(pods []*api.Pod) (bool, bool) {
|
|||||||
// TODO: Should we admit the pod when machine info is unavailable?
|
// TODO: Should we admit the pod when machine info is unavailable?
|
||||||
return false, false
|
return false, false
|
||||||
}
|
}
|
||||||
capacity := CapacityFromMachineInfo(info)
|
capacity := cadvisor.CapacityFromMachineInfo(info)
|
||||||
_, notFittingCPU, notFittingMemory := predicates.CheckPodsExceedingFreeResources(pods, capacity)
|
_, notFittingCPU, notFittingMemory := predicates.CheckPodsExceedingFreeResources(pods, capacity)
|
||||||
return len(notFittingCPU) > 0, len(notFittingMemory) > 0
|
return len(notFittingCPU) > 0, len(notFittingMemory) > 0
|
||||||
}
|
}
|
||||||
@ -2506,7 +2510,7 @@ func (kl *Kubelet) setNodeStatus(node *api.Node) error {
|
|||||||
} else {
|
} else {
|
||||||
node.Status.NodeInfo.MachineID = info.MachineID
|
node.Status.NodeInfo.MachineID = info.MachineID
|
||||||
node.Status.NodeInfo.SystemUUID = info.SystemUUID
|
node.Status.NodeInfo.SystemUUID = info.SystemUUID
|
||||||
node.Status.Capacity = CapacityFromMachineInfo(info)
|
node.Status.Capacity = cadvisor.CapacityFromMachineInfo(info)
|
||||||
node.Status.Capacity[api.ResourcePods] = *resource.NewQuantity(
|
node.Status.Capacity[api.ResourcePods] = *resource.NewQuantity(
|
||||||
int64(kl.pods), resource.DecimalSI)
|
int64(kl.pods), resource.DecimalSI)
|
||||||
if node.Status.NodeInfo.BootID != "" &&
|
if node.Status.NodeInfo.BootID != "" &&
|
||||||
|
@ -42,6 +42,7 @@ import (
|
|||||||
"k8s.io/kubernetes/pkg/client/record"
|
"k8s.io/kubernetes/pkg/client/record"
|
||||||
"k8s.io/kubernetes/pkg/client/unversioned/testclient"
|
"k8s.io/kubernetes/pkg/client/unversioned/testclient"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
||||||
|
"k8s.io/kubernetes/pkg/kubelet/cm"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/container"
|
"k8s.io/kubernetes/pkg/kubelet/container"
|
||||||
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/network"
|
"k8s.io/kubernetes/pkg/kubelet/network"
|
||||||
|
@ -26,6 +26,7 @@ import (
|
|||||||
"k8s.io/kubernetes/pkg/api"
|
"k8s.io/kubernetes/pkg/api"
|
||||||
"k8s.io/kubernetes/pkg/client/record"
|
"k8s.io/kubernetes/pkg/client/record"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
||||||
|
"k8s.io/kubernetes/pkg/kubelet/cm"
|
||||||
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/network"
|
"k8s.io/kubernetes/pkg/kubelet/network"
|
||||||
kubepod "k8s.io/kubernetes/pkg/kubelet/pod"
|
kubepod "k8s.io/kubernetes/pkg/kubelet/pod"
|
||||||
@ -56,7 +57,7 @@ func TestRunOnce(t *testing.T) {
|
|||||||
diskSpaceManager: diskSpaceManager,
|
diskSpaceManager: diskSpaceManager,
|
||||||
containerRuntime: fakeRuntime,
|
containerRuntime: fakeRuntime,
|
||||||
}
|
}
|
||||||
kb.containerManager, _ = newContainerManager(fakeContainerMgrMountInt(), cadvisor, "", "", "")
|
kb.containerManager = cm.NewStubContainerManager()
|
||||||
|
|
||||||
kb.networkPlugin, _ = network.InitNetworkPlugin([]network.NetworkPlugin{}, "", network.NewFakeHost(nil))
|
kb.networkPlugin, _ = network.InitNetworkPlugin([]network.NetworkPlugin{}, "", network.NewFakeHost(nil))
|
||||||
if err := kb.setupDataDirs(); err != nil {
|
if err := kb.setupDataDirs(); err != nil {
|
||||||
|
@ -19,26 +19,12 @@ package kubelet
|
|||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
cadvisorapi "github.com/google/cadvisor/info/v1"
|
|
||||||
"k8s.io/kubernetes/pkg/api"
|
"k8s.io/kubernetes/pkg/api"
|
||||||
"k8s.io/kubernetes/pkg/api/resource"
|
|
||||||
"k8s.io/kubernetes/pkg/capabilities"
|
"k8s.io/kubernetes/pkg/capabilities"
|
||||||
kubetypes "k8s.io/kubernetes/pkg/kubelet/types"
|
kubetypes "k8s.io/kubernetes/pkg/kubelet/types"
|
||||||
"k8s.io/kubernetes/pkg/securitycontext"
|
"k8s.io/kubernetes/pkg/securitycontext"
|
||||||
)
|
)
|
||||||
|
|
||||||
func CapacityFromMachineInfo(info *cadvisorapi.MachineInfo) api.ResourceList {
|
|
||||||
c := api.ResourceList{
|
|
||||||
api.ResourceCPU: *resource.NewMilliQuantity(
|
|
||||||
int64(info.NumCores*1000),
|
|
||||||
resource.DecimalSI),
|
|
||||||
api.ResourceMemory: *resource.NewQuantity(
|
|
||||||
info.MemoryCapacity,
|
|
||||||
resource.BinarySI),
|
|
||||||
}
|
|
||||||
return c
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check whether we have the capabilities to run the specified pod.
|
// Check whether we have the capabilities to run the specified pod.
|
||||||
func canRunPod(pod *api.Pod) error {
|
func canRunPod(pod *api.Pod) error {
|
||||||
if pod.Spec.SecurityContext != nil && pod.Spec.SecurityContext.HostNetwork {
|
if pod.Spec.SecurityContext != nil && pod.Spec.SecurityContext.HostNetwork {
|
||||||
|
@ -23,6 +23,7 @@ import (
|
|||||||
"k8s.io/kubernetes/pkg/api"
|
"k8s.io/kubernetes/pkg/api"
|
||||||
client "k8s.io/kubernetes/pkg/client/unversioned"
|
client "k8s.io/kubernetes/pkg/client/unversioned"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
"k8s.io/kubernetes/pkg/kubelet/cadvisor"
|
||||||
|
"k8s.io/kubernetes/pkg/kubelet/cm"
|
||||||
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
kubecontainer "k8s.io/kubernetes/pkg/kubelet/container"
|
||||||
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
"k8s.io/kubernetes/pkg/kubelet/dockertools"
|
||||||
"k8s.io/kubernetes/pkg/volume/empty_dir"
|
"k8s.io/kubernetes/pkg/volume/empty_dir"
|
||||||
@ -41,6 +42,7 @@ func NewHollowKubelet(
|
|||||||
cadvisorInterface cadvisor.Interface,
|
cadvisorInterface cadvisor.Interface,
|
||||||
dockerClient dockertools.DockerInterface,
|
dockerClient dockertools.DockerInterface,
|
||||||
kubeletPort, kubeletReadOnlyPort int,
|
kubeletPort, kubeletReadOnlyPort int,
|
||||||
|
containerManager cm.ContainerManager,
|
||||||
) *HollowKubelet {
|
) *HollowKubelet {
|
||||||
testRootDir := integration.MakeTempDirOrDie("hollow-kubelet.", "")
|
testRootDir := integration.MakeTempDirOrDie("hollow-kubelet.", "")
|
||||||
manifestFilePath := integration.MakeTempDirOrDie("manifest", testRootDir)
|
manifestFilePath := integration.MakeTempDirOrDie("manifest", testRootDir)
|
||||||
@ -69,6 +71,7 @@ func NewHollowKubelet(
|
|||||||
10*time.Second, /* NodeStatusUpdateFrequency */
|
10*time.Second, /* NodeStatusUpdateFrequency */
|
||||||
10*time.Second, /* SyncFrequency */
|
10*time.Second, /* SyncFrequency */
|
||||||
40, /* MaxPods */
|
40, /* MaxPods */
|
||||||
|
containerManager,
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user