k8s在線和離線批量修改鏡像地址的兩種方式

背景介紹

有時往k8s集羣裏部署一堆服務的時候,須要拷貝一堆yaml文件,固然還有其餘方式部署,例如經過創建一個一個的流水線等方式,可是這太慢了,雖然是一勞永逸,可是若是說僅僅是部署一次那就可太費勁了,那麼直接拷貝一堆yaml文件就簡單了許多,可是若是以前的環境中鏡像地址是走的內網,而如今放到另外一個環境中,網絡不通時,就須要更改其中的鏡像地址了python

假如以前的網絡環境到阿里雲內網鏡像地址是通的,也就是長這樣:registry-vpc.cn-beijing.aliyuncs.com/xxxx/xxxxxdocker

而後如今要部署到華爲雲上時,直接啓動yaml文件確定是起不來的,須要修改下此鏡像地址,改成:registry.cn-beijing.aliyuncs.com/xxxx/xxxx,改爲這樣就能夠拉了。數組

那麼該如何實現呢?markdown

調用k8s接口完成鏡像替換

下面這段代碼是經過k8s的接口,先去查當前命名空間下都有哪些服務,而後把這些服務都寫道一個數組裏,而後再去迭代這個數組,而後去修改整個命名空間下的全部pod的鏡像地址網絡

import re
from kubernetes import client, config


class deployServer:
    def __init__(self, kubeconfig):
        self.kubeconfig = kubeconfig
        config.kube_config.load_kube_config(config_file=self.kubeconfig)
        self._AppsV1Api = client.AppsV1Api()
        # 這倆暫時用不到
        # self._CoreV1Api = client.CoreV1Api()
        # self._ExtensionsV1beta1Api = client.ExtensionsV1beta1Api()

    def list_deploy(self, namespace_name):
        ''' :param namespace_name: 指定命名空間 :return: 返回一個deployment的列表 '''
        deploySubj = self._AppsV1Api.list_namespaced_deployment(namespace_name)
        return [ subj.metadata.name for subj in deploySubj.items ]

    def patchMultiDeploy(self, namespace_name, newimgdomain):
        for i in self.list_deploy(namespace_name):
            self.patchDeploy(namespace_name, i, newimgdomain)
            print("{}: {} patch success.".format(namespace_name, i))

    def patchDeploy(self, deploy_namespace, deploy_name, newimgdomain, keyword='vpc'):
        img_addr_rule = r"[^?]{1,}\.[^?]{1,}\.com(\/.*\:.*)"
        img_domain_rule = r"([^?]{1,}\.[^?]{1,}\.com).*\:.*"
        old_deploy = self._AppsV1Api.read_namespaced_deployment(
            name=deploy_name,
            namespace=deploy_namespace,
        )
        old_deploy_container = old_deploy.spec.template.spec.containers
        # 迭代deployment的列表,獲取deployment的名稱以及它所在索引位置
        for i, k in enumerate(old_deploy_container):
            # 捕獲處域名以外的鏡像地址
            oldImgAddr = re.findall(img_addr_rule, old_deploy_container[i].image)[0]
            # 捕獲鏡像地址的域名,也能夠不獲取,可是獲取會更準確些
            oldImgDoamin = re.findall(img_domain_rule, old_deploy_container[i].image)[0]
            # 符合條件的纔會進行替換
            if keyword in oldImgDoamin:
                old_deploy_container[i].image = newimgdomain + oldImgAddr
                self._AppsV1Api.patch_namespaced_deployment(
                    name=deploy_name,
                    namespace=deploy_namespace,
                    body=old_deploy
                )
        return


if __name__ == '__main__':
    kubeconfig = r'kubeconfig/config'
    k8s = deployServer(kubeconfig)
    # 指定服務所在命名空間
    namespace = 'ops-logging'
    # 指定要替換的鏡像的域名
    img = 'docker.elastic.co'
    k8s.patchMultiDeploy(namespace, img)
複製代碼

注意這裏須要指定kubeconfig文件dom

修改文件裏的鏡像地址

上面那個是直接調接口,經過patch來進行修改,下面是直接修改yaml文件ui

import os
import re

def modifyImagesFromFile(originpath, src_img, dst_img):
    _re_rule = r".*image: ([^?]{1,}\.[^?]{1,}\.com).*\:.*"
    if os.path.isdir(originpath):
        filesubj = os.walk(originpath)
        filename = []
        # 迭代指定路徑下的全部文件
        for path, _, file in filesubj:
            # 把全部的文件拼成一個完整的路徑,並寫道一個列表裏
            filename = [os.path.join(path, f) for f in file]
        if filename:
            for f in filename:
                with open(f, 'r+', encoding='utf-8') as fr:
                    fr_data = fr.read()
                    replace_list = re.findall(_re_rule, fr_data)
                    if replace_list:
                        for pattern in replace_list:
                            if src_img in pattern:
                                # 把匹配到的內容進行替換
                                fr_data = fr_data.replace(pattern, dst_img)
                        fr.seek(0)
                        fr.write(fr_data)
                        print("{} replace success".format(f))
                    else:
                        print("Unknown")
    else:
        print("{} not a directory".format(originpath))


if __name__ == '__main__':
    originpath = r"E:\項目\DEV環境\sg-saas-pro-hbali\gldsg-gvs\deployments"
    dst_img = 'registry.cn-beijing.aliyuncs.com'
    src_img = 'registry-vpc.cn-beijing.aliyuncs.com'
    modifyImagesFromFile(originpath)
複製代碼

注意: 須要把全部的deployment文件都放到一個目錄裏阿里雲

總結一哈

若是是在線修改的話,就用上面調k8s接口經過patch來修改,直接粘貼複製,指定好命名空間,指定好kubeconfig的文件位置便可
若是是把全部的yaml文件都down下來了,那麼就直接迭代目錄下的全部文件,經過正則去捕獲鏡像地址,而後進行替換,再寫入源文件就能夠了。spa

相關文章
相關標籤/搜索