Files
Rainbond/gpushare-device-plugin/pkg/kubelet/client/client.go
2025-08-25 16:04:00 +08:00

135 lines
3.2 KiB
Go

package client
import (
"encoding/json"
"fmt"
"io"
v1 "k8s.io/api/core/v1"
utilnet "k8s.io/apimachinery/pkg/util/net"
restclient "k8s.io/client-go/rest"
"k8s.io/client-go/transport"
"net/http"
"time"
)
// KubeletClientConfig defines config parameters for the kubelet client
type KubeletClientConfig struct {
// Address specifies the kubelet address
Address string
// Port specifies the default port - used if no information about Kubelet port can be found in Node.NodeStatus.DaemonEndpoints.
Port uint
// TLSClientConfig contains settings to enable transport layer security
restclient.TLSClientConfig
// Server requires Bearer authentication
BearerToken string
// HTTPTimeout is used by the client to timeout http requests to Kubelet.
HTTPTimeout time.Duration
}
type KubeletClient struct {
defaultPort uint
host string
client *http.Client
}
func NewKubeletClient(config *KubeletClientConfig) (*KubeletClient, error) {
trans, err := makeTransport(config, true)
if err != nil {
return nil, err
}
client := &http.Client{
Transport: trans,
Timeout: config.HTTPTimeout,
}
return &KubeletClient{
host: config.Address,
defaultPort: config.Port,
client: client,
}, nil
}
// transportConfig converts a client config to an appropriate transport config.
func (c *KubeletClientConfig) transportConfig() *transport.Config {
cfg := &transport.Config{
TLS: transport.TLSConfig{
CAFile: c.CAFile,
CAData: c.CAData,
CertFile: c.CertFile,
CertData: c.CertData,
KeyFile: c.KeyFile,
KeyData: c.KeyData,
},
BearerToken: c.BearerToken,
}
if !cfg.HasCA() {
cfg.TLS.Insecure = true
}
return cfg
}
// makeTransport creates a RoundTripper for HTTP Transport.
func makeTransport(config *KubeletClientConfig, insecureSkipTLSVerify bool) (http.RoundTripper, error) {
// do the insecureSkipTLSVerify on the pre-transport *before* we go get a potentially cached connection.
// transportConfig always produces a new struct pointer.
preTLSConfig := config.transportConfig()
if insecureSkipTLSVerify && preTLSConfig != nil {
preTLSConfig.TLS.Insecure = true
preTLSConfig.TLS.CAData = nil
preTLSConfig.TLS.CAFile = ""
}
tlsConfig, err := transport.TLSConfigFor(preTLSConfig)
if err != nil {
return nil, err
}
rt := http.DefaultTransport
if tlsConfig != nil {
// If SSH Tunnel is turned on
rt = utilnet.SetOldTransportDefaults(&http.Transport{
TLSClientConfig: tlsConfig,
})
}
return transport.HTTPWrappersForConfig(config.transportConfig(), rt)
}
func ReadAll(r io.Reader) ([]byte, error) {
b := make([]byte, 0, 512)
for {
if len(b) == cap(b) {
// Add more capacity (let append pick how much).
b = append(b, 0)[:len(b)]
}
n, err := r.Read(b[len(b):cap(b)])
b = b[:len(b)+n]
if err != nil {
if err == io.EOF {
err = nil
}
return b, err
}
}
}
func (k *KubeletClient) GetNodeRunningPods() (*v1.PodList, error) {
resp, err := k.client.Get(fmt.Sprintf("https://%v:%d/pods/", k.host, k.defaultPort))
if err != nil {
return nil, err
}
body, err := ReadAll(resp.Body)
if err != nil {
return nil, err
}
podLists := &v1.PodList{}
if err = json.Unmarshal(body, &podLists); err != nil {
return nil, err
}
return podLists, err
}