• Argo Rollouts结合Service进行Blue-Green部署


    删除03 部署04
    root@k8s-master01:~/learning-jenkins-cicd/09-argocd-and-rollout/rollout-demos# kubectl delete    -f 03-rollouts-with-prometheus-analysis.yaml 
    
    root@k8s-master01:~/learning-jenkins-cicd/09-argocd-and-rollout/rollout-demos# kubectl apply -f 04-rollouts-bluegreen-demo.yaml 
    
    
    • 1
    • 2
    • 3
    • 4
    • 5

    更新镜像

    root@k8s-master01:~/k8s-prom# kubectl  rollouts set image rollout-helloworld-bluegreen spring-boot-helloworld=ikubernetes/demoapp:v1.0
    rollout "rollout-helloworld-bluegreen" image updated
    
    • 1
    • 2


    在这里插入图片描述
    虽然新版已经启动,但外部流量依旧访问得是旧版本,此时在图形界面手动切换promote,切换后会发现流量切换到新版本上

    删除04,开启05
    kubectl apply -f 05-rollouts-bluegreen-with-analysis.yaml

    开启错误请求
    while true ; do curl hello.magedu.com/dd ;sleep 2;done

    执行更新

    root@k8s-master01:~/k8s-prom# kubectl get rollouts.argoproj.io 
    NAME                                         DESIRED   CURRENT   UP-TO-DATE   AVAILABLE   AGE
    rollout-helloworld-bluegreen-with-analysis   3         3         3            3           48s
    root@k8s-master01:~/k8s-prom# kubectl rollout
    rollout   (Manage the rollout of a resource)                        rollouts  (The command rollouts is a plugin installed by the user)
    root@k8s-master01:~/k8s-prom# kubectl rollouts set image rollout-helloworld-bluegreen-with-analysis spring-boot-helloworld=ikubernetes/demoapp:v1.0
    rollout "rollout-helloworld-bluegreen-with-analysis" image update
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    删除05
    root@k8s-master01:~/learning-jenkins-cicd/09-argocd-and-rollout/rollout-demos# kubectl delete -f 05-rollouts-bluegreen-with-analysis.yaml

    将gitlab中spring-boot-helloWorld/rollouts/rollouts-canary-demo.yaml替换为/learning-jenkins-cicd/09-argocd-and-rollout/rollout-demos/03-rollouts-with-prometheus-analysis.yaml

    重建jenkins
    root@k8s-master01:~/learning-k8s/jenkins# kubectl apply -f deploy/
    root@k8s-master01:~/learning-k8s/jenkins# kubectl apply -f deploy/

    查看token

    jenkins@jenkins-dc5478948-tw7gc:/$ cat /var/run/secrets/kubernetes.io/serviceaccount/token && echo
    eyJhbGciOiJSUzI1NiIsImtpZCI6IklQaC1rY29PSDVqMlZGblpYbVpwMGhzN0V2Nm5jSFNTd3Vmc1dBQ0dTa1EifQ.eyJhdWQiOlsiaHR0cHM6Ly9rdWJlcm5ldGVzLmRlZmF1bHQuc3ZjLmNsdXN0ZXIubG9jYWwiXSwiZXhwIjoxNzMxOTExMzcwLCJpYXQiOjE3MDAzNzUzNzAsImlzcyI6Imh0dHBzOi8va3ViZXJuZXRlcy5kZWZhdWx0LnN2Yy5jbHVzdGVyLmxvY2FsIiwia3ViZXJuZXRlcy5pbyI6eyJuYW1lc3BhY2UiOiJqZW5raW5zIiwicG9kIjp7Im5hbWUiOiJqZW5raW5zLWRjNTQ3ODk0OC10dzdnYyIsInVpZCI6IjdkN2U1ZDU4LTYyZjgtNGZmMS04ODUzLWIzZjhmMWVhNTExYyJ9LCJzZXJ2aWNlYWNjb3VudCI6eyJuYW1lIjoiamVua2lucy1tYXN0ZXIiLCJ1aWQiOiI5ZjEwOTgyNi0yOTE0LTRlNDgtODUwYS1iNjUwMmQ0M2M1ZWEifSwid2FybmFmdGVyIjoxNzAwMzc4OTc3fSwibmJmIjoxNzAwMzc1MzcwLCJzdWIiOiJzeXN0ZW06c2VydmljZWFjY291bnQ6amVua2luczpqZW5raW5zLW1hc3RlciJ9.iSRsLe8QGP1WJ18jMf5_CESItiZECh3Y6mo_Ab1EhB8iVFgiFihXzTkOVphqwhvZ5P5ofZ-gTkfPXVGmkq0AStLBp05gGwtIMmu-OHp-Y-LkYlrE_CUsmu9Oh8mcN33tSWr3n1rP6MNS4LqN0O7LYdW8oJFUZDmuLBfBTLIdN5aeFAmbdfQymjcpGKPM7N1FVU7e9BJk4N8saEvvTfi0Vgkgd8beSF68QJ6IEh4s-aoynUuARxyPRLejoygJNOUcqlsMvJ_cr7cG81mwY4BIxLQTZ6t4wmYgSt_k8yJCIZ271sJqHZyyWWfxSauQYieGx3a4WYRbITQfQHBLPt73AQ

    jenkins凭据管理更新凭据

    jenkins流水线配置

    pipeline {
        agent {
            kubernetes {
                inheritFrom 'maven-docker-kubectl'
            }
        }   
        triggers {
            GenericTrigger(
                genericVariables: [
                    [key: 'ref', value: '$.ref']
                ],
                token: 'fClZ0e/kTcqL2ARh7YqxW/3ndOCZA2SqfKnRTLat',
                causeString: 'Triggered on $ref',
                printContributedVariables: true,
                printPostContent: true
            )
        }   
        environment {
            codeRepo="http://192.168.1.50/root/spring-boot-helloWorld.git"
            registry='harbor.luohw.net'
            registryUrl='https://harbor.luohw.net'
            registryCredential='harbor-user-credential'
            projectName='spring-boot-helloworld'
            imageUrl="${registry}/ikubernetes/${projectName}"
            imageTag="${BUILD_ID}"
        }
        stages {
            stage('Source') {
                steps {
                    git branch: 'main', credentialsId: 'gitlab-root-credential', url: "${codeRepo}"
                }
            }
            stage('Build') {
                steps {
                    container('maven') {
                        sh 'mvn -B -DskipTests clean package'
                    }
                }
            }
            stage('Test') {
                steps {
                    container('maven') {
                        sh 'mvn test'
                    }
                }
            }
            stage("SonarQube Analysis") {
                steps {
                    container('maven') {                
                        withSonarQubeEnv('SonaQube-Server') {
                            sh 'mvn sonar:sonar'
                        }
                    }
                }
            }
            stage("Quality Gate") {
                steps {
                    timeout(time: 30, unit: 'MINUTES') {
                        waitForQualityGate abortPipeline: true
                    }
                }
            } 
            stage('Build Image') {
                steps {
                    container('dind') {
                        script {
                            dockerImage = docker.build("${imageUrl}:${imageTag}")  
                        }
                    }
                }
            }       
            stage('Push Image') {
                steps {
                    container('dind') {
                        script {
                            docker.withRegistry(registryUrl, registryCredential) {
                                dockerImage.push()
                                dockerImage.push('latest')
                            }
                        }
                    }
                }
            }
            stage('Update-manifests') {
            	steps {
            	    container('jnlp') {
            	        sh 'sed -i "s#__IMAGE__#${imageUrl}:${imageTag}#gi" rollouts/rollouts-canary-demo.yaml'
            	    }  
            	}
            }
            stage('Deploy') {
                steps {
                    container('kubectl') {
                        withKubeConfig([credentialsId: 'k8s-cicd-admin-credentials', serverUrl: 'https://kubernetes.default.svc']) {
                            sh '''
                                kubectl apply -f rollouts/rollouts-canary-demo.yaml -n default
                            '''
                        }
                    }
                }
            }              
        }
        post{
            always{
                qyWechatNotification failNotify: true, webhookUrl: 'https://qyapi.weixin.qq.com/cgi-bin/webhook/send?key=5530d220-0983-490e-ada5-a74fa66570c8'
            }
        }   
    }
    
    • 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

    deploy失败是因为token会更新,运行测试容器,重新获取token并在jenkins中更新即可
    在这里插入图片描述

    测试容器yaml
    root@k8s-master01:~# cat mypod.yaml 
    apiVersion: v1
    kind: Pod
    metadata:
      creationTimestamp: null
      labels:
        run: mypod
      name: mypod
      namespace: kube-system
    spec:
      containers:
      - image: ikubernetes/demoapp:v1.0
        name: mypod
        resources: {}
      dnsPolicy: ClusterFirst
      restartPolicy: Always
      serviceAccountName: k8s-cicd-admin
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    root@k8s-master01:~# kubectl apply -f mypod.yaml 
    pod/mypod created
    root@k8s-master01:~# kubectl exec -it  -n kube-system   mypod  -- sh
    [root@mypod /]# cat /run/secrets/kubernetes.io/serviceaccount/token  && echo 
    eyJhbGciOiJSUzI1NiIsImtpZCI6IklQaC1rY29PSDVqMlZGblpYbVpwMGhzN0V2Nm5jSFNTd3Vmc1dBQ0dTa1EifQ.eyJhdWQiOlsiaHR0cHM6Ly9rdWJlcm5ldGVzLmRlZmF1bHQuc3ZjLmNsdXN0ZXIubG9jYWwiXSwiZXhwIjoxNzMxOTEyODUzLCJpYXQiOjE3MDAzNzY4NTMsImlzcyI6Imh0dHBzOi8va3ViZXJuZXRlcy5kZWZhdWx0LnN2Yy5jbHVzdGVyLmxvY2FsIiwia3ViZXJuZXRlcy5pbyI6eyJuYW1lc3BhY2UiOiJrdWJlLXN5c3RlbSIsInBvZCI6eyJuYW1lIjoibXlwb2QiLCJ1aWQiOiI1ZGEwZWRhYS1lMWQ4LTRhYjItYWUyNy1lY2Q1YWQzYjI4NmEifSwic2VydmljZWFjY291bnQiOnsibmFtZSI6Ims4cy1jaWNkLWFkbWluIiwidWlkIjoiNGQzN2U4MjktOTE5ZS00MDcwLTk4YTUtMDA1YzAwZDAwMzc5In0sIndhcm5hZnRlciI6MTcwMDM4MDQ2MH0sIm5iZiI6MTcwMDM3Njg1Mywic3ViIjoic3lzdGVtOnNlcnZpY2VhY2NvdW50Omt1YmUtc3lzdGVtOms4cy1jaWNkLWFkbWluIn0.pOae_dgto7sXu-yQ4iTegXR-lPYnLKPJXyWt4TcI3fmlgMZqmA4O6SUS_ntAbfnWN6XDNd0x1CvMTVPuXh7DSuJ5RqItXDXAy_xgMf3xMYKV0J9YHo7MJAwpLbupcS2B1sl8_Hpfc-N6lrih_JeAoSzc1sCfUQAjh35VbFB6wkkkAUQfWFSpg2iCT23FZcxyKQIq7P4ixH1LZb8mjFTXuB7229H4GqrQiyVSOq9RsqWDLtB-mH8XUiW3tSWQwpzV15OQ_elFgYVqujA_z3TdMs3BoANM0RKU-E30af5YeR40vTFG6pI2EcE12_Apq39Wvp5RUvx2EcEeWW3xjAJp3w
    
    • 1
    • 2
    • 3
    • 4
    • 5

    在这里插入图片描述

  • 相关阅读:
    【Vue】问题:TypeScript intellisense is disabled on template
    Visual studio解决‘scanf: This function or variable may be unsafe. 问题
    一个简单的模拟实例说明Task及其调度问题
    创芯科技USB_CAN【库文件】
    可视化 | (三)Edward Tufted基本设计准则
    技术学习:Python(18)|爬虫篇|解析器BeautifulSoup4(一)
    接口测试 Jmeter 接口测试 —— 请求 Headers 与传参方式
    nodejs获取微信access_token并保存文件
    C++进阶语法之函数和指针【学习笔记(二)】
    Java老人护理上门服务类型系统小程序APP源码
  • 原文地址:https://blog.csdn.net/m0_37749659/article/details/134489891