小哥之哥 小哥之哥
首页
    • Prometheus
    • Kubertenes
    • Docker
    • MySQL
  • Go
  • Python
  • Vue
  • Jenkins
  • ELK
  • LDAP
  • 随笔
  • 最佳实践
  • 博客搭建
  • 问题杂谈
关于
友链
  • 分类
  • 标签
  • 归档
GitHub (opens new window)

小哥之哥

运维扫地僧
首页
    • Prometheus
    • Kubertenes
    • Docker
    • MySQL
  • Go
  • Python
  • Vue
  • Jenkins
  • ELK
  • LDAP
  • 随笔
  • 最佳实践
  • 博客搭建
  • 问题杂谈
关于
友链
  • 分类
  • 标签
  • 归档
GitHub (opens new window)
  • LDAP

  • Jenkins

    • Jenkins之Docker部署
    • Jenkins之自动化项目发布
    • Jenkins之使用ansible发布项目
      • Jenkins之pipline初识
      • Jenkins之pipline语法
      • Jenkins之钉钉通知
      • Jenkins最佳实践之为job添加构建预览信息
      • Jenkins最佳实践之webhook
    • 技术专题
    • Jenkins
    tchua
    2023-05-19
    目录

    Jenkins之使用ansible发布项目

    # 一、前言


    ansible属于批量管理工具,关于ansible的安装配置这里不在详细介绍,直接参考文档 (opens new window)即可,需要注意的是,使用ansible需要Jenkins主机可以免密登录目标机器。

    # 二、ansible配置


    # 2.1 创建主机清单

    需要Jenkins主机可以免密登录主机组中的机器

    # 查看目前版本
    [root@localhost ~]# ansible --version
    ansible 2.9.27
    #  主机清单 默认文件/etc/ansible/hosts
    # ## 新增开发主机组
    [hz-hosts-ali]
    47.99.69.144
    # ## ansible测试
    [root@localhost ansible]# ansible hz-hosts-ali -m 'ping'
    [WARNING]: Invalid characters were found in group names but not replaced, use -vvvv to see details
    47.99.69.144 | SUCCESS => {
        "ansible_facts": {
            "discovered_interpreter_python": "/usr/bin/python"
        }, 
        "changed": false, 
        "ping": "pong"
    }
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17

    image-20230519113801269

    # 2.2 配置palybook
    # 创建目录
    [root@localhost ansible]# mkdir roles/docker/tasks -p
    # task 剧本文件
    [root@localhost ansible]# vim roles/docker/tasks/main.yml
    剧本具体内容在下面介绍
    # 入口文件
    [root@localhost ansible]# cat docker.yml 
    - hosts: all
      gather_facts: yes
      remote_user: root
      roles:
      - docker
    # 执行 
    [root@localhost ansible]# ansible-playbook docker.yml -l hz-hosts-ali -e name="dingtalk" -e port="18084" 
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    • ansible执行过程

    image-20230519113531542

    • 目标主机结果

    image-20230519113613937

    ::: detail mail.yml

    - pip:
        name: docker
        state: present
    - name: Login registry
      docker_login:
        registry: registry.cn-hangzhou.aliyuncs.com
        username: ${user}
        password: ${password}
        reauthorize: yes
    - name: Pull image
      docker_image:
        name: registry.cn-hangzhou.aliyuncs.com/tf-public/{{ name }}:{{ env | default('latest') }}
        force: yes
    - name: Restart container
      docker_container:
        name: "{{ docker_name | default(name) }}"
        image: registry.cn-hangzhou.aliyuncs.com/tf-public/{{ name }}:{{ env | default('latest') }}
        network_mode: host
        volumes:
          - /data/apps/logs:/data/apps/logs
        log_driver: json-file
        log_options:
          max-size: "10M"
          max-file: "2"
        recreate: yes
        restart_policy: always
        state: started
    - name: Clean image
      shell: docker image prune -f
    
    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

    :::

    注意

    这里发布docker使用的是ansible的docker模块,因此我们需要先在目标主机安装pip命令,可以通过yum -y install python-pip安装,并且不能使用Centos7.9版本,因为自带的python3会影响模块的使用。

    img

    # 三、Docker发布


    前面文章我们提到过使用Docker部署Java项目,这里我进改造下,只要ansible进行发布,这样可以方便我们后续的维护,这种不仅适用于Docker本机部署也可以远程部署,其他应用部署也是一样可以,只需要修改剧本内容即可。

    # 3.1 修改发布配置

    直接修改CD脚本配置

    # 新增内容
    HOSTS="hz-hosts-ali"
    DOCKER_NAME="dingtalk"
    PORT=18084
    
    ansible-playbook docker.yml -l ${HOSTS} -e name="dingtalk" -e port="18084"
    
    1
    2
    3
    4
    5
    6

    ::: detail 完整内容

    # 变量配置
    JAR_PATH="${WORKSPACE}/sp-erp/target"
    JAR_NAME="sp-erp-1.0-SNAPSHOT.jar"
    APP_PATH="/data/apps/sp-erp"
    DOCKER_HUB="registry-vpc.cn-hangzhou.aliyuncs.com/qpos"    ## 镜像仓库地址
    IMAGE_NAME="sp-erp"
    HOSTS="hz-hosts-ali"
    DOCKER_NAME="dingtalk"
    PORT=18084
    # CI 打包
    mvn clean install -DskipTests
    # build image
    # ## Dockerfile
    cat >Dockerfile << EOF
    FROM registry-vpc.cn-hangzhou.aliyuncs.com/public/java:1.8
    MAINTAINER tchua
    ADD ${JAR_PATH}/${JAR_NAME} /apps/
    EXPOSE 18084
    ENTRYPOINT ["java","-jar","/apps/${JAR_NAME}"]
    EOF
    # ## build
    # --username 阿里云镜像仓库用户 --password 阿里云镜像仓库密码
    docker login --username=docker@registry-vpc.cn-hangzhou.aliyuncs.com --password=${password}
    docker build -t $DOCKER_HUB/${IMAGE_NAME}:dev .
    docker push $DOCKER_HUB/${IMAGE_NAME}:dev
    # ## CD
    ansible-playbook /etc/ansible/docker.yml -l ${HOSTS} -e name=${DOCKER_NAME} -e port=${PORT}
    
    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

    :::

    # 3.2 注意事项

    使用Ansible发布需要注意以下:

    • ansible主控机可以免密登录被控主机
    • ansible发布Docker应用时,需要确保被控机上有Docker API Python客户端(docker-py或docker)
    • 经过验证,Centos7.9无法正常使用,推测是因为默认安装有python2和python3的原因

    # 四、K8S发布


    这里介绍的是最简单的模式,原理就是Jenkins主机通过ansible远程至k8s-master节点,调用kubectl命令进行执行应用资源清单文件。

    # 4.1 ansible配置

    这里会使用到模板,主要是用来生成应用的清单文件

    [root@localhost ansible]# mkdir roles/k8s/{tasks,templates} -p
    
    1
    • 模版文件内容
    # roles/k8s/templates/k8s-template.yaml.j2
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      namespace: {{ env }}
      name: {{ app_name }}
      labels:
        app: {{ app_name }}
    spec:
      revisionHistoryLimit: 10
      replicas: {{ replicas }}
      selector:
        matchLabels:
          app: {{ app_name }}
      template:
        metadata:
          labels:
            team: qpos
            app: {{ app_name }}
            version: "{{ tag }}"
        spec:
          nodeSelector:
            channel-env: {{ env }}
          imagePullSecrets:
          - name: bsd-qpos-images
          containers:
          - name: {{ app_name }}
            image: {{ image_url }}/{{ app_name }}:{{ env }}{{ tag }}
            imagePullPolicy: Always
            env:
            - name: APP_NAME
              value: {{ app_name }}
            resources:
              limits:
                memory: {{ pod_limit | default('2048Mi') }}
              requests:
                memory: {{ pod_requests | default('1800Mi') }}
            livenessProbe:
              tcpSocket:
                port: {{ port }}
              initialDelaySeconds: 10
              timeoutSeconds: 3
              periodSeconds: 10
              successThreshold: 1
              failureThreshold: 5
            readinessProbe:
              httpGet:
                port: {{ port }}
                path: /health
            startupProbe:
              tcpSocket:
                port: {{ port }}
              initialDelaySeconds: 25
              timeoutSeconds: 3
              periodSeconds: 10
              successThreshold: 1
              failureThreshold: 30 
    
    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
    • 剧本内容

    /etc/ansible/roles/k8s/template/k8s-template.yaml.j2

    - name: '应用清单文件生成'
      template: src=k8s-template.yaml.j2 dest=/data/bsd-k8s/{{ env }}/bsd-k8s-{{ app_name }}.yaml
    - name: "应用 deploy 部署"
      shell: kubectl apply -f /data/bsd-k8s/{{ env }}/bsd-k8s-{{ app_name }}.yaml --record
    
    1
    2
    3
    4
    • 入口文件

    /etc/ansible/k8s.yml

    - hosts: all
      gather_facts: yes
      remote_user: root
      roles:
      - k8s
    
    1
    2
    3
    4
    5
    # 4.2 Jenkins脚本配置

    Jenkins这里其实与Docker配置基本都一样,只是修改下CD的配置

    # 变量配置
    JAR_PATH="${WORKSPACE}/sp-erp/target"
    JAR_NAME="sp-erp-1.0-SNAPSHOT.jar"
    APP_PATH="/data/apps/sp-erp"
    DOCKER_HUB="registry-vpc.cn-hangzhou.aliyuncs.com/qpos"    ## 镜像仓库地址
    IMAGE_NAME="sp-erp"
    HOSTS="hz-hosts-ali"
    DOCKER_NAME="dingtalk"
    PORT=18084
    Number=1
    # CI 打包
    mvn clean install -DskipTests
    # build image
    # ## Dockerfile
    cat >Dockerfile << EOF
    FROM registry-vpc.cn-hangzhou.aliyuncs.com/public/java:1.8
    MAINTAINER tchua
    ADD ${JAR_PATH}/${JAR_NAME} /apps/
    EXPOSE 18084
    ENTRYPOINT ["java","-jar","/apps/${JAR_NAME}"]
    EOF
    # ## build
    # --username 阿里云镜像仓库用户 --password 阿里云镜像仓库密码
    docker login --username=docker@registry-vpc.cn-hangzhou.aliyuncs.com --password=${password}
    docker build -t $DOCKER_HUB/${IMAGE_NAME}:dev .
    docker push $DOCKER_HUB/${IMAGE_NAME}:dev
    # CD
    ansible-playbook /etc/ansible/k8s-deploy.yml -l asset-k8s-master01 -t bsd-channel-k8s -e \
    	"port=${Port} \
    	replicas=${Number} \
    	env=${Env} \
    	tag=${BUILD_ID} \
    	image_url=${IMAGE_URL} \
    	app_name=${IMAGE_NAME}
    
    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
    # 4.3 总结

    虽然文章介绍的都是简单的使用方式,只要ansible剧本脚本配置好,也能满足大部分工作场景,无论是直接发布java、Docker这种单体模式,还是直接对接k8s,其实CI部分基本都很类似,那么唯一的区别就是CD这里,我们只要把想要实现的功能,通过脚本配置好,就可以完成自己想要的效果,关于Jenkins更加深入的时候,我后面也会根据自己遇到的需求进行记录,因为每个公司架构体系可能不一样,所以没有啥可复制化的东西,只是想着写出来这些,能提供一种思路就行。

    编辑 (opens new window)
    上次更新: 2023/06/29, 18:27:26
    Jenkins之自动化项目发布
    Jenkins之pipline初识

    ← Jenkins之自动化项目发布 Jenkins之pipline初识→

    最近更新
    01
    cert-manager自动签发Lets Encrypt
    09-05
    02
    Docker构建多架构镜像
    08-02
    03
    Prometheus数据迁移至VMstorage
    08-01
    更多文章>
    Theme by Vdoing | Copyright © 2023-2024 |豫ICP备2021026650号
    • 跟随系统
    • 浅色模式
    • 深色模式
    • 阅读模式