go语言试操作k8s集群

连接k8s

k8s连接都是需要认证的

认证方式有很多种

这里采用最简单的配置文件的方式

可以重新生成配置文件

这里测试,所以,直接将master节点上的admin.conf文件拿着用

位置在 /etc/kubernetes/admin.conf

连接部分的代码

func TestDemo(t *testing.T) {
	kubeconfigPath := "../conf/admin.conf"
	config, err := clientcmd.BuildConfigFromFlags("", kubeconfigPath)
	if err != nil {
		t.Fatal(err.Error())
	}

	clientset, err := kubernetes.NewForConfig(config)
	if err != nil {
		t.Fatal(err.Error())
	}
}

使用

一个小demo

package demo_test

import (
	"context"
	"fmt"
	"testing"

	appsv1 "k8s.io/api/apps/v1"
	corev1 "k8s.io/api/core/v1"
	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
	"k8s.io/apimachinery/pkg/util/intstr"
	"k8s.io/client-go/kubernetes"
	"k8s.io/client-go/tools/clientcmd"
)

func TestDemo(t *testing.T) {
	kubeconfigPath := "../conf/admin.conf"
	config, err := clientcmd.BuildConfigFromFlags("", kubeconfigPath)
	if err != nil {
		t.Fatal(err.Error())
	}

	clientset, err := kubernetes.NewForConfig(config)
	if err != nil {
		t.Fatal(err.Error())
	}
	pods, err := clientset.CoreV1().Pods("").List(context.TODO(), metav1.ListOptions{})
	if err != nil {
		t.Fatal(err.Error())
	}

	for _, pod := range pods.Items {
		fmt.Printf("Pod Name: %-40s\tNamespace: %-10s\t%s\n", pod.Name, pod.Namespace, pod.Status.Phase)
	}
}

这是获取集群中所有pod

创建namespace

func TestCreatNamespace(t *testing.T) {
	kubeconfigPath := "admin.conf"

	config, err := clientcmd.BuildConfigFromFlags("", kubeconfigPath)
	if err != nil {
		t.Fatal(err.Error())
	}

	clientset, err := kubernetes.NewForConfig(config)
	if err != nil {
		t.Fatal(err.Error())
	}
    //namespace的名称
	name := "client-go-test"
    // 创建一个namespace的客户端
	namespacesClient := clientset.CoreV1().Namespaces()

    // 构建一个namespace
	namespace := &corev1.Namespace{
		ObjectMeta: metav1.ObjectMeta{
			Name: name,
		},
		Status: corev1.NamespaceStatus{
			Phase: corev1.NamespaceActive,
		},
	}
    
    // 创建namespace
	res, err := namespacesClient.Create(context.Background(), namespace, metav1.CreateOptions{})
	if err != nil {
		panic(err)
	}
	fmt.Printf("Created Namespaces %s on %s\n", res.ObjectMeta.Name, res.ObjectMeta.CreationTimestamp)
}

获取一个namespace

func TestGetNamespace(t *testing.T) {
	kubeconfigPath := "admin.conf"

	config, err := clientcmd.BuildConfigFromFlags("", kubeconfigPath)
	if err != nil {
		t.Fatal(err.Error())
	}

	clientset, err := kubernetes.NewForConfig(config)
	if err != nil {
		t.Fatal(err.Error())
	}

    //需要获取的namespace的名称
	name := "client-go-test"
    // 创建namespace的客户端
	namespacesClient := clientset.CoreV1().Namespaces()
    // 用客户端来查询对应的namespace
	res, err := namespacesClient.Get(context.Background(), name, metav1.GetOptions{})
	if err != nil {
		panic(err)
	}
	fmt.Printf("Get Namespaces %s on %s\n", res.ObjectMeta.Name, res.ObjectMeta.CreationTimestamp)
}

删除namespace

func TestDeleteNamespace(t *testing.T) {
	kubeconfigPath := "admin.conf"

	config, err := clientcmd.BuildConfigFromFlags("", kubeconfigPath)
	if err != nil {
		t.Fatal(err.Error())
	}

	clientset, err := kubernetes.NewForConfig(config)
	if err != nil {
		t.Fatal(err.Error())
	}
	name := "client-go-test"
	namespacesClient := clientset.CoreV1().Namespaces()
	err = namespacesClient.Delete(context.Background(), name, metav1.DeleteOptions{})
	if err != nil {
		panic(err)
	}
	fmt.Printf("删除成功")
}

获取所有namespace

func TestAllNamespace(t *testing.T) {
	kubeconfigPath := "admin.conf"

	config, err := clientcmd.BuildConfigFromFlags("", kubeconfigPath)
	if err != nil {
		t.Fatal(err.Error())
	}

	clientset, err := kubernetes.NewForConfig(config)
	if err != nil {
		t.Fatal(err.Error())
	}
	namespacesClient := clientset.CoreV1().Namespaces()
	res, err := namespacesClient.List(context.Background(), metav1.ListOptions{})
	if err != nil {
		panic(err)
	}
	for _, v := range res.Items {
		fmt.Printf("%s==============%s\n", v.Name, v.CreationTimestamp)
	}
}

部署deployment和对应的service

准备的资源清单文件

---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-deployment
  namespace: default
spec:
  replicas: 3
  selector:
    matchLabels:
      app: http-server
  template:
    metadata:
      labels:
        app: http-server
    spec:
      restartPolicy: Always
      containers:
      - name: http-web
        image: httpd
        imagePullPolicy: IfNotPresent
        ports:
        - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  name: http
  namespace: default
spec:
  type: NodePort
  selector: 
    app: http-server
  ports:
      #这个是指定协议
    - protocol: TCP
      #这个是service的端口
      port: 8080
      #这个是容器内部的端口
      targetPort: 80
      #nodePort
      nodePort: 31111

就是一个简单的http服务

然后转换成代码

func TestDeployment(t *testing.T) {
	kubeconfigPath := "admin.conf"

	config, err := clientcmd.BuildConfigFromFlags("", kubeconfigPath)
	if err != nil {
		t.Fatal(err.Error())
	}

	clientset, err := kubernetes.NewForConfig(config)
	if err != nil {
		t.Fatal(err.Error())
	}
	var i int32 = 3
	// 创建Deployment
	deployment := &appsv1.Deployment{
		ObjectMeta: metav1.ObjectMeta{
			Name: "http-web",
		},
		Spec: appsv1.DeploymentSpec{
			Replicas: &i,
			Selector: &metav1.LabelSelector{
				MatchLabels: map[string]string{
					"app": "http-server",
				},
			},
			Template: corev1.PodTemplateSpec{
				ObjectMeta: metav1.ObjectMeta{
					Labels: map[string]string{
						"app": "http-server",
					},
				},
				Spec: corev1.PodSpec{
					Containers: []corev1.Container{
						{
							Name:  "http",
							Image: "httpd:latest",

							Ports: []corev1.ContainerPort{
								{
									ContainerPort: 80,
								},
							},
						},
					},
				},
			},
		},
	}

	// 创建Deployment资源
	_, err = clientset.AppsV1().Deployments("default").Create(context.TODO(), deployment, metav1.CreateOptions{})
	if err != nil {
		panic(err)
	}

	fmt.Println("Deployment created successfully!")

	// 创建Service
	service := &corev1.Service{
		ObjectMeta: metav1.ObjectMeta{
			Name: "http-service",
		},
		Spec: corev1.ServiceSpec{
			Selector: map[string]string{
				"app": "http-server",
			},
			Ports: []corev1.ServicePort{
				{
					Name:       "http",
					Port:       80,
					TargetPort: intstr.FromInt(80),
					Protocol:   corev1.ProtocolTCP,
					NodePort:   31111,
				},
			},
			Type: corev1.ServiceTypeNodePort,
		},
	}

	// 创建Service资源
	_, err = clientset.CoreV1().Services("default").Create(context.TODO(), service, metav1.CreateOptions{})
	if err != nil {
		panic(err)
	}

	fmt.Println("Service created successfully!")
}

也尝试通过直接传输资源清单文件的方法,但是都不理想,官方给的这个sdk也还行,就是代码量相对要多一些,不太友好,但是如果对资源清单文件比较熟悉的话,也还是挺好用的。

posted @   厚礼蝎  阅读(167)  评论(0编辑  收藏  举报
阅读排行:
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 单元测试从入门到精通
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 上周热点回顾(3.3-3.9)
· winform 绘制太阳,地球,月球 运作规律
点击右上角即可分享
微信分享提示