/
client.go
148 lines (119 loc) · 4.63 KB
/
client.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
package client
import (
"context"
"crypto/tls"
"fmt"
"net/http"
"path"
"time"
"github.com/pkg/errors"
v1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/labels"
"k8s.io/apimachinery/pkg/version"
"k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
"k8s.io/client-go/tools/clientcmd"
"k8s.io/client-go/util/homedir"
)
// Kubernetes provides an interface to common Kubernetes API operations
type Kubernetes interface {
// FindNode returns a Node reference containing the pod named as the argument, if any
FindNode(name string) (*v1.Node, error)
// FindPodsByLabel returns a PodList reference containing the pods matching the provided label selector.
FindPodsByLabel(namespace string, labelSelector metav1.LabelSelector) (*v1.PodList, error)
// FindServicesByLabel returns a ServiceList containing the services matching the provided label selector.
FindServicesByLabel(namespace string, labelSelector metav1.LabelSelector) (*v1.ServiceList, error)
// ListServices returns a ServiceList containing all the services.
ListServices(namespace string) (*v1.ServiceList, error)
// Config returns a config of API client
Config() *rest.Config
// SecureHTTPClient returns http.Client configured with timeout and CA Cert
SecureHTTPClient(time.Duration) (*http.Client, error)
// FindSecret returns the secret with the given name, if any
FindSecret(name, namespace string) (*v1.Secret, error)
// ServerVersion returns the kubernetes server version.
ServerVersion() (*version.Info, error)
}
type goClientImpl struct {
client *kubernetes.Clientset
config *rest.Config
}
func (ka *goClientImpl) ServerVersion() (*version.Info, error) {
return ka.client.ServerVersion()
}
func (ka *goClientImpl) Config() *rest.Config {
return ka.config
}
func (ka *goClientImpl) FindNode(name string) (*v1.Node, error) {
return ka.client.CoreV1().Nodes().Get(context.TODO(), name, metav1.GetOptions{})
}
func (ka *goClientImpl) FindPodsByLabel(namespace string, labelSelector metav1.LabelSelector) (*v1.PodList, error) {
selectorMap, err := metav1.LabelSelectorAsMap(&labelSelector)
if err != nil {
return nil, fmt.Errorf("converting label selector %q to map: %w", labelSelector, err)
}
return ka.client.CoreV1().Pods(namespace).List(context.TODO(), metav1.ListOptions{ // nosemgrep: context-todo
LabelSelector: labels.SelectorFromSet(selectorMap).String(),
})
}
func (ka *goClientImpl) FindServicesByLabel(namespace string, labelSelector metav1.LabelSelector) (*v1.ServiceList, error) {
selectorMap, err := metav1.LabelSelectorAsMap(&labelSelector)
if err != nil {
return nil, fmt.Errorf("converting label selector %q to map: %w", labelSelector, err)
}
return ka.client.CoreV1().Services(namespace).List(context.TODO(), metav1.ListOptions{ // nosemgrep: context-todo
LabelSelector: labels.SelectorFromSet(selectorMap).String(),
})
}
func (ka *goClientImpl) ListServices(namespace string) (*v1.ServiceList, error) {
return ka.client.CoreV1().Services(namespace).List(context.TODO(), metav1.ListOptions{}) // nosemgrep: context-todo
}
func (ka *goClientImpl) SecureHTTPClient(t time.Duration) (*http.Client, error) {
c, ok := ka.client.RESTClient().(*rest.RESTClient)
if !ok {
return nil, errors.New("failed to set up a client for connecting to Kubelet through API proxy")
}
return c.Client, nil
}
func (ka *goClientImpl) FindSecret(name, namespace string) (*v1.Secret, error) {
return ka.client.CoreV1().Secrets(namespace).Get(context.TODO(), name, metav1.GetOptions{})
}
// BasicHTTPClient returns http.Client configured with timeout
func BasicHTTPClient(t time.Duration) *http.Client {
return &http.Client{
Timeout: t,
}
}
// InsecureHTTPClient returns http.Client configured with timeout
// and InsecureSkipVerify flag enabled
func InsecureHTTPClient(t time.Duration) *http.Client {
client := BasicHTTPClient(t)
client.Transport = &http.Transport{
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
}
return client
}
// NewKubernetes instantiates a Kubernetes API client
// if tryLocalKubeConfig is true, this will try to load your kubeconfig from ~/.kube/config
func NewKubernetes(tryLocalKubeConfig bool) (Kubernetes, error) {
ka := new(goClientImpl)
var err error
ka.config, err = rest.InClusterConfig()
if err != nil {
if !tryLocalKubeConfig {
return nil, err
}
kubeconf := path.Join(homedir.HomeDir(), ".kube", "config")
config, err := clientcmd.BuildConfigFromFlags("", kubeconf)
if err != nil {
return nil, errors.Wrap(err, "could not load local kube config")
}
ka.config = config
}
ka.client, err = kubernetes.NewForConfig(ka.config)
if err != nil {
return nil, err
}
return ka, nil
}