Add support for correctly displaying node and pod IP address + fix make clean
This commit is contained in:
2
Makefile
2
Makefile
@@ -54,7 +54,7 @@ docker:
|
|||||||
@echo "Docker Build..."
|
@echo "Docker Build..."
|
||||||
$Q docker build -t $(DOCKER_IMAGE) .
|
$Q docker build -t $(DOCKER_IMAGE) .
|
||||||
|
|
||||||
clean: clean-build
|
clean:
|
||||||
@echo "Clean..."
|
@echo "Clean..."
|
||||||
$Q rm -rf bin
|
$Q rm -rf bin
|
||||||
|
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ import (
|
|||||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||||
|
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/cache"
|
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/cache"
|
||||||
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/proxy"
|
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/proxy"
|
||||||
proxymocks "github.com/virtual-kubelet/virtual-kubelet/providers/vic/proxy/mocks"
|
proxymocks "github.com/virtual-kubelet/virtual-kubelet/providers/vic/proxy/mocks"
|
||||||
@@ -30,7 +31,13 @@ const (
|
|||||||
podName = "busybox-sleep"
|
podName = "busybox-sleep"
|
||||||
podHandle = "fakehandle"
|
podHandle = "fakehandle"
|
||||||
|
|
||||||
fakeEP = "fake-endpoint"
|
fakeEP = "fake-endpoint"
|
||||||
|
stateRunning = "Running"
|
||||||
|
stateStarting = "Starting"
|
||||||
|
stateStopping = "Stopping"
|
||||||
|
stateStopped = "Stopped"
|
||||||
|
stateRemoving = "Removing"
|
||||||
|
stateRemoved = "Removed"
|
||||||
)
|
)
|
||||||
|
|
||||||
func createMocks(t *testing.T) (*proxymocks.ImageStore, *proxymocks.IsolationProxy, cache.PodCache, trace.Operation) {
|
func createMocks(t *testing.T) (*proxymocks.ImageStore, *proxymocks.IsolationProxy, cache.PodCache, trace.Operation) {
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import (
|
|||||||
"fmt"
|
"fmt"
|
||||||
"strings"
|
"strings"
|
||||||
"sync"
|
"sync"
|
||||||
|
"time"
|
||||||
|
|
||||||
"github.com/kr/pretty"
|
"github.com/kr/pretty"
|
||||||
|
|
||||||
@@ -17,6 +18,7 @@ import (
|
|||||||
"github.com/vmware/vic/pkg/trace"
|
"github.com/vmware/vic/pkg/trace"
|
||||||
|
|
||||||
"k8s.io/api/core/v1"
|
"k8s.io/api/core/v1"
|
||||||
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||||
)
|
)
|
||||||
|
|
||||||
type PodCreator interface {
|
type PodCreator interface {
|
||||||
@@ -143,6 +145,8 @@ func (v *VicPodCreator) CreatePod(op trace.Operation, pod *v1.Pod, start bool) e
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
now := metav1.NewTime(time.Now())
|
||||||
|
vp.Pod.Status.StartTime = &now
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
|
|||||||
151
providers/vic/operations/pod_status.go
Normal file
151
providers/vic/operations/pod_status.go
Normal file
@@ -0,0 +1,151 @@
|
|||||||
|
package operations
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"net"
|
||||||
|
|
||||||
|
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/proxy"
|
||||||
|
|
||||||
|
"github.com/vmware/vic/lib/apiservers/portlayer/client"
|
||||||
|
"github.com/vmware/vic/pkg/trace"
|
||||||
|
|
||||||
|
"k8s.io/api/core/v1"
|
||||||
|
)
|
||||||
|
|
||||||
|
type PodStatus interface {
|
||||||
|
GetStatus(op trace.Operation, namespace string, name string, hostAddress string) (*v1.PodStatus, error)
|
||||||
|
}
|
||||||
|
|
||||||
|
type VicPodStatus struct {
|
||||||
|
client *client.PortLayer
|
||||||
|
isolationProxy proxy.IsolationProxy
|
||||||
|
}
|
||||||
|
|
||||||
|
type VicPodStatusError string
|
||||||
|
|
||||||
|
func (e VicPodStatusError) Error() string { return string(e) }
|
||||||
|
|
||||||
|
const (
|
||||||
|
PodStatusPortlayerClientError = VicPodStatusError("PodStatus called with an invalid portlayer client")
|
||||||
|
PodStatusIsolationProxyError = VicPodStatusError("PodStatus called with an invalid isolation proxy")
|
||||||
|
PodStatusInvalidPodIDError = VicPodStatusError("PodStatus called with invalid PodID")
|
||||||
|
PodStatusInvalidPodNameError = VicPodStatusError("PodStatus called with invalid PodName")
|
||||||
|
)
|
||||||
|
|
||||||
|
func NewPodStatus(client *client.PortLayer, isolationProxy proxy.IsolationProxy) (PodStatus, error) {
|
||||||
|
if client == nil {
|
||||||
|
return nil, PodStatusPortlayerClientError
|
||||||
|
} else if isolationProxy == nil {
|
||||||
|
return nil, PodStatusIsolationProxyError
|
||||||
|
}
|
||||||
|
|
||||||
|
return &VicPodStatus{
|
||||||
|
client: client,
|
||||||
|
isolationProxy: isolationProxy,
|
||||||
|
}, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// Gets pod status does not delete it
|
||||||
|
//
|
||||||
|
// arguments:
|
||||||
|
// op operation trace logger
|
||||||
|
// id pod id
|
||||||
|
// name pod name
|
||||||
|
// returns:
|
||||||
|
// error
|
||||||
|
func (v *VicPodStatus) GetStatus(op trace.Operation, id, name string, hostAddress string) (*v1.PodStatus, error) {
|
||||||
|
defer trace.End(trace.Begin(fmt.Sprintf("id(%s), name(%s)", id, name), op))
|
||||||
|
|
||||||
|
return v.getStatus(op, id, name, hostAddress)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (v *VicPodStatus) getStatus(op trace.Operation, id, name string, hostAddress string) (*v1.PodStatus, error) {
|
||||||
|
defer trace.End(trace.Begin(fmt.Sprintf("id(%s), name(%s)", id, name), op))
|
||||||
|
// Start out with unknown
|
||||||
|
phase := v1.PodUnknown
|
||||||
|
podReady := v1.ConditionUnknown
|
||||||
|
podInitialized := v1.ConditionUnknown
|
||||||
|
podScheduled := v1.ConditionUnknown
|
||||||
|
|
||||||
|
// Get current state
|
||||||
|
state, err := v.isolationProxy.State(op, id, name)
|
||||||
|
if err == nil {
|
||||||
|
podScheduled = v1.ConditionTrue
|
||||||
|
switch state {
|
||||||
|
case "Starting":
|
||||||
|
// if we are starting let the user know they must use the force
|
||||||
|
phase = v1.PodPending
|
||||||
|
podInitialized = v1.ConditionFalse
|
||||||
|
podReady = v1.ConditionFalse
|
||||||
|
case "Running":
|
||||||
|
phase = v1.PodRunning
|
||||||
|
podInitialized = v1.ConditionTrue
|
||||||
|
podReady = v1.ConditionTrue
|
||||||
|
case "Stopping":
|
||||||
|
phase = v1.PodRunning
|
||||||
|
podReady = v1.ConditionFalse
|
||||||
|
podInitialized = v1.ConditionTrue
|
||||||
|
case "Stopped":
|
||||||
|
phase = v1.PodSucceeded
|
||||||
|
podReady = v1.ConditionFalse
|
||||||
|
podInitialized = v1.ConditionTrue
|
||||||
|
case "Removing":
|
||||||
|
phase = v1.PodSucceeded
|
||||||
|
podReady = v1.ConditionFalse
|
||||||
|
podInitialized = v1.ConditionTrue
|
||||||
|
case "Removed":
|
||||||
|
phase = v1.PodSucceeded
|
||||||
|
podReady = v1.ConditionFalse
|
||||||
|
podInitialized = v1.ConditionTrue
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
status := &v1.PodStatus{
|
||||||
|
Phase: phase,
|
||||||
|
Conditions: []v1.PodCondition{
|
||||||
|
{
|
||||||
|
Type: v1.PodInitialized,
|
||||||
|
Status: podInitialized,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
Type: v1.PodReady,
|
||||||
|
Status: podReady,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
Type: v1.PodScheduled,
|
||||||
|
Status: podScheduled,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
addresses, err := v.getIPAddresses(op, id, name)
|
||||||
|
if err == nil && len(addresses) > 0 {
|
||||||
|
status.HostIP = hostAddress
|
||||||
|
status.PodIP = addresses[0]
|
||||||
|
} else {
|
||||||
|
status.HostIP = "0.0.0.0"
|
||||||
|
status.PodIP = "0.0.0.0"
|
||||||
|
}
|
||||||
|
|
||||||
|
return status, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (v *VicPodStatus) getIPAddresses(op trace.Operation, id, name string) ([]string, error) {
|
||||||
|
defer trace.End(trace.Begin(id, op))
|
||||||
|
|
||||||
|
apAddresses, err := v.isolationProxy.EpAddresses(op, id, name)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
IPAddresses := make([]string, 0)
|
||||||
|
for _, epAddr := range apAddresses {
|
||||||
|
if epAddr != "" {
|
||||||
|
ip, _, err := net.ParseCIDR(epAddr)
|
||||||
|
if err == nil {
|
||||||
|
IPAddresses = append(IPAddresses, ip.String())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return IPAddresses, err
|
||||||
|
}
|
||||||
225
providers/vic/operations/pod_status_test.go
Normal file
225
providers/vic/operations/pod_status_test.go
Normal file
@@ -0,0 +1,225 @@
|
|||||||
|
package operations
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
|
|
||||||
|
"github.com/vmware/vic/lib/apiservers/portlayer/client"
|
||||||
|
"k8s.io/api/core/v1"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestNewPodStatus(t *testing.T) {
|
||||||
|
_, ip, _, _ := createMocks(t)
|
||||||
|
client := client.Default
|
||||||
|
|
||||||
|
// Positive Cases
|
||||||
|
s, err := NewPodStatus(client, ip)
|
||||||
|
assert.NotNil(t, s, "Expected non-nil creating a pod Status but received nil")
|
||||||
|
|
||||||
|
// Negative Cases
|
||||||
|
s, err = NewPodStatus(nil, ip)
|
||||||
|
assert.Nil(t, s, "Expected nil")
|
||||||
|
assert.Equal(t, err, PodStatusPortlayerClientError)
|
||||||
|
|
||||||
|
s, err = NewPodStatus(client, nil)
|
||||||
|
assert.Nil(t, s, "Expected nil")
|
||||||
|
assert.Equal(t, err, PodStatusIsolationProxyError)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestStatusPodStarting(t *testing.T) {
|
||||||
|
client := client.Default
|
||||||
|
_, ip, _, op := createMocks(t)
|
||||||
|
|
||||||
|
s, err := NewPodStatus(client, ip)
|
||||||
|
assert.NotNil(t, s, "Expected non-nil creating a pod Status but received nil")
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
|
||||||
|
HostAddress := "1.2.3.4"
|
||||||
|
EndpointAddresses := []string{
|
||||||
|
"5.6.7.8/24",
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set up the mocks for this test
|
||||||
|
ip.On("State", op, podID, podName).Return(stateStarting, nil)
|
||||||
|
ip.On("EpAddresses", op, podID, podName).Return(EndpointAddresses, nil)
|
||||||
|
|
||||||
|
// Positive case
|
||||||
|
status, err := s.GetStatus(op, podID, podName, HostAddress)
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
assert.Equal(t, status.Phase, v1.PodPending, "Expected Phase Pending")
|
||||||
|
verifyConditions(t, status.Conditions, v1.ConditionTrue, v1.ConditionFalse, v1.ConditionFalse)
|
||||||
|
assert.Equal(t, status.HostIP, "1.2.3.4", "Expected Host IP Address")
|
||||||
|
assert.Equal(t, status.PodIP, "5.6.7.8", "Expected Pod IP Address")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestStatusPodRunning(t *testing.T) {
|
||||||
|
client := client.Default
|
||||||
|
_, ip, _, op := createMocks(t)
|
||||||
|
|
||||||
|
s, err := NewPodStatus(client, ip)
|
||||||
|
assert.NotNil(t, s, "Expected non-nil creating a pod Status but received nil")
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
|
||||||
|
HostAddress := "1.2.3.4"
|
||||||
|
EndpointAddresses := []string{
|
||||||
|
"5.6.7.8/24",
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set up the mocks for this test
|
||||||
|
ip.On("State", op, podID, podName).Return(stateRunning, nil)
|
||||||
|
ip.On("EpAddresses", op, podID, podName).Return(EndpointAddresses, nil)
|
||||||
|
|
||||||
|
// Pod Running case
|
||||||
|
status, err := s.GetStatus(op, podID, podName, HostAddress)
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
assert.Equal(t, status.Phase, v1.PodRunning, "Expected Phase PodRunning")
|
||||||
|
verifyConditions(t, status.Conditions, v1.ConditionTrue, v1.ConditionTrue, v1.ConditionTrue)
|
||||||
|
assert.Equal(t, status.HostIP, "1.2.3.4", "Expected Host IP Address")
|
||||||
|
assert.Equal(t, status.PodIP, "5.6.7.8", "Expected Pod IP Address")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestStatusPodStopping(t *testing.T) {
|
||||||
|
client := client.Default
|
||||||
|
_, ip, _, op := createMocks(t)
|
||||||
|
|
||||||
|
s, err := NewPodStatus(client, ip)
|
||||||
|
assert.NotNil(t, s, "Expected non-nil creating a pod Status but received nil")
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
|
||||||
|
HostAddress := "1.2.3.4"
|
||||||
|
EndpointAddresses := []string{
|
||||||
|
"5.6.7.8/24",
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set up the mocks for this test
|
||||||
|
ip.On("State", op, podID, podName).Return(stateStopping, nil)
|
||||||
|
ip.On("EpAddresses", op, podID, podName).Return(EndpointAddresses, nil)
|
||||||
|
|
||||||
|
// Pod error case
|
||||||
|
status, err := s.GetStatus(op, podID, podName, HostAddress)
|
||||||
|
|
||||||
|
assert.Equal(t, status.Phase, v1.PodRunning, "Expected Phase PodFailed")
|
||||||
|
verifyConditions(t, status.Conditions, v1.ConditionTrue, v1.ConditionTrue, v1.ConditionFalse)
|
||||||
|
assert.Equal(t, status.HostIP, "1.2.3.4", "Expected Host IP Address")
|
||||||
|
assert.Equal(t, status.PodIP, "5.6.7.8", "Expected Pod IP Address")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestStatusPodStopped(t *testing.T) {
|
||||||
|
client := client.Default
|
||||||
|
_, ip, _, op := createMocks(t)
|
||||||
|
|
||||||
|
s, err := NewPodStatus(client, ip)
|
||||||
|
assert.NotNil(t, s, "Expected non-nil creating a pod Status but received nil")
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
|
||||||
|
HostAddress := "1.2.3.4"
|
||||||
|
EndpointAddresses := []string{
|
||||||
|
"5.6.7.8/24",
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set up the mocks for this test
|
||||||
|
ip.On("State", op, podID, podName).Return(stateStopped, nil)
|
||||||
|
ip.On("EpAddresses", op, podID, podName).Return(EndpointAddresses, nil)
|
||||||
|
|
||||||
|
// Pod error case
|
||||||
|
status, err := s.GetStatus(op, podID, podName, HostAddress)
|
||||||
|
|
||||||
|
assert.Equal(t, status.Phase, v1.PodSucceeded, "Expected Phase PodFailed")
|
||||||
|
verifyConditions(t, status.Conditions, v1.ConditionTrue, v1.ConditionTrue, v1.ConditionFalse)
|
||||||
|
assert.Equal(t, status.HostIP, "1.2.3.4", "Expected Host IP Address")
|
||||||
|
assert.Equal(t, status.PodIP, "5.6.7.8", "Expected Pod IP Address")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestStatusPodRemoving(t *testing.T) {
|
||||||
|
client := client.Default
|
||||||
|
_, ip, _, op := createMocks(t)
|
||||||
|
|
||||||
|
s, err := NewPodStatus(client, ip)
|
||||||
|
assert.NotNil(t, s, "Expected non-nil creating a pod Status but received nil")
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
|
||||||
|
HostAddress := "1.2.3.4"
|
||||||
|
EndpointAddresses := []string{
|
||||||
|
"5.6.7.8/24",
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set up the mocks for this test
|
||||||
|
ip.On("State", op, podID, podName).Return(stateRemoving, nil)
|
||||||
|
ip.On("EpAddresses", op, podID, podName).Return(EndpointAddresses, nil)
|
||||||
|
|
||||||
|
// Pod error case
|
||||||
|
status, err := s.GetStatus(op, podID, podName, HostAddress)
|
||||||
|
|
||||||
|
assert.Equal(t, status.Phase, v1.PodSucceeded, "Expected Phase PodFailed")
|
||||||
|
verifyConditions(t, status.Conditions, v1.ConditionTrue, v1.ConditionTrue, v1.ConditionFalse)
|
||||||
|
assert.Equal(t, status.HostIP, "1.2.3.4", "Expected Host IP Address")
|
||||||
|
assert.Equal(t, status.PodIP, "5.6.7.8", "Expected Pod IP Address")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestStatusPodRemoved(t *testing.T) {
|
||||||
|
client := client.Default
|
||||||
|
_, ip, _, op := createMocks(t)
|
||||||
|
|
||||||
|
s, err := NewPodStatus(client, ip)
|
||||||
|
assert.NotNil(t, s, "Expected non-nil creating a pod Status but received nil")
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
|
||||||
|
HostAddress := "1.2.3.4"
|
||||||
|
EndpointAddresses := []string{
|
||||||
|
"5.6.7.8/24",
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set up the mocks for this test
|
||||||
|
ip.On("State", op, podID, podName).Return(stateRemoved, nil)
|
||||||
|
ip.On("EpAddresses", op, podID, podName).Return(EndpointAddresses, nil)
|
||||||
|
|
||||||
|
// Pod error case
|
||||||
|
status, err := s.GetStatus(op, podID, podName, HostAddress)
|
||||||
|
|
||||||
|
assert.Equal(t, status.Phase, v1.PodSucceeded, "Expected Phase PodFailed")
|
||||||
|
verifyConditions(t, status.Conditions, v1.ConditionTrue, v1.ConditionTrue, v1.ConditionFalse)
|
||||||
|
assert.Equal(t, status.HostIP, "1.2.3.4", "Expected Host IP Address")
|
||||||
|
assert.Equal(t, status.PodIP, "5.6.7.8", "Expected Pod IP Address")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestStatusError(t *testing.T) {
|
||||||
|
client := client.Default
|
||||||
|
_, ip, _, op := createMocks(t)
|
||||||
|
|
||||||
|
// Start with arguments
|
||||||
|
s, err := NewPodStatus(client, ip)
|
||||||
|
assert.NotNil(t, s, "Expected non-nil creating a pod Status but received nil")
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
|
||||||
|
HostAddress := "0.0.0.0"
|
||||||
|
|
||||||
|
// Set up the mocks for this test
|
||||||
|
fakeErr := fakeError("invalid Pod")
|
||||||
|
ip.On("State", op, podID, podName).Return("", fakeErr)
|
||||||
|
ip.On("EpAddresses", op, podID, podName).Return(nil, fakeErr)
|
||||||
|
|
||||||
|
// Error case
|
||||||
|
status, err := s.GetStatus(op, podID, podName, HostAddress)
|
||||||
|
assert.Nil(t, err, "Expected nil")
|
||||||
|
assert.Equal(t, status.Phase, v1.PodUnknown, "Expected Phase PodUnknown")
|
||||||
|
verifyConditions(t, status.Conditions, v1.ConditionUnknown, v1.ConditionUnknown, v1.ConditionUnknown)
|
||||||
|
assert.Equal(t, status.HostIP, "0.0.0.0", "Expected Host IP Address")
|
||||||
|
assert.Equal(t, status.PodIP, "0.0.0.0", "Expected Pod IP Address")
|
||||||
|
}
|
||||||
|
|
||||||
|
func verifyConditions(t *testing.T, conditions []v1.PodCondition, scheduled v1.ConditionStatus, initialized v1.ConditionStatus, ready v1.ConditionStatus) {
|
||||||
|
for _, condition := range conditions {
|
||||||
|
switch condition.Type {
|
||||||
|
case v1.PodScheduled:
|
||||||
|
assert.Equal(t, condition.Status, scheduled, "Condition Pod Scheduled")
|
||||||
|
break
|
||||||
|
case v1.PodInitialized:
|
||||||
|
assert.Equal(t, condition.Status, initialized, "Condition Pod Initialized")
|
||||||
|
break
|
||||||
|
case v1.PodReady:
|
||||||
|
assert.Equal(t, condition.Status, ready, "Condition Pod Ready")
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -36,8 +36,10 @@ type IsolationProxy interface {
|
|||||||
UnbindScope(op trace.Operation, handle string, name string) (string, interface{}, error)
|
UnbindScope(op trace.Operation, handle string, name string) (string, interface{}, error)
|
||||||
|
|
||||||
Handle(op trace.Operation, id, name string) (string, error)
|
Handle(op trace.Operation, id, name string) (string, error)
|
||||||
State(op trace.Operation, id, name string) (string, error)
|
|
||||||
Remove(op trace.Operation, id string, force bool) error
|
Remove(op trace.Operation, id string, force bool) error
|
||||||
|
|
||||||
|
State(op trace.Operation, id, name string) (string, error)
|
||||||
|
EpAddresses(op trace.Operation, id, name string) ([]string, error)
|
||||||
}
|
}
|
||||||
|
|
||||||
type VicIsolationProxy struct {
|
type VicIsolationProxy struct {
|
||||||
@@ -440,29 +442,6 @@ func (v *VicIsolationProxy) SetState(op trace.Operation, handle, name, state str
|
|||||||
return resp.Payload, nil
|
return resp.Payload, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *VicIsolationProxy) State(op trace.Operation, id, name string) (string, error) {
|
|
||||||
defer trace.End(trace.Begin(id, op))
|
|
||||||
|
|
||||||
if v.client == nil {
|
|
||||||
return "", vicerrors.NillPortlayerClientError("IsolationProxy")
|
|
||||||
}
|
|
||||||
|
|
||||||
results, err := v.client.Containers.GetContainerInfo(containers.NewGetContainerInfoParamsWithContext(op).WithID(id))
|
|
||||||
if err != nil {
|
|
||||||
switch err := err.(type) {
|
|
||||||
case *containers.GetContainerInfoNotFound:
|
|
||||||
return "", vicerrors.NotFoundError(name)
|
|
||||||
case *containers.GetContainerInfoInternalServerError:
|
|
||||||
return "", vicerrors.InternalServerError(err.Payload.Message)
|
|
||||||
default:
|
|
||||||
return "", vicerrors.InternalServerError(fmt.Sprintf("Unknown error from the interaction port layer: %s", err))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
state := results.Payload.ContainerConfig.State
|
|
||||||
return state, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (v *VicIsolationProxy) Remove(op trace.Operation, id string, force bool) error {
|
func (v *VicIsolationProxy) Remove(op trace.Operation, id string, force bool) error {
|
||||||
defer trace.End(trace.Begin(id, op))
|
defer trace.End(trace.Begin(id, op))
|
||||||
|
|
||||||
@@ -481,6 +460,57 @@ func (v *VicIsolationProxy) Remove(op trace.Operation, id string, force bool) er
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (v *VicIsolationProxy) State(op trace.Operation, id, name string) (string, error) {
|
||||||
|
defer trace.End(trace.Begin(id, op))
|
||||||
|
|
||||||
|
payload, err := v.getInfo(op, id, name)
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
|
||||||
|
state := payload.ContainerConfig.State
|
||||||
|
return state, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (v *VicIsolationProxy) EpAddresses(op trace.Operation, id, name string) ([]string, error) {
|
||||||
|
defer trace.End(trace.Begin(id, op))
|
||||||
|
|
||||||
|
payload, err := v.getInfo(op, id, name)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
addresses := make([]string, 0)
|
||||||
|
for _, ep := range payload.Endpoints {
|
||||||
|
addresses = append(addresses, ep.Address)
|
||||||
|
}
|
||||||
|
|
||||||
|
return addresses, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// Private methods
|
||||||
|
func (v *VicIsolationProxy) getInfo(op trace.Operation, id, name string) (*models.ContainerInfo, error) {
|
||||||
|
defer trace.End(trace.Begin(id, op))
|
||||||
|
|
||||||
|
if v.client == nil {
|
||||||
|
return nil, vicerrors.NillPortlayerClientError("IsolationProxy")
|
||||||
|
}
|
||||||
|
|
||||||
|
results, err := v.client.Containers.GetContainerInfo(containers.NewGetContainerInfoParamsWithContext(op).WithID(id))
|
||||||
|
if err != nil {
|
||||||
|
switch err := err.(type) {
|
||||||
|
case *containers.GetContainerInfoNotFound:
|
||||||
|
return nil, vicerrors.NotFoundError(name)
|
||||||
|
case *containers.GetContainerInfoInternalServerError:
|
||||||
|
return nil, vicerrors.InternalServerError(err.Payload.Message)
|
||||||
|
default:
|
||||||
|
return nil, vicerrors.InternalServerError(fmt.Sprintf("Unknown error from port layer: %s", err))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return results.Payload, nil
|
||||||
|
}
|
||||||
|
|
||||||
//------------------------------------
|
//------------------------------------
|
||||||
// Utility Functions
|
// Utility Functions
|
||||||
//------------------------------------
|
//------------------------------------
|
||||||
|
|||||||
@@ -187,6 +187,29 @@ func (_m *IsolationProxy) CreateHandleTask(op trace.Operation, handle string, id
|
|||||||
return r0, r1
|
return r0, r1
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// EpAddresses provides a mock function with given fields: op, id, name
|
||||||
|
func (_m *IsolationProxy) EpAddresses(op trace.Operation, id string, name string) ([]string, error) {
|
||||||
|
ret := _m.Called(op, id, name)
|
||||||
|
|
||||||
|
var r0 []string
|
||||||
|
if rf, ok := ret.Get(0).(func(trace.Operation, string, string) []string); ok {
|
||||||
|
r0 = rf(op, id, name)
|
||||||
|
} else {
|
||||||
|
if ret.Get(0) != nil {
|
||||||
|
r0 = ret.Get(0).([]string)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var r1 error
|
||||||
|
if rf, ok := ret.Get(1).(func(trace.Operation, string, string) error); ok {
|
||||||
|
r1 = rf(op, id, name)
|
||||||
|
} else {
|
||||||
|
r1 = ret.Error(1)
|
||||||
|
}
|
||||||
|
|
||||||
|
return r0, r1
|
||||||
|
}
|
||||||
|
|
||||||
// Handle provides a mock function with given fields: op, id, name
|
// Handle provides a mock function with given fields: op, id, name
|
||||||
func (_m *IsolationProxy) Handle(op trace.Operation, id string, name string) (string, error) {
|
func (_m *IsolationProxy) Handle(op trace.Operation, id string, name string) (string, error) {
|
||||||
ret := _m.Called(op, id, name)
|
ret := _m.Called(op, id, name)
|
||||||
|
|||||||
@@ -28,6 +28,8 @@ import (
|
|||||||
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/proxy"
|
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/proxy"
|
||||||
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/utils"
|
"github.com/virtual-kubelet/virtual-kubelet/providers/vic/utils"
|
||||||
|
|
||||||
|
"net"
|
||||||
|
|
||||||
"k8s.io/api/core/v1"
|
"k8s.io/api/core/v1"
|
||||||
"k8s.io/apimachinery/pkg/api/resource"
|
"k8s.io/apimachinery/pkg/api/resource"
|
||||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||||
@@ -120,6 +122,7 @@ func waitForVCH(op trace.Operation, plClient *client.PortLayer, personaAddr stri
|
|||||||
backoffConf := retry.NewBackoffConfig()
|
backoffConf := retry.NewBackoffConfig()
|
||||||
backoffConf.MaxInterval = 2 * time.Second
|
backoffConf.MaxInterval = 2 * time.Second
|
||||||
backoffConf.InitialInterval = 500 * time.Millisecond
|
backoffConf.InitialInterval = 500 * time.Millisecond
|
||||||
|
backoffConf.MaxElapsedTime = 10 * time.Minute
|
||||||
|
|
||||||
// Wait for portlayer to start up
|
// Wait for portlayer to start up
|
||||||
systemProxy := vicproxy.NewSystemProxy(plClient)
|
systemProxy := vicproxy.NewSystemProxy(plClient)
|
||||||
@@ -262,34 +265,56 @@ func (v *VicProvider) GetPodStatus(namespace, name string) (*v1.PodStatus, error
|
|||||||
defer trace.End(trace.Begin("GetPodStatus", op))
|
defer trace.End(trace.Begin("GetPodStatus", op))
|
||||||
|
|
||||||
now := metav1.NewTime(time.Now())
|
now := metav1.NewTime(time.Now())
|
||||||
|
errorStatus := &v1.PodStatus{
|
||||||
status := &v1.PodStatus{
|
Phase: v1.PodUnknown,
|
||||||
Phase: v1.PodRunning,
|
|
||||||
HostIP: "1.2.3.4",
|
|
||||||
PodIP: "5.6.7.8",
|
|
||||||
StartTime: &now,
|
StartTime: &now,
|
||||||
Conditions: []v1.PodCondition{
|
Conditions: []v1.PodCondition{
|
||||||
{
|
{
|
||||||
Type: v1.PodInitialized,
|
Type: v1.PodInitialized,
|
||||||
Status: v1.ConditionTrue,
|
Status: v1.ConditionUnknown,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
Type: v1.PodReady,
|
Type: v1.PodReady,
|
||||||
Status: v1.ConditionTrue,
|
Status: v1.ConditionUnknown,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
Type: v1.PodScheduled,
|
Type: v1.PodScheduled,
|
||||||
Status: v1.ConditionTrue,
|
Status: v1.ConditionUnknown,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
pod, err := v.GetPod(namespace, name)
|
// Look for the pod in our cache of running pods
|
||||||
|
vp, err := v.podCache.Get(op, namespace, name)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return status, err
|
return errorStatus, err
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, container := range pod.Spec.Containers {
|
// Instantiate status object
|
||||||
|
statusReporter, err := operations.NewPodStatus(v.client, v.isolationProxy)
|
||||||
|
if err != nil {
|
||||||
|
return errorStatus, err
|
||||||
|
}
|
||||||
|
|
||||||
|
var nodeAddress string
|
||||||
|
nodeAddresses := v.NodeAddresses()
|
||||||
|
if len(nodeAddresses) > 0 {
|
||||||
|
nodeAddress = nodeAddresses[0].Address
|
||||||
|
} else {
|
||||||
|
nodeAddress = "0.0.0.0"
|
||||||
|
}
|
||||||
|
status, err := statusReporter.GetStatus(op, vp.ID, name, nodeAddress)
|
||||||
|
if err != nil {
|
||||||
|
return errorStatus, err
|
||||||
|
}
|
||||||
|
|
||||||
|
if vp.Pod.Status.StartTime != nil {
|
||||||
|
status.StartTime = vp.Pod.Status.StartTime
|
||||||
|
} else {
|
||||||
|
status.StartTime = &now
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, container := range vp.Pod.Spec.Containers {
|
||||||
status.ContainerStatuses = append(status.ContainerStatuses, v1.ContainerStatus{
|
status.ContainerStatuses = append(status.ContainerStatuses, v1.ContainerStatus{
|
||||||
Name: container.Name,
|
Name: container.Name,
|
||||||
Image: container.Image,
|
Image: container.Image,
|
||||||
@@ -297,7 +322,7 @@ func (v *VicProvider) GetPodStatus(namespace, name string) (*v1.PodStatus, error
|
|||||||
RestartCount: 0,
|
RestartCount: 0,
|
||||||
State: v1.ContainerState{
|
State: v1.ContainerState{
|
||||||
Running: &v1.ContainerStateRunning{
|
Running: &v1.ContainerStateRunning{
|
||||||
StartedAt: now,
|
StartedAt: *status.StartTime,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
@@ -390,7 +415,25 @@ func (v *VicProvider) NodeConditions() []v1.NodeCondition {
|
|||||||
// NodeAddresses returns a list of addresses for the node status
|
// NodeAddresses returns a list of addresses for the node status
|
||||||
// within Kubernetes.
|
// within Kubernetes.
|
||||||
func (v *VicProvider) NodeAddresses() []v1.NodeAddress {
|
func (v *VicProvider) NodeAddresses() []v1.NodeAddress {
|
||||||
return nil
|
addrs, err := net.InterfaceAddrs()
|
||||||
|
if err != nil {
|
||||||
|
return []v1.NodeAddress{}
|
||||||
|
}
|
||||||
|
|
||||||
|
var outAddresses []v1.NodeAddress
|
||||||
|
for _, addr := range addrs {
|
||||||
|
ipnet, ok := addr.(*net.IPNet)
|
||||||
|
if !ok || ipnet.IP.IsLoopback() || ipnet.IP.To4() == nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
outAddress := v1.NodeAddress{
|
||||||
|
Type: v1.NodeInternalIP,
|
||||||
|
Address: ipnet.IP.String(),
|
||||||
|
}
|
||||||
|
outAddresses = append(outAddresses, outAddress)
|
||||||
|
}
|
||||||
|
|
||||||
|
return outAddresses
|
||||||
}
|
}
|
||||||
|
|
||||||
// NodeDaemonEndpoints returns NodeDaemonEndpoints for the node status
|
// NodeDaemonEndpoints returns NodeDaemonEndpoints for the node status
|
||||||
|
|||||||
Reference in New Issue
Block a user