* Copyright (c) 2024 Huawei Technologies Co., Ltd.
* openFuyao is licensed under Mulan PSL v2.
* You can use this software according to the terms and conditions of the Mulan PSL v2.
* You may obtain a copy of Mulan PSL v2 at:
* http://license.coscl.org.cn/MulanPSL2
* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
* EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
* MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
* See the Mulan PSL v2 for more details.
*/
package k8sutil
import (
"context"
"fmt"
"regexp"
"time"
v1 "k8s.io/api/core/v1"
"k8s.io/apimachinery/pkg/api/errors"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/client-go/dynamic"
"k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
"k8s.io/client-go/tools/clientcmd"
"console-service/pkg/constant"
"console-service/pkg/zlog"
)
const (
requestLastTime = 10
)
func LoadKubeConfigFromBytes(kubeconfig []byte) (*rest.Config, error) {
clientConfig, err := clientcmd.NewClientConfigFromBytes(kubeconfig)
if err != nil {
return nil, err
}
config, err := clientConfig.ClientConfig()
if err != nil {
return nil, err
}
return config, nil
}
func GetSecret(clientset kubernetes.Interface, secretName, namespace string) (*v1.Secret, error) {
secret, err := clientset.CoreV1().Secrets(namespace).
Get(context.Background(), secretName, metav1.GetOptions{})
if err != nil {
zlog.Errorf("Secret %s lookup failed, err: %v", secretName, err)
return nil, err
}
zlog.Infof("Secret %s found in namespace %s", secret.Name, secret.Namespace)
return secret, nil
}
func ListSecret(clientset kubernetes.Interface, namespace string) (*v1.SecretList, error) {
secretList, err := clientset.CoreV1().Secrets(namespace).
List(context.Background(), metav1.ListOptions{})
if err != nil {
zlog.Errorf("Listing Secret failed, err: %v", err)
return nil, err
}
zlog.Infof("List all Secrets in namespace %s", namespace)
return secretList, nil
}
func CreateSecret(clientset kubernetes.Interface, secret *v1.Secret) (*v1.Secret, error) {
secretName := secret.Name
secret, err := clientset.CoreV1().Secrets(secret.Namespace).
Create(context.Background(), secret, metav1.CreateOptions{})
if err != nil {
zlog.Infof("Failed to create secret %s, err: %v", secretName, err)
return nil, err
}
zlog.Infof("Secret %s created in namespace %s", secretName, secret.Namespace)
return secret, err
}
func UpdateSecret(clientset kubernetes.Interface, secret *v1.Secret) (*v1.Secret, error) {
secretName := secret.Name
secret, err := clientset.CoreV1().Secrets(secret.Namespace).
Update(context.Background(), secret, metav1.UpdateOptions{})
if err != nil {
zlog.Infof("Failed to update secret %s, err: %v", secretName, err)
return nil, err
}
zlog.Infof("Secret %s updated in namespace %s", secret.Name, secret.Namespace)
return secret, err
}
func DeleteSecret(clientset kubernetes.Interface, secretName, namespace string) error {
ctx, cancel := context.WithTimeout(context.Background(), requestLastTime*time.Second)
defer cancel()
err := clientset.CoreV1().Secrets(namespace).Delete(ctx, secretName, metav1.DeleteOptions{})
if err != nil {
zlog.Infof("Failed to delete secret %s, err: %v", secretName, err)
return err
}
zlog.Infof("Secret %s deleted in namespace %s\n", secretName, namespace)
return err
}
func GetConfigMap(clientset kubernetes.Interface, configmapName, namespace string) (*v1.ConfigMap, error) {
configMap, err := clientset.CoreV1().ConfigMaps(namespace).
Get(context.Background(), configmapName, metav1.GetOptions{})
if err != nil {
zlog.Errorf("ConfigMap %s lookup failed, err: %v", configmapName, err)
return nil, err
}
zlog.Infof("ConfigMap %s found in namespace %s", configMap.Name, configMap.Namespace)
return configMap, nil
}
func ListConfigMap(clientset kubernetes.Interface, namespace string) (*v1.ConfigMapList, error) {
configmapList, err := clientset.CoreV1().ConfigMaps(namespace).
List(context.Background(), metav1.ListOptions{})
if err != nil {
zlog.Errorf("Listing Configmap failed, err: %v", err)
return nil, err
}
zlog.Infof("List all Configmap in namespace %s", namespace)
return configmapList, nil
}
func CreateConfigMap(clientset kubernetes.Interface, configMap *v1.ConfigMap) (*v1.ConfigMap, error) {
configMapName := configMap.Name
configMap, err := clientset.CoreV1().ConfigMaps(configMap.Namespace).
Create(context.Background(), configMap, metav1.CreateOptions{})
if err != nil {
zlog.Infof("Failed to create configMap %s, err: %v", configMapName, err)
return nil, err
}
zlog.Infof("ConfigMap %s created in namespace %s", configMap.Name, configMap.Namespace)
return configMap, nil
}
func UpdateConfigMap(clientset kubernetes.Interface, configMap *v1.ConfigMap) (*v1.ConfigMap, error) {
configMapName := configMap.Name
configMap, err := clientset.CoreV1().ConfigMaps(configMap.Namespace).
Update(context.Background(), configMap, metav1.UpdateOptions{})
if err != nil {
zlog.Infof("Failed to update configMap %s, err: %v", configMapName, err)
return nil, err
}
zlog.Infof("ConfigMap %s updated in namespace %s", configMap.Name, configMap.Namespace)
return configMap, nil
}
func DeleteConfigMap(clientset kubernetes.Interface, configmapName, namespace string) error {
ctx, cancel := context.WithTimeout(context.Background(), requestLastTime*time.Second)
defer cancel()
err := clientset.CoreV1().ConfigMaps(namespace).Delete(ctx, configmapName, metav1.DeleteOptions{})
if err != nil {
zlog.Infof("Failed to delete secret %s, err: %v", configmapName, err)
return err
}
zlog.Infof("Configmap %s deleted in namespace %s\n", configmapName, namespace)
return err
}
func CrExists(dynamicClient dynamic.Interface, resourceName, namespace string,
gvr schema.GroupVersionResource) (bool, error) {
_, err := dynamicClient.Resource(gvr).Namespace(namespace).
Get(context.Background(), resourceName, metav1.GetOptions{})
if err != nil {
if errors.IsNotFound(err) {
return false, nil
}
zlog.Errorf("check CR existence failed: %v", err)
return false, err
}
return true, nil
}
func StructToUnstructured(v interface{}) (*unstructured.Unstructured, error) {
UnstructuredResult, err := runtime.DefaultUnstructuredConverter.ToUnstructured(v)
if err != nil {
return nil, err
}
return &unstructured.Unstructured{
Object: UnstructuredResult,
}, nil
}
func ResourceMetadataRegexValid(metadataName string) (bool, error) {
re, err := regexp.Compile(constant.MetadataNameRegExPattern)
if err != nil {
return false, err
}
if !re.MatchString(metadataName) {
return false, &RegexError{
Message: "Input does not match metadata.name regex pattern",
}
}
return true, nil
}
type RegexError struct {
Message string
}
func (e *RegexError) Error() string {
return fmt.Sprintf("RegexError: %s", e.Message)
}