Add generated file

This PR adds generated files under pkg/client and vendor folder.
This commit is contained in:
xing-yang
2018-07-12 10:55:15 -07:00
parent 36b1de0341
commit e213d1890d
17729 changed files with 5090889 additions and 0 deletions

138
vendor/k8s.io/kubernetes/pkg/util/ipvs/BUILD generated vendored Normal file
View File

@@ -0,0 +1,138 @@
package(default_visibility = ["//visibility:public"])
load(
"@io_bazel_rules_go//go:def.bzl",
"go_library",
"go_test",
)
go_test(
name = "go_default_test",
srcs = [
"ipvs_test.go",
] + select({
"@io_bazel_rules_go//go/platform:linux": [
"ipvs_linux_test.go",
"kernelcheck_linux_test.go",
],
"//conditions:default": [],
}),
embed = [":go_default_library"],
deps = select({
"@io_bazel_rules_go//go/platform:linux": [
"//vendor/github.com/docker/libnetwork/ipvs:go_default_library",
"//vendor/k8s.io/utils/exec:go_default_library",
"//vendor/k8s.io/utils/exec/testing:go_default_library",
],
"//conditions:default": [],
}),
)
go_library(
name = "go_default_library",
srcs = [
"ipvs.go",
] + select({
"@io_bazel_rules_go//go/platform:android": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:darwin": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:dragonfly": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:freebsd": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:linux": [
"ipvs_linux.go",
"kernelcheck_linux.go",
],
"@io_bazel_rules_go//go/platform:nacl": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:netbsd": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:openbsd": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:plan9": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:solaris": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"@io_bazel_rules_go//go/platform:windows": [
"ipvs_unsupported.go",
"kernelcheck_unsupported.go",
],
"//conditions:default": [],
}),
importpath = "k8s.io/kubernetes/pkg/util/ipvs",
deps = select({
"@io_bazel_rules_go//go/platform:android": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:darwin": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:dragonfly": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:freebsd": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:linux": [
"//vendor/github.com/docker/libnetwork/ipvs:go_default_library",
"//vendor/github.com/golang/glog:go_default_library",
"//vendor/k8s.io/apimachinery/pkg/util/sets:go_default_library",
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:nacl": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:netbsd": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:openbsd": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:plan9": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:solaris": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"@io_bazel_rules_go//go/platform:windows": [
"//vendor/k8s.io/utils/exec:go_default_library",
],
"//conditions:default": [],
}),
)
filegroup(
name = "package-srcs",
srcs = glob(["**"]),
tags = ["automanaged"],
visibility = ["//visibility:private"],
)
filegroup(
name = "all-srcs",
srcs = [
":package-srcs",
"//pkg/util/ipvs/testing:all-srcs",
],
tags = ["automanaged"],
)

7
vendor/k8s.io/kubernetes/pkg/util/ipvs/OWNERS generated vendored Normal file
View File

@@ -0,0 +1,7 @@
reviewers:
- thockin
- m1093782566
approvers:
- thockin
- m1093782566

109
vendor/k8s.io/kubernetes/pkg/util/ipvs/ipvs.go generated vendored Normal file
View File

@@ -0,0 +1,109 @@
/*
Copyright 2017 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 ipvs
import (
"net"
"strconv"
)
// Interface is an injectable interface for running ipvs commands. Implementations must be goroutine-safe.
type Interface interface {
// Flush clears all virtual servers in system. return occurred error immediately.
Flush() error
// AddVirtualServer creates the specified virtual server.
AddVirtualServer(*VirtualServer) error
// UpdateVirtualServer updates an already existing virtual server. If the virtual server does not exist, return error.
UpdateVirtualServer(*VirtualServer) error
// DeleteVirtualServer deletes the specified virtual server. If the virtual server does not exist, return error.
DeleteVirtualServer(*VirtualServer) error
// Given a partial virtual server, GetVirtualServer will return the specified virtual server information in the system.
GetVirtualServer(*VirtualServer) (*VirtualServer, error)
// GetVirtualServers lists all virtual servers in the system.
GetVirtualServers() ([]*VirtualServer, error)
// AddRealServer creates the specified real server for the specified virtual server.
AddRealServer(*VirtualServer, *RealServer) error
// GetRealServers returns all real servers for the specified virtual server.
GetRealServers(*VirtualServer) ([]*RealServer, error)
// DeleteRealServer deletes the specified real server from the specified virtual server.
DeleteRealServer(*VirtualServer, *RealServer) error
}
// VirtualServer is an user-oriented definition of an IPVS virtual server in its entirety.
type VirtualServer struct {
Address net.IP
Protocol string
Port uint16
Scheduler string
Flags ServiceFlags
Timeout uint32
}
// ServiceFlags is used to specify session affinity, ip hash etc.
type ServiceFlags uint32
const (
// FlagPersistent specify IPVS service session affinity
FlagPersistent = 0x1
// FlagHashed specify IPVS service hash flag
FlagHashed = 0x2
// IPVSProxyMode is match set up cluster with ipvs proxy model
IPVSProxyMode = "ipvs"
)
// Sets of IPVS required kernel modules.
var ipvsModules = []string{
"ip_vs",
"ip_vs_rr",
"ip_vs_wrr",
"ip_vs_sh",
"nf_conntrack_ipv4",
}
// Equal check the equality of virtual server.
// We don't use struct == since it doesn't work because of slice.
func (svc *VirtualServer) Equal(other *VirtualServer) bool {
return svc.Address.Equal(other.Address) &&
svc.Protocol == other.Protocol &&
svc.Port == other.Port &&
svc.Scheduler == other.Scheduler &&
svc.Flags == other.Flags &&
svc.Timeout == other.Timeout
}
func (svc *VirtualServer) String() string {
return net.JoinHostPort(svc.Address.String(), strconv.Itoa(int(svc.Port))) + "/" + svc.Protocol
}
// RealServer is an user-oriented definition of an IPVS real server in its entirety.
type RealServer struct {
Address net.IP
Port uint16
Weight int
}
func (rs *RealServer) String() string {
return net.JoinHostPort(rs.Address.String(), strconv.Itoa(int(rs.Port)))
}
// Equal check the equality of real server.
// We don't use struct == since it doesn't work because of slice.
func (rs *RealServer) Equal(other *RealServer) bool {
return rs.Address.Equal(other.Address) &&
rs.Port == other.Port &&
rs.Weight == other.Weight
}

268
vendor/k8s.io/kubernetes/pkg/util/ipvs/ipvs_linux.go generated vendored Normal file
View File

@@ -0,0 +1,268 @@
// +build linux
/*
Copyright 2017 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 ipvs
import (
"errors"
"fmt"
"net"
"strings"
"syscall"
libipvs "github.com/docker/libnetwork/ipvs"
"github.com/golang/glog"
utilexec "k8s.io/utils/exec"
)
// runner implements ipvs.Interface.
type runner struct {
exec utilexec.Interface
ipvsHandle *libipvs.Handle
}
// Protocol is the IPVS service protocol type
type Protocol uint16
// New returns a new Interface which will call ipvs APIs.
func New(exec utilexec.Interface) Interface {
handle, err := libipvs.New("")
if err != nil {
glog.Errorf("IPVS interface can't be initialized, error: %v", err)
return nil
}
return &runner{
exec: exec,
ipvsHandle: handle,
}
}
// AddVirtualServer is part of ipvs.Interface.
func (runner *runner) AddVirtualServer(vs *VirtualServer) error {
svc, err := toIPVSService(vs)
if err != nil {
return err
}
return runner.ipvsHandle.NewService(svc)
}
// UpdateVirtualServer is part of ipvs.Interface.
func (runner *runner) UpdateVirtualServer(vs *VirtualServer) error {
svc, err := toIPVSService(vs)
if err != nil {
return err
}
return runner.ipvsHandle.UpdateService(svc)
}
// DeleteVirtualServer is part of ipvs.Interface.
func (runner *runner) DeleteVirtualServer(vs *VirtualServer) error {
svc, err := toIPVSService(vs)
if err != nil {
return err
}
return runner.ipvsHandle.DelService(svc)
}
// GetVirtualServer is part of ipvs.Interface.
func (runner *runner) GetVirtualServer(vs *VirtualServer) (*VirtualServer, error) {
svc, err := toIPVSService(vs)
if err != nil {
return nil, err
}
ipvsSvc, err := runner.ipvsHandle.GetService(svc)
if err != nil {
return nil, err
}
vServ, err := toVirtualServer(ipvsSvc)
if err != nil {
return nil, err
}
return vServ, nil
}
// GetVirtualServers is part of ipvs.Interface.
func (runner *runner) GetVirtualServers() ([]*VirtualServer, error) {
ipvsSvcs, err := runner.ipvsHandle.GetServices()
if err != nil {
return nil, err
}
vss := make([]*VirtualServer, 0)
for _, ipvsSvc := range ipvsSvcs {
vs, err := toVirtualServer(ipvsSvc)
if err != nil {
return nil, err
}
vss = append(vss, vs)
}
return vss, nil
}
// Flush is part of ipvs.Interface. Currently we delete IPVS services one by one
func (runner *runner) Flush() error {
return runner.ipvsHandle.Flush()
}
// AddRealServer is part of ipvs.Interface.
func (runner *runner) AddRealServer(vs *VirtualServer, rs *RealServer) error {
svc, err := toIPVSService(vs)
if err != nil {
return err
}
dst, err := toIPVSDestination(rs)
if err != nil {
return err
}
return runner.ipvsHandle.NewDestination(svc, dst)
}
// DeleteRealServer is part of ipvs.Interface.
func (runner *runner) DeleteRealServer(vs *VirtualServer, rs *RealServer) error {
svc, err := toIPVSService(vs)
if err != nil {
return err
}
dst, err := toIPVSDestination(rs)
if err != nil {
return err
}
return runner.ipvsHandle.DelDestination(svc, dst)
}
// GetRealServers is part of ipvs.Interface.
func (runner *runner) GetRealServers(vs *VirtualServer) ([]*RealServer, error) {
svc, err := toIPVSService(vs)
if err != nil {
return nil, err
}
dsts, err := runner.ipvsHandle.GetDestinations(svc)
if err != nil {
return nil, err
}
rss := make([]*RealServer, 0)
for _, dst := range dsts {
dst, err := toRealServer(dst)
// TODO: aggregate errors?
if err != nil {
return nil, err
}
rss = append(rss, dst)
}
return rss, nil
}
// toVirtualServer converts an IPVS Service to the equivalent VirtualServer structure.
func toVirtualServer(svc *libipvs.Service) (*VirtualServer, error) {
if svc == nil {
return nil, errors.New("ipvs svc should not be empty")
}
vs := &VirtualServer{
Address: svc.Address,
Port: svc.Port,
Scheduler: svc.SchedName,
Protocol: protocolToString(Protocol(svc.Protocol)),
Timeout: svc.Timeout,
}
// Test Flags >= 0x2, valid Flags ranges [0x2, 0x3]
if svc.Flags&FlagHashed == 0 {
return nil, fmt.Errorf("Flags of successfully created IPVS service should be >= %d since every service is hashed into the service table", FlagHashed)
}
// Sub Flags to 0x2
// 011 -> 001, 010 -> 000
vs.Flags = ServiceFlags(svc.Flags &^ uint32(FlagHashed))
if vs.Address == nil {
if svc.AddressFamily == syscall.AF_INET {
vs.Address = net.IPv4zero
} else {
vs.Address = net.IPv6zero
}
}
return vs, nil
}
// toRealServer converts an IPVS Destination to the equivalent RealServer structure.
func toRealServer(dst *libipvs.Destination) (*RealServer, error) {
if dst == nil {
return nil, errors.New("ipvs destination should not be empty")
}
return &RealServer{
Address: dst.Address,
Port: dst.Port,
Weight: dst.Weight,
}, nil
}
// toIPVSService converts a VirtualServer to the equivalent IPVS Service structure.
func toIPVSService(vs *VirtualServer) (*libipvs.Service, error) {
if vs == nil {
return nil, errors.New("virtual server should not be empty")
}
ipvsSvc := &libipvs.Service{
Address: vs.Address,
Protocol: stringToProtocol(vs.Protocol),
Port: vs.Port,
SchedName: vs.Scheduler,
Flags: uint32(vs.Flags),
Timeout: vs.Timeout,
}
if ip4 := vs.Address.To4(); ip4 != nil {
ipvsSvc.AddressFamily = syscall.AF_INET
ipvsSvc.Netmask = 0xffffffff
} else {
ipvsSvc.AddressFamily = syscall.AF_INET6
ipvsSvc.Netmask = 128
}
return ipvsSvc, nil
}
// toIPVSDestination converts a RealServer to the equivalent IPVS Destination structure.
func toIPVSDestination(rs *RealServer) (*libipvs.Destination, error) {
if rs == nil {
return nil, errors.New("real server should not be empty")
}
return &libipvs.Destination{
Address: rs.Address,
Port: rs.Port,
Weight: rs.Weight,
}, nil
}
// stringToProtocolType returns the protocol type for the given name
func stringToProtocol(protocol string) uint16 {
switch strings.ToLower(protocol) {
case "tcp":
return uint16(syscall.IPPROTO_TCP)
case "udp":
return uint16(syscall.IPPROTO_UDP)
}
return uint16(0)
}
// protocolTypeToString returns the name for the given protocol.
func protocolToString(proto Protocol) string {
switch proto {
case syscall.IPPROTO_TCP:
return "TCP"
case syscall.IPPROTO_UDP:
return "UDP"
}
return ""
}

View File

@@ -0,0 +1,390 @@
// +build linux
/*
Copyright 2017 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 ipvs
import (
"fmt"
"net"
"reflect"
"syscall"
"testing"
libipvs "github.com/docker/libnetwork/ipvs"
)
func Test_toVirtualServer(t *testing.T) {
Tests := []struct {
ipvsService libipvs.Service
virtualServer VirtualServer
expectError bool
reason string
}{
{
libipvs.Service{
Flags: 0x0,
},
VirtualServer{},
true,
fmt.Sprintf("IPVS Service Flags should be >= %d, got 0x0", FlagHashed),
},
{
libipvs.Service{
Flags: 0x1,
},
VirtualServer{},
true,
fmt.Sprintf("IPVS Service Flags should be >= %d, got 0x1", FlagHashed),
},
{
libipvs.Service{
Protocol: syscall.IPPROTO_TCP,
Port: 80,
FWMark: 0,
SchedName: "",
Flags: uint32(FlagPersistent + FlagHashed),
Timeout: 0,
Netmask: 0xffffffff,
AddressFamily: syscall.AF_INET,
Address: nil,
PEName: "",
},
VirtualServer{
Address: net.ParseIP("0.0.0.0"),
Protocol: "TCP",
Port: 80,
Scheduler: "",
Flags: ServiceFlags(FlagPersistent),
Timeout: 0,
},
false,
"",
},
{
libipvs.Service{
Protocol: syscall.IPPROTO_UDP,
Port: 33434,
FWMark: 0,
SchedName: "wlc",
Flags: uint32(0 + FlagHashed),
Timeout: 100,
Netmask: 128,
AddressFamily: syscall.AF_INET6,
Address: net.ParseIP("2012::beef"),
PEName: "",
},
VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "UDP",
Port: 33434,
Scheduler: "wlc",
Flags: ServiceFlags(0),
Timeout: 100,
},
false,
"",
},
{
libipvs.Service{
Protocol: 0,
Port: 0,
FWMark: 0,
SchedName: "lc",
Flags: uint32(0 + FlagHashed),
Timeout: 0,
Netmask: 0xffffffff,
AddressFamily: syscall.AF_INET,
Address: net.ParseIP("1.2.3.4"),
PEName: "",
},
VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Protocol: "",
Port: 0,
Scheduler: "lc",
Flags: ServiceFlags(0),
Timeout: 0,
},
false,
"",
},
{
libipvs.Service{
Protocol: 0,
Port: 0,
FWMark: 0,
SchedName: "wrr",
Flags: uint32(FlagPersistent + FlagHashed),
Timeout: 0,
Netmask: 128,
AddressFamily: syscall.AF_INET6,
Address: nil,
PEName: "",
},
VirtualServer{
Address: net.ParseIP("::0"),
Protocol: "",
Port: 0,
Scheduler: "wrr",
Flags: ServiceFlags(FlagPersistent),
Timeout: 0,
},
false,
"",
},
}
for i := range Tests {
got, err := toVirtualServer(&Tests[i].ipvsService)
if Tests[i].expectError && err == nil {
t.Errorf("case: %d, expected error: %s, got nil", i, Tests[i].reason)
}
if !Tests[i].expectError && err != nil {
t.Errorf("case: %d, unexpected error: %v", i, err)
}
if got != nil && &Tests[i].virtualServer != nil {
if !reflect.DeepEqual(*got, Tests[i].virtualServer) {
t.Errorf("case: %d, got %#v, want %#v", i, *got, Tests[i].virtualServer)
}
}
}
}
func Test_toIPVSService(t *testing.T) {
Tests := []struct {
ipvsService libipvs.Service
virtualServer VirtualServer
}{
{
libipvs.Service{
Protocol: syscall.IPPROTO_TCP,
Port: 80,
FWMark: 0,
SchedName: "",
Flags: 0,
Timeout: 0,
Netmask: 0xffffffff,
AddressFamily: syscall.AF_INET,
Address: net.ParseIP("0.0.0.0"),
PEName: "",
},
VirtualServer{
Address: net.ParseIP("0.0.0.0"),
Protocol: "TCP",
Port: 80,
Scheduler: "",
Flags: 0,
Timeout: 0,
},
},
{
libipvs.Service{
Protocol: syscall.IPPROTO_UDP,
Port: 33434,
FWMark: 0,
SchedName: "wlc",
Flags: 1234,
Timeout: 100,
Netmask: 128,
AddressFamily: syscall.AF_INET6,
Address: net.ParseIP("2012::beef"),
PEName: "",
},
VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "UDP",
Port: 33434,
Scheduler: "wlc",
Flags: 1234,
Timeout: 100,
},
},
{
libipvs.Service{
Protocol: 0,
Port: 0,
FWMark: 0,
SchedName: "lc",
Flags: 0,
Timeout: 0,
Netmask: 0xffffffff,
AddressFamily: syscall.AF_INET,
Address: net.ParseIP("1.2.3.4"),
PEName: "",
},
VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Protocol: "",
Port: 0,
Scheduler: "lc",
Flags: 0,
Timeout: 0,
},
},
{
libipvs.Service{
Protocol: 0,
Port: 0,
FWMark: 0,
SchedName: "wrr",
Flags: 0,
Timeout: 0,
Netmask: 128,
AddressFamily: syscall.AF_INET6,
Address: net.ParseIP("::0"),
PEName: "",
},
VirtualServer{
Address: net.ParseIP("::0"),
Protocol: "",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
},
}
for i := range Tests {
got, err := toIPVSService(&Tests[i].virtualServer)
if err != nil {
t.Errorf("case: %d, unexpected error: %v", i, err)
}
if !reflect.DeepEqual(*got, Tests[i].ipvsService) {
t.Errorf("case: %d - got %#v, want %#v", i, *got, Tests[i].ipvsService)
}
}
}
func Test_toRealServer(t *testing.T) {
Tests := []struct {
ipvsDestination libipvs.Destination
realServer RealServer
}{
{
libipvs.Destination{
Port: 54321,
ConnectionFlags: 0,
Weight: 1,
Address: net.ParseIP("1.2.3.4"),
},
RealServer{
Address: net.ParseIP("1.2.3.4"),
Port: 54321,
Weight: 1,
},
},
{
libipvs.Destination{
Port: 53,
ConnectionFlags: 0,
Weight: 1,
Address: net.ParseIP("2002::cafe"),
},
RealServer{
Address: net.ParseIP("2002::cafe"),
Port: 53,
Weight: 1,
},
},
}
for i := range Tests {
got, err := toRealServer(&Tests[i].ipvsDestination)
if err != nil {
t.Errorf("case %d unexpected error: %v", i, err)
}
if !reflect.DeepEqual(*got, Tests[i].realServer) {
t.Errorf("case %d Failed to translate Destination - got %#v, want %#v", i, *got, Tests[i].realServer)
}
}
}
func Test_toIPVSDestination(t *testing.T) {
Tests := []struct {
realServer RealServer
ipvsDestination libipvs.Destination
}{
{
RealServer{
Address: net.ParseIP("1.2.3.4"),
Port: 54321,
Weight: 1,
},
libipvs.Destination{
Port: 54321,
ConnectionFlags: 0,
Weight: 1,
Address: net.ParseIP("1.2.3.4"),
},
},
{
RealServer{
Address: net.ParseIP("2002::cafe"),
Port: 53,
Weight: 1,
},
libipvs.Destination{
Port: 53,
ConnectionFlags: 0,
Weight: 1,
Address: net.ParseIP("2002::cafe"),
},
},
}
for i := range Tests {
got, err := toIPVSDestination(&Tests[i].realServer)
if err != nil {
t.Errorf("case %d unexpected error: %v", i, err)
}
if !reflect.DeepEqual(*got, Tests[i].ipvsDestination) {
t.Errorf("case %d failed to translate Destination - got %#v, want %#v", i, *got, Tests[i].ipvsDestination)
}
}
}
func Test_stringToProtocol(t *testing.T) {
tests := []string{
"TCP", "UDP", "ICMP",
}
expected := []uint16{
uint16(syscall.IPPROTO_TCP), uint16(syscall.IPPROTO_UDP), uint16(0),
}
for i := range tests {
got := stringToProtocol(tests[i])
if got != expected[i] {
t.Errorf("stringToProtocol() failed - got %#v, want %#v",
got, expected[i])
}
}
}
func Test_protocolToString(t *testing.T) {
tests := []Protocol{
syscall.IPPROTO_TCP, syscall.IPPROTO_UDP, Protocol(0),
}
expected := []string{
"TCP", "UDP", "",
}
for i := range tests {
got := protocolToString(tests[i])
if got != expected[i] {
t.Errorf("protocolToString() failed - got %#v, want %#v",
got, expected[i])
}
}
}

366
vendor/k8s.io/kubernetes/pkg/util/ipvs/ipvs_test.go generated vendored Normal file
View File

@@ -0,0 +1,366 @@
/*
Copyright 2017 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 ipvs
import (
"net"
"testing"
)
func TestVirtualServerEqual(t *testing.T) {
Tests := []struct {
svcA *VirtualServer
svcB *VirtualServer
equal bool
reason string
}{
{
svcA: &VirtualServer{
Address: net.ParseIP("10.20.30.40"),
Protocol: "",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
svcB: &VirtualServer{
Address: net.ParseIP("10.20.30.41"),
Protocol: "",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
equal: false,
reason: "IPv4 address not equal",
},
{
svcA: &VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
svcB: &VirtualServer{
Address: net.ParseIP("2017::beef"),
Protocol: "",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
equal: false,
reason: "IPv6 address not equal",
},
{
svcA: &VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "TCP",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
svcB: &VirtualServer{
Address: net.ParseIP("2012::beeef"),
Protocol: "UDP",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
equal: false,
reason: "Protocol not equal",
},
{
svcA: &VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "TCP",
Port: 80,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
svcB: &VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "TCP",
Port: 8080,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
equal: false,
reason: "Port not equal",
},
{
svcA: &VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Protocol: "TCP",
Port: 80,
Scheduler: "rr",
Flags: 0,
Timeout: 0,
},
svcB: &VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Protocol: "TCP",
Port: 80,
Scheduler: "wlc",
Flags: 0,
Timeout: 0,
},
equal: false,
reason: "Scheduler not equal",
},
{
svcA: &VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Protocol: "TCP",
Port: 80,
Scheduler: "rr",
Flags: 2,
Timeout: 0,
},
svcB: &VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Protocol: "TCP",
Port: 80,
Scheduler: "rr",
Flags: 3,
Timeout: 0,
},
equal: false,
reason: "Flags not equal",
},
{
svcA: &VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 0,
},
svcB: &VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "",
Port: 0,
Scheduler: "wrr",
Flags: 0,
Timeout: 10800,
},
equal: false,
reason: "Timeout not equal",
},
{
svcA: &VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Protocol: "TCP",
Port: 80,
Scheduler: "rr",
Flags: 0x1,
Timeout: 10800,
},
svcB: &VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Protocol: "TCP",
Port: 80,
Scheduler: "rr",
Flags: 0x1,
Timeout: 10800,
},
equal: true,
reason: "All fields equal",
},
}
for i := range Tests {
equal := Tests[i].svcA.Equal(Tests[i].svcB)
if equal != Tests[i].equal {
t.Errorf("case: %d got %v, expected %v, reason: %s", i, equal, Tests[i].equal, Tests[i].reason)
}
}
}
func TestRealServerEqual(t *testing.T) {
Tests := []struct {
rsA *RealServer
rsB *RealServer
equal bool
reason string
}{
{
rsA: &RealServer{
Address: net.ParseIP("10.20.30.40"),
Port: 80,
Weight: 1,
},
rsB: &RealServer{
Address: net.ParseIP("10.20.30.41"),
Port: 80,
Weight: 1,
},
equal: false,
reason: "IPv4 address not equal",
},
{
rsA: &RealServer{
Address: net.ParseIP("2012::beef"),
Port: 80,
Weight: 1,
},
rsB: &RealServer{
Address: net.ParseIP("2017::beef"),
Port: 80,
Weight: 1,
},
equal: false,
reason: "IPv6 address not equal",
},
{
rsA: &RealServer{
Address: net.ParseIP("2012::beef"),
Port: 80,
Weight: 1,
},
rsB: &RealServer{
Address: net.ParseIP("2012::beef"),
Port: 8080,
Weight: 1,
},
equal: false,
reason: "Port not equal",
},
{
rsA: &RealServer{
Address: net.ParseIP("10.20.30.40"),
Port: 8080,
Weight: 1,
},
rsB: &RealServer{
Address: net.ParseIP("10.20.30.40"),
Port: 8080,
Weight: 10,
},
equal: false,
reason: "Weight not equal",
},
{
rsA: &RealServer{
Address: net.ParseIP("1.2.3.4"),
Port: 3080,
Weight: 10,
},
rsB: &RealServer{
Address: net.ParseIP("1.2.3.4"),
Port: 3080,
Weight: 10,
},
equal: true,
reason: "All fields equal",
},
{
rsA: &RealServer{
Address: net.ParseIP("2012::beef"),
Port: 3080,
Weight: 10,
},
rsB: &RealServer{
Address: net.ParseIP("2012::beef"),
Port: 3080,
Weight: 10,
},
equal: true,
reason: "All fields equal",
},
}
for i := range Tests {
equal := Tests[i].rsA.Equal(Tests[i].rsB)
if equal != Tests[i].equal {
t.Errorf("case: %d got %v, expected %v, reason: %s", i, equal, Tests[i].equal, Tests[i].reason)
}
}
}
func TestFrontendServiceString(t *testing.T) {
Tests := []struct {
svc *VirtualServer
expected string
}{
{
svc: &VirtualServer{
Address: net.ParseIP("10.20.30.40"),
Protocol: "TCP",
Port: 80,
},
expected: "10.20.30.40:80/TCP",
},
{
svc: &VirtualServer{
Address: net.ParseIP("2012::beef"),
Protocol: "UDP",
Port: 8080,
},
expected: "[2012::beef]:8080/UDP",
},
{
svc: &VirtualServer{
Address: net.ParseIP("10.20.30.41"),
Protocol: "ESP",
Port: 1234,
},
expected: "10.20.30.41:1234/ESP",
},
}
for i := range Tests {
if Tests[i].expected != Tests[i].svc.String() {
t.Errorf("case: %d got %v, expected %v", i, Tests[i].svc.String(), Tests[i].expected)
}
}
}
func TestFrontendDestinationString(t *testing.T) {
Tests := []struct {
svc *RealServer
expected string
}{
{
svc: &RealServer{
Address: net.ParseIP("10.20.30.40"),
Port: 80,
},
expected: "10.20.30.40:80",
},
{
svc: &RealServer{
Address: net.ParseIP("2012::beef"),
Port: 8080,
},
expected: "[2012::beef]:8080",
},
}
for i := range Tests {
if Tests[i].expected != Tests[i].svc.String() {
t.Errorf("case: %d got %v, expected %v", i, Tests[i].svc.String(), Tests[i].expected)
}
}
}

View File

@@ -0,0 +1,71 @@
// +build !linux
/*
Copyright 2017 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 ipvs
import (
"fmt"
utilexec "k8s.io/utils/exec"
)
// New returns a dummy Interface for unsupported platform.
func New(utilexec.Interface) Interface {
return &runner{}
}
type runner struct {
}
func (runner *runner) Flush() error {
return fmt.Errorf("IPVS not supported for this platform")
}
func (runner *runner) AddVirtualServer(*VirtualServer) error {
return fmt.Errorf("IPVS not supported for this platform")
}
func (runner *runner) UpdateVirtualServer(*VirtualServer) error {
return fmt.Errorf("IPVS not supported for this platform")
}
func (runner *runner) DeleteVirtualServer(*VirtualServer) error {
return fmt.Errorf("IPVS not supported for this platform")
}
func (runner *runner) GetVirtualServer(*VirtualServer) (*VirtualServer, error) {
return nil, fmt.Errorf("IPVS not supported for this platform")
}
func (runner *runner) GetVirtualServers() ([]*VirtualServer, error) {
return nil, fmt.Errorf("IPVS not supported for this platform")
}
func (runner *runner) AddRealServer(*VirtualServer, *RealServer) error {
return fmt.Errorf("IPVS not supported for this platform")
}
func (runner *runner) GetRealServers(*VirtualServer) ([]*RealServer, error) {
return nil, fmt.Errorf("IPVS not supported for this platform")
}
func (runner *runner) DeleteRealServer(*VirtualServer, *RealServer) error {
return fmt.Errorf("IPVS not supported for this platform")
}
var _ = Interface(&runner{})

View File

@@ -0,0 +1,94 @@
// +build linux
/*
Copyright 2018 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 ipvs
import (
"fmt"
"regexp"
"strings"
"k8s.io/apimachinery/pkg/util/sets"
utilsexec "k8s.io/utils/exec"
"github.com/golang/glog"
)
// RequiredIPVSKernelModulesAvailableCheck tests IPVS required kernel modules.
type RequiredIPVSKernelModulesAvailableCheck struct {
Executor utilsexec.Interface
}
// Name returns label for RequiredIPVSKernelModulesAvailableCheck
func (r RequiredIPVSKernelModulesAvailableCheck) Name() string {
return "RequiredIPVSKernelModulesAvailable"
}
// Check try to validates IPVS required kernel modules exists or not.
// The name of function can not be changed.
func (r RequiredIPVSKernelModulesAvailableCheck) Check() (warnings, errors []error) {
glog.V(1).Infoln("validating the kernel module IPVS required exists in machine or not")
// Find out loaded kernel modules
out, err := r.Executor.Command("cut", "-f1", "-d", " ", "/proc/modules").CombinedOutput()
if err != nil {
errors = append(errors, fmt.Errorf("error getting installed ipvs required kernel modules: %v(%s)", err, out))
return nil, errors
}
mods := strings.Split(string(out), "\n")
wantModules := sets.NewString()
loadModules := sets.NewString()
wantModules.Insert(ipvsModules...)
loadModules.Insert(mods...)
modules := wantModules.Difference(loadModules).UnsortedList()
// Check builtin modules exist or not
if len(modules) != 0 {
kernelVersionFile := "/proc/sys/kernel/osrelease"
b, err := r.Executor.Command("cut", "-f1", "-d", " ", kernelVersionFile).CombinedOutput()
if err != nil {
errors = append(errors, fmt.Errorf("error getting os release kernel version: %v(%s)", err, out))
return nil, errors
}
kernelVersion := strings.TrimSpace(string(b))
builtinModsFilePath := fmt.Sprintf("/lib/modules/%s/modules.builtin", kernelVersion)
out, err := r.Executor.Command("cut", "-f1", "-d", " ", builtinModsFilePath).CombinedOutput()
if err != nil {
errors = append(errors, fmt.Errorf("error getting required builtin kernel modules: %v(%s)", err, out))
return nil, errors
}
builtInModules := sets.NewString()
for _, builtInMode := range ipvsModules {
match, _ := regexp.Match(builtInMode+".ko", out)
if !match {
builtInModules.Insert(string(builtInMode))
}
}
if len(builtInModules) != 0 {
warnings = append(warnings, fmt.Errorf(
"the IPVS proxier will not be used, because the following required kernel modules are not loaded: %v or no builtin kernel ipvs support: %v\n"+
"you can solve this problem with following methods:\n 1. Run 'modprobe -- ' to load missing kernel modules;\n"+
"2. Provide the missing builtin kernel ipvs support\n", modules, builtInModules))
}
}
return warnings, errors
}

View File

@@ -0,0 +1,130 @@
/*
Copyright 2018 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 ipvs
import (
"testing"
utilsexec "k8s.io/utils/exec"
fakeexec "k8s.io/utils/exec/testing"
)
func TestRequiredIPVSKernelModulesAvailableCheck(t *testing.T) {
cases := []struct {
caseName string
loadedKernel string
kernelVersion string
builtinKernel string
expectErrors bool
expectWarnings bool
}{
{
caseName: "no installed kernel modules and no builtin kernel modules",
loadedKernel: "",
kernelVersion: "3.13.0-24-generic",
builtinKernel: "",
expectErrors: false,
expectWarnings: true,
},
{
caseName: "no installed kernel modules and missing builtin kernel modules",
loadedKernel: "",
kernelVersion: "3.13.0-24-generic",
builtinKernel: "kernel/net/netfilter/ipvs/ip_vs.ko\n" +
"kernel/net/ipv4/netfilter/nf_conntrack_ipv4.ko",
expectErrors: false,
expectWarnings: true,
},
{
caseName: "no installed kernel modules and own all builtin kernel modules",
loadedKernel: "",
kernelVersion: "3.13.0-24-generic",
builtinKernel: "kernel/net/netfilter/ipvs/ip_vs.ko\n" +
"kernel/net/netfilter/ipvs/ip_vs_rr.ko\n" +
"kernel/net/netfilter/ipvs/ip_vs_wrr.ko\n" +
"kernel/net/netfilter/ipvs/ip_vs_sh.ko\n" +
"kernel/net/ipv4/netfilter/nf_conntrack_ipv4.ko",
expectErrors: false,
expectWarnings: false,
},
{
caseName: "missing installed kernel modules and no builtin kernel modules",
loadedKernel: "ip_vs",
kernelVersion: "3.13.0-24-generic",
builtinKernel: "",
expectErrors: false,
expectWarnings: true,
},
{
caseName: "own all installed kernel modules and no builtin kernel modules",
loadedKernel: "ip_vs\n" + "ip_vs_wrr\n" + "nf_conntrack_ipv4\n" +
"ip_vs_rr\n" + "ip_vs_sh",
kernelVersion: "3.13.0-24-generic",
builtinKernel: "",
expectErrors: false,
expectWarnings: false,
},
{
caseName: "own all installed kernel modules and all builtin kernel modules",
loadedKernel: "ip_vs\n" + "ip_vs_wrr\n" + "nf_conntrack_ipv4\n" + "ip_vs_rr\n" + "ip_vs_sh",
kernelVersion: "3.13.0-24-generic",
builtinKernel: "kernel/net/netfilter/ipvs/ip_vs.ko\n" +
"kernel/net/netfilter/ipvs/ip_vs_rr.ko\n" +
"kernel/net/netfilter/ipvs/ip_vs_wrr.ko\n" +
"kernel/net/netfilter/ipvs/ip_vs_sh.ko\n" +
"kernel/net/ipv4/netfilter/nf_conntrack_ipv4.ko",
expectErrors: false,
expectWarnings: false,
},
}
for i, tc := range cases {
fcmd := fakeexec.FakeCmd{
CombinedOutputScript: []fakeexec.FakeCombinedOutputAction{
func() ([]byte, error) { return []byte(cases[i].loadedKernel), nil },
func() ([]byte, error) { return []byte(cases[i].kernelVersion), nil },
func() ([]byte, error) { return []byte(cases[i].builtinKernel), nil },
},
}
fexec := fakeexec.FakeExec{
CommandScript: []fakeexec.FakeCommandAction{
func(cmd string, args ...string) utilsexec.Cmd { return fakeexec.InitFakeCmd(&fcmd, cmd, args...) },
func(cmd string, args ...string) utilsexec.Cmd { return fakeexec.InitFakeCmd(&fcmd, cmd, args...) },
func(cmd string, args ...string) utilsexec.Cmd { return fakeexec.InitFakeCmd(&fcmd, cmd, args...) },
},
}
check := RequiredIPVSKernelModulesAvailableCheck{
Executor: &fexec,
}
warnings, errors := check.Check()
switch {
case warnings != nil && !tc.expectWarnings:
t.Errorf("RequiredIPVSKernelModulesAvailableCheck: unexpected warnings for installed kernel modules %v and builtin kernel modules %v. Warnings: %v", tc.loadedKernel, tc.builtinKernel, warnings)
case warnings == nil && tc.expectWarnings:
t.Errorf("RequiredIPVSKernelModulesAvailableCheck: expected warnings for installed kernel modules %v and builtin kernel modules %v but got nothing", tc.loadedKernel, tc.builtinKernel)
case errors != nil && !tc.expectErrors:
t.Errorf("RequiredIPVSKernelModulesAvailableCheck: unexpected errors for installed kernel modules %v and builtin kernel modules %v. errors: %v", tc.loadedKernel, tc.builtinKernel, errors)
case errors == nil && tc.expectErrors:
t.Errorf("RequiredIPVSKernelModulesAvailableCheck: expected errors for installed kernel modules %v and builtin kernel modules %v but got nothing", tc.loadedKernel, tc.builtinKernel)
}
}
}

View File

@@ -0,0 +1,39 @@
// +build !linux
/*
Copyright 2018 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 ipvs
import (
utilsexec "k8s.io/utils/exec"
)
// RequiredIPVSKernelModulesAvailableCheck tests IPVS required kernel modules.
type RequiredIPVSKernelModulesAvailableCheck struct {
Executor utilsexec.Interface
}
// Name returns label for RequiredIPVSKernelModulesAvailableCheck
func (r RequiredIPVSKernelModulesAvailableCheck) Name() string {
return "RequiredIPVSKernelModulesAvailable"
}
// Check try to validates IPVS required kernel modules exists or not.
func (r RequiredIPVSKernelModulesAvailableCheck) Check() (warnings, errors []error) {
return nil, nil
}

34
vendor/k8s.io/kubernetes/pkg/util/ipvs/testing/BUILD generated vendored Normal file
View File

@@ -0,0 +1,34 @@
package(default_visibility = ["//visibility:public"])
load(
"@io_bazel_rules_go//go:def.bzl",
"go_library",
"go_test",
)
go_library(
name = "go_default_library",
srcs = ["fake.go"],
importpath = "k8s.io/kubernetes/pkg/util/ipvs/testing",
deps = ["//pkg/util/ipvs:go_default_library"],
)
filegroup(
name = "package-srcs",
srcs = glob(["**"]),
tags = ["automanaged"],
visibility = ["//visibility:private"],
)
filegroup(
name = "all-srcs",
srcs = [":package-srcs"],
tags = ["automanaged"],
)
go_test(
name = "go_default_test",
srcs = ["fake_test.go"],
embed = [":go_default_library"],
deps = ["//pkg/util/ipvs:go_default_library"],
)

196
vendor/k8s.io/kubernetes/pkg/util/ipvs/testing/fake.go generated vendored Normal file
View File

@@ -0,0 +1,196 @@
/*
Copyright 2017 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 testing
import (
"fmt"
"net"
"strconv"
utilipvs "k8s.io/kubernetes/pkg/util/ipvs"
)
//FakeIPVS no-op implementation of ipvs Interface
type FakeIPVS struct {
Scheduler string
Services map[serviceKey]*utilipvs.VirtualServer
Destinations map[serviceKey][]*utilipvs.RealServer
}
type serviceKey struct {
IP string
Port uint16
Protocol string
}
func (s *serviceKey) String() string {
return fmt.Sprintf("%s:%d/%s", s.IP, s.Port, s.Protocol)
}
type realServerKey struct {
Address net.IP
Port uint16
}
func (r *realServerKey) String() string {
return net.JoinHostPort(r.Address.String(), strconv.Itoa(int(r.Port)))
}
//NewFake creates a fake ipvs implementation - a cache store.
func NewFake() *FakeIPVS {
return &FakeIPVS{
Services: make(map[serviceKey]*utilipvs.VirtualServer),
Destinations: make(map[serviceKey][]*utilipvs.RealServer),
}
}
func toServiceKey(serv *utilipvs.VirtualServer) serviceKey {
return serviceKey{
IP: serv.Address.String(),
Port: serv.Port,
Protocol: serv.Protocol,
}
}
func toRealServerKey(rs *utilipvs.RealServer) *realServerKey {
return &realServerKey{
Address: rs.Address,
Port: rs.Port,
}
}
//AddVirtualServer is a fake implementation, it simply adds the VirtualServer into the cache store.
func (f *FakeIPVS) AddVirtualServer(serv *utilipvs.VirtualServer) error {
if serv == nil {
return fmt.Errorf("Failed to add virtual server, error: virtual server can't be nil")
}
key := toServiceKey(serv)
f.Services[key] = serv
// make sure no destination present when creating new service
f.Destinations[key] = make([]*utilipvs.RealServer, 0)
return nil
}
//UpdateVirtualServer is a fake implementation, it updates the VirtualServer in the cache store.
func (f *FakeIPVS) UpdateVirtualServer(serv *utilipvs.VirtualServer) error {
if serv == nil {
return fmt.Errorf("Failed to update service, service can't be nil")
}
key := toServiceKey(serv)
f.Services[key] = serv
return nil
}
//DeleteVirtualServer is a fake implementation, it simply deletes the VirtualServer from the cache store.
func (f *FakeIPVS) DeleteVirtualServer(serv *utilipvs.VirtualServer) error {
if serv == nil {
return fmt.Errorf("Failed to delete service: service can't be nil")
}
key := toServiceKey(serv)
delete(f.Services, key)
// clear specific destinations as well
f.Destinations[key] = nil
return nil
}
//GetVirtualServer is a fake implementation, it tries to find a specific VirtualServer from the cache store.
func (f *FakeIPVS) GetVirtualServer(serv *utilipvs.VirtualServer) (*utilipvs.VirtualServer, error) {
if serv == nil {
return nil, fmt.Errorf("Failed to get service: service can't be nil")
}
key := toServiceKey(serv)
svc, found := f.Services[key]
if found {
return svc, nil
}
return nil, fmt.Errorf("Not found serv: %v", key.String())
}
//GetVirtualServers is a fake implementation, it simply returns all VirtualServers in the cache store.
func (f *FakeIPVS) GetVirtualServers() ([]*utilipvs.VirtualServer, error) {
res := make([]*utilipvs.VirtualServer, 0)
for _, svc := range f.Services {
res = append(res, svc)
}
return res, nil
}
//Flush is a fake implementation, it simply clears the cache store.
func (f *FakeIPVS) Flush() error {
// directly drop old data
f.Services = nil
f.Destinations = nil
return nil
}
//AddRealServer is a fake implementation, it simply creates a RealServer for a VirtualServer in the cache store.
func (f *FakeIPVS) AddRealServer(serv *utilipvs.VirtualServer, dest *utilipvs.RealServer) error {
if serv == nil || dest == nil {
return fmt.Errorf("Failed to add destination for service, neither service nor destination shouldn't be nil")
}
key := toServiceKey(serv)
if _, ok := f.Services[key]; !ok {
return fmt.Errorf("Failed to add destination for service %v, service not found", key.String())
}
dests := f.Destinations[key]
if dests == nil {
dests = make([]*utilipvs.RealServer, 0)
f.Destinations[key] = dests
}
f.Destinations[key] = append(f.Destinations[key], dest)
return nil
}
//GetRealServers is a fake implementation, it simply returns all RealServers in the cache store.
func (f *FakeIPVS) GetRealServers(serv *utilipvs.VirtualServer) ([]*utilipvs.RealServer, error) {
if serv == nil {
return nil, fmt.Errorf("Failed to get destination for nil service")
}
key := toServiceKey(serv)
if _, ok := f.Services[key]; !ok {
return nil, fmt.Errorf("Failed to get destinations for service %v, service not found", key.String())
}
return f.Destinations[key], nil
}
//DeleteRealServer is a fake implementation, it deletes the real server in the cache store.
func (f *FakeIPVS) DeleteRealServer(serv *utilipvs.VirtualServer, dest *utilipvs.RealServer) error {
if serv == nil || dest == nil {
return fmt.Errorf("Failed to delete destination, neither service nor destination can't be nil")
}
key := toServiceKey(serv)
if _, ok := f.Services[key]; !ok {
return fmt.Errorf("Failed to delete destination for service %v, service not found", key.String())
}
dests := f.Destinations[key]
exist := false
for i := range dests {
if toRealServerKey(dests[i]).String() == toRealServerKey(dest).String() {
// Delete one element
f.Destinations[key] = append(f.Destinations[key][:i], f.Destinations[key][i+1:]...)
exist = true
break
}
}
// Not Found
if !exist {
return fmt.Errorf("Failed to delete real server for service %v, real server not found", key.String())
}
return nil
}
var _ = utilipvs.Interface(&FakeIPVS{})

View File

@@ -0,0 +1,179 @@
/*
Copyright 2017 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 testing
import (
"net"
"testing"
utilipvs "k8s.io/kubernetes/pkg/util/ipvs"
)
func TestVirtualServer(t *testing.T) {
// Initialize
fake := NewFake()
// Add a virtual server
vs1 := &utilipvs.VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Port: uint16(80),
Protocol: string("TCP"),
Flags: utilipvs.FlagHashed,
}
err := fake.AddVirtualServer(vs1)
if err != nil {
t.Errorf("Fail to add virtual server, error: %v", err)
}
// Get a specific virtual server
got1, err := fake.GetVirtualServer(vs1)
if err != nil {
t.Errorf("Fail to get virtual server, error: %v", err)
}
if !vs1.Equal(got1) {
t.Errorf("Expect virtual server: %v, got: %v", vs1, got1)
}
// Update virtual server
vs12 := &utilipvs.VirtualServer{
Address: net.ParseIP("1.2.3.4"),
Port: uint16(80),
Protocol: string("TCP"),
Flags: utilipvs.FlagPersistent,
}
err = fake.UpdateVirtualServer(vs12)
if err != nil {
t.Errorf("Fail to update virtual server, error: %v", err)
}
// Check the updated virtual server
got12, err := fake.GetVirtualServer(vs1)
if !got12.Equal(vs12) {
t.Errorf("Expect virtual server: %v, got: %v", vs12, got12)
}
// Add another virtual server
vs2 := &utilipvs.VirtualServer{
Address: net.ParseIP("10::40"),
Port: uint16(8080),
Protocol: string("UDP"),
}
err = fake.AddVirtualServer(vs2)
if err != nil {
t.Errorf("Unexpected error when add virtual server, error: %v", err)
}
// List all virtual servers
list, err := fake.GetVirtualServers()
if err != nil {
t.Errorf("Fail to list virtual servers, error: %v", err)
}
if len(list) != 2 {
t.Errorf("Expect 2 virtual servers, got: %d", len(list))
}
// Delete a virtual server
err = fake.DeleteVirtualServer(vs1)
if err != nil {
t.Errorf("Fail to delete virtual server: %v, error: %v", vs1, err)
}
// Check the deleted virtual server no longer exists
got, _ := fake.GetVirtualServer(vs1)
if got != nil {
t.Errorf("Expect nil, got: %v", got)
}
// Flush all virtual servers
err = fake.Flush()
if err != nil {
t.Errorf("Fail to flush virtual servers, error: %v", err)
}
// List all virtual servers
list, err = fake.GetVirtualServers()
if err != nil {
t.Errorf("Fail to list virtual servers, error: %v", err)
}
if len(list) != 0 {
t.Errorf("Expect 0 virtual servers, got: %d", len(list))
}
}
func TestRealServer(t *testing.T) {
// Initialize
fake := NewFake()
// Add a virtual server
vs := &utilipvs.VirtualServer{
Address: net.ParseIP("10.20.30.40"),
Port: uint16(80),
Protocol: string("TCP"),
}
rss := []*utilipvs.RealServer{
{net.ParseIP("172.16.2.1"), 8080, 1},
{net.ParseIP("172.16.2.2"), 8080, 2},
{net.ParseIP("172.16.2.3"), 8080, 3},
}
err := fake.AddVirtualServer(vs)
if err != nil {
t.Errorf("Fail to add virtual server, error: %v", err)
}
// Add real server to the virtual server
for i := range rss {
if err = fake.AddRealServer(vs, rss[i]); err != nil {
t.Errorf("Fail to add real server, error: %v", err)
}
}
// Delete a real server of the virtual server
// Make sure any position of the list can be real deleted
rssLen := len(rss)
for i := range rss {
// List all real servers of the virtual server
list, err := fake.GetRealServers(vs)
if err != nil {
t.Errorf("Fail to get real servers of the virtual server, error: %v", err)
}
if len(list) != rssLen {
t.Errorf("Expect %d virtual servers, got: %d", len(rss), len(list))
}
rsToDel := list[i]
if err = fake.DeleteRealServer(vs, rsToDel); err != nil {
t.Errorf("Fail to delete real server of the virtual server, error: %v", err)
} else {
dests, err := fake.GetRealServers(vs)
if err != nil {
t.Errorf("Fail to get real servers of the virtual server, error: %v", err)
}
for _, dest := range dests {
if toRealServerKey(dest).String() == toRealServerKey(rsToDel).String() {
t.Errorf("Expect real server %q be deleted.", rsToDel.String())
}
}
if err = fake.AddRealServer(vs, rsToDel); err != nil {
t.Errorf("Fail to add real server, error: %v", err)
}
}
}
// Test delete real server that not exist
rs := &utilipvs.RealServer{
Address: net.ParseIP("172.16.2.4"),
Port: uint16(8080),
Weight: 1,
}
if err = fake.DeleteRealServer(vs, rs); err == nil {
t.Errorf("Delete real server that not exist, Expect error, got nil")
}
// Delete the virtual server
err = fake.DeleteVirtualServer(vs)
if err != nil {
t.Errorf("Fail to delete virtual server, error: %v", err)
}
_, err = fake.GetRealServers(vs)
if err == nil {
t.Errorf("Expect error, got nil")
}
}