logo头像

老陕小张学技术接地气

Devops从入门到实战

硬件项目配置

服务器名称 ip 系统版本 服务名称
gitlab 192.168.75.100 Centos7.8 2vcpu4G gitlab
jenkins 192.168.75.101 Centos7.8 2vcpu6G jenkins、sonarQube、Client
harbor 192.168.75.102 Centos7.8 2vcpu4G harbor
masternode 192.168.75.103 Centos7.8 2vcpu4G k8s-master
node1 192.168.75.104 Centos7.8 2vcpu4G k8s-node

一、DevOps介绍

软件开发最开始是由两个团队组成:

  • 开发计划由开发团队从头开始设计和整体系统的构建。需要系统不停的迭代更新。
  • 运维团队将开发团队的Code进行测试后部署上线。希望系统稳定安全运行。

这看似两个目标不同的团队需要协同完成一个软件的开发。

在开发团队指定好计划并完成coding后,需要提供到运维团队。

运维团队向开发团队反馈需要修复的BUG以及一些需要返工的任务。

这时开发团队需要经常等待运维团队的反馈。这无疑延长了事件并推迟了整个软件开发的周期。

会有一种方式,在开发团队等待的时候,让开发团队转移到下一个项目中。等待运维团队为之前的代码提供反馈。

可是这样就意味着一个完整的项目需要一个更长的周期才可以开发出最终代码。


基于现在的互联网现状,更推崇敏捷式开发,这样就导致项目的迭代速度更快,但是由于开发团队与运维团队的沟通问题,会导致新版本上线的时间成本很高。

这又违背的敏捷式开发的最初的目的。那么如果让开发团队和运维团队整合到成一个团队,协同应对一套软件呢?这就被称DevOps.DevOps,字面意思是Development &Operations的缩写,也就是开发&运维

虽然字面意思只涉及到开发团队和运维团队,其实QA测试团队也是参与其中的。

网上可以查看到DevOops的符合类似一个无穷大符合

二、Operate阶段工具

!部署过程,会采用Docker进行部署,暂时只安装Docker即可,后续还需要安装kubenetes

2.1 Docker 安装

  • 准备测试环境&生产环境

  • 下载Docker依赖组件

    yum install -y yum-utils \
      device-mapper-persistent-data \
      lvm2
  • 设置下载Docker的镜像源为阿里云

    yum-config-manager \
        --add-repo \
        http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
  • 安装Docker服务

    yum install docker-ce docker-ce-cli containerd.io docker-compose-plugin
  • 安装成功后,启动Docker并设置开机自启

    systemctl start docker
    systemctl enable docker
  • 测试安装

    [root@jenkins ~]# docker version
    Client: Docker Engine - Community
     Version:           24.0.4
     API version:       1.43
     Go version:        go1.20.5
     Git commit:        3713ee1
     Built:             Fri Jul  7 14:54:21 2023
     OS/Arch:           linux/amd64
     Context:           default

2.2 Docker-Compose安装

#访问下载地址
https://github.com/docker/compose/tags
#根据需要下载相应的版本
wget https://github.com/docker/compose/releases/download/v2.19.1/docker-compose-linux-x86_64 
#将docker-compose-linux-x86_64 到/usr/local/bin
mv docker-compose-linux-x86_64 /usr/local/bin
#赋予执行取消
chmod a+x /usr/local/bin/docker-compose
#验证是否安装成功
[root@jenkins ~]# docker-compose  version
Docker Compose version v2.19.1

三、Code阶段工具

3.1 Git安装

  • Linux安装

    yum install -y git
  • Window安装

3.2 GitLab安装

  • 硬件配置必须大于4G内存

  • 拉取GitLab镜像

    docker pull gitlab/gitlab-ce
  • 准备docker-compose.yml

    version: "3.1"
    services:
      gitlab:
        image: "gitlab/gitlab-ce:latest"
        restart: always
        environment:
          GITLAB_OMNIBUS_CONFIG: |
            external_url "http://192.168.75.100:8929"
            gitlab_rails['gitlab_shell_ssh_port'] = 2224
        ports:
          - "8929:8929"
          - "2224:2224"
        volumes:
          - "./config:/etc/gitlab"
          - "./logs:/var/log/gitlab"
          - "./data:/var/opt/gitlab"
  • 启动容器(需要稍微等一下)

    docker-compose  up -d
  • 打开浏览器访问GitLab首页http://192.168.75.100:8929/

  • 登录GitLab

    用户:root

    密码在 initial_root_password文件中

    cat config/initial_root_password
  • 创建新项目在gitlab中

  • 将源代码上传到gitlab中,我这里使用window中git工具
#进入项目代码文件夹
cd demoHello
#初始化git仓库
git init
#添加文件
git add .
#提交到本地
git commit -m "代码v1"
#配置远端仓库,点击gitlab项目中的clone查找项目仓库地址
git remote add origin http://192.168.75.100:8929/root/demoHello.git
#push到远程仓库某分支,完成代码上传
git push -u origin "master"
  • 查看代码上传结果

四、Build阶段工具

构建Java项目的工具一般有二种选择,一个是Maven,一个是Gradle。

这里我们选择Maven作为项目的编译工具。

具体安装Maven流程不做阐述,但是需要确保配置好Maven仓库以及JDK编译版本。

五、Integrate工具

持续集成、持续部署CI、CD的工具很多,其中Jenkins是一个开源的持续集成平台Jenkins涉及到将编写完毕的代码发布到测试环境和生产环境的任务,并且还涉及到了构建项目等任务。
Jenkins需要大量的插件保证工作,安装成本较高,下面会基于Docker搭建Jenkins。

5.1 Jenkins介绍

Jenkins是一个开源软件项目,是基于Java开发的一种持续集成工具Jenkins应用广泛,大多数互联网公司都采用Jenkins配合GitLab、Docker、K8s作为实现DevOps的核心工具.Jenkins最强大的就在于插件,Jenkins官方提供了大量的插件库,来自动化CI/CD过程中的各种琐碎功能。

Jenkins最主要的工作就是将GitLab上可以构建的工程代码拉取并且进行构建,再根据流程可以选择发布到测试环境或是生产环境。

一般是GitLab上的代码经过大量的测试后,确定发行版本,再发布到生产环境。

CI/CD可以理解为:

  • CI过程即是通过Jenkins将代码拉取、构建、制作镜像交给测试人员测试。

    1.持续集成:让软件代码可以持续的集成到主干上,并自动构建和测试。

  • CD过程即是通过Jenkins将打好标签的发行版本代码拉取、构建、制作镜像交给运维人员部署

    1.持续交付:让经过持续集成的代码可以进行手动部署。

    2.持续部署:让可以持续交付的代码随时随地的自动化部署。

5.2 Jenkins安装

  • 了解一下jenkins官网是jenkins.io
  • 拉取Jenkins镜像
docker pull jenkins/jenkins:2.413-jdk11
  • 编写docker-compose.yml
version: "3.1"
services:
  jenkins:
    image: jenkins/jenkins:2.413-jdk11
    container_name: jenkins
    ports:
      - 8080:8080
      - 50000:50000
    volumes:
      - ./data/:/var/jenkins_home/
  • 启动Jenkins容器
[root@jenkins ~]# docker-compose  up -d
  • 日志报错修改
# 查看日志
[root@jenkins ~]# docker logs -f  jenkins
touch: cannot touch '/var/jenkins_home/copy_reference_file.log': Permission denied
Can not write to /var/jenkins_home/copy_reference_file.log. Wrong volume permissions?
# 修改bug
[root@jenkins ~]# chmod -R  777 data/
# 重新启动容器
[root@jenkins ~]# docker-compose  restart
[+] Restarting 1/1
 ✔ Container jenkins  Started 
# 查看日志,如果显示密码,则服务正常
[root@jenkins ~]# docker logs -f  jenkins
  • 访问Jenkins服务在浏览器http://192.168.75.101:8080

  • 重新启动Jenkins容器后,由于Jenkins需要下载大量内容,但是由于默认下载地址下载速度较慢,需要重新设置下载地址为国内镜像站

  • 解锁Jenkins,查看Jenkins密码,并把命名填充

[root@jenkins ~]# cat data/secrets/initialAdminPassword
98ff1758a1c34e6aad615361b9975317
  • 插件安装教学,选择插件来安装,最后选择安装,耐心等待,有可能安装失败,可以点击“继续”,可以进入Jenkins官网进行插件下载

  • 创建管理员名,并选择默认访问路径

  • 安装完成,来到Jenkins管理界面

  • 安装本实验需要的插件,点击Manage Jenkins/插件管理/可选插件,依次安装本实验需要的基础插件git parameter,Publish Over SSH

5.3 Jenkins 入门配置

5.3.1 配置Maven 构建代码

  • 安装jdk
#jdk文件下载官网
https://www.oracle.com/java/technologies/downloads/
#下载版本
jdk-8u141-linux-x64.tar.gz
tar -xvf jdk-8u141-linux-x64.tar.gz  -C /usr/local/ #解压文件
  • 安装Maven
#Maven文件下载官网
https://maven.apache.org/download.cgi
#下载版本
apache-maven-3.5.4.zip
unzip apache-maven-3.5.4.zip
mv apache-maven-3.5.4 /usr/local/maven  #解压文件
  • 配置maven国内源
vim /usr/local/maven/conf/settings.xml
#159行添加国内源配置
    <mirror>
       <id>alimaven</id>
       <name>aliyun maven</name>
       <url>http://maven.aliyun.com/nexus/content/groups/public/</url>
       <mirrorOf>central</mirrorOf>
     </mirror>
     </mirrors>
  • 配置jdk编译选项
vim /usr/local/maven/conf/settings.xml
# maven 默认使用 jdk1.8 版本,找到<profiles>标签,往其中添加:
#253行添加
<profile>
    <id>jdk8</id>
    <activation>
        <activeByDefault>true</activeByDefault>
        <jdk>1.8</jdk>
    </activation>
    <properties>
        <maven.compiler.source>1.8</maven.compiler.source>
        <maven.compiler.target>1.8</maven.compiler.target>
        <maven.compiler.compilerVersion>1.8</maven.compiler.compilerVersion>
    </properties>
</profile>
  • 启动jdk8
vim /usr/local/maven/conf/settings.xml
# 275行处添加
  <activeProfiles>
     <activeProfile>jdk8</activeProfile>
  </activeProfiles>
  • 将配置好的jdk和Maven配置到jenkins环境中
[root@jenkins ~]# mv /usr/local/jdk/ data/
[root@jenkins ~]# mv /usr/local/maven/ data/
[root@jenkins ~]# chmod -R  777 data/
  • 在jenkins全局配置中配置jdk和maven的环境

5.3.2配置Publish 发布&远程操作

在系统管理中添加SSH servers配置

六、CI、CD入门操作

6.1 持续集成

6.1.1 构建任务

  • 选择项目任务

  • 配置git拉取仓库地址保存项目

  • 执行构建任务并检查空调输出构建内容

  • 服务器查看git clone 的代码
#内容存在,证明任务正确,也可以看执行任务的图标
[root@jenkins ~]# ls data/workspace/demoHello/
demoHello.iml  pom.xml  src
  • 配置mave打包Jar包

  • 重新构建任务,并验证打包结果,这次任务构建时间比较长,需要等待一下
#查看打包任务
[root@jenkins ~]# ls  data/workspace/demoHello/target/
classes  demoHello-0.0.1.jar  demoHello-0.0.1.jar.original  generated-sources  generated-test-sources  maven-archiver  maven-status  test-classes
  • 配置将生成的Jar包放到目标服务器上,并构建环境

  • 查看工具中Jar包
[root@jenkins ~]# ls /usr/local/test/target/
demoHello-0.0.1.jar

准备Docker构建环境

#docker文件夹结构
$ ls docker/
Dockerfile  docker-compose.yml
#文件Dockerfile
FROM daocloud.io/library/java:8u40-jdk
COPY demoHello-0.0.1.jar /usr/local
WORKDIR /usr/local
CMD java -jar demoHello-0.0.1.jar
#docker-compose.yml
version: "3.1"
services:
  demohello:
    build:
      context: ./
      dockerfile: Dockerfile
    image: demohello:v1.0.0
    container_name: demohello
    ports:
      - 8081:8081
#修改pox.xml
    <build>
    <finalName>demoHello</finalName> #增加内容,代表项目名称
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
  • 将项目代码更新gitlab上
$ git add .
$ git commit -m "docker"
$ git push
  • 构建配置环境

  • 构建新的任务,并查看结果

    [root@jenkins ~]# docker  ps
    CONTAINER ID   IMAGE                         COMMAND                  CREATED          STATUS          PORTS                                                                                      NAMES
    c01978f0cd8c   demohello:v1.0.0              "/bin/sh -c 'java -j…"   56 seconds ago   Up 56 seconds   0.0.0.0:8081->8081/tcp, :::8081->8081/tcp                                                  demohello
    [root@jenkins ~]# docker images
    REPOSITORY                 TAG           IMAGE ID       CREATED          SIZE
    demohello                  v1.0.0        478867d8574e   52 minutes ago   846MB
    #可以通过Linux命令访问部署任务,也可以通过浏览器访问
    [root@jenkins docker]# curl  http://192.168.75.101:8081/hello
    Hello World v1.0.1

6.2 持续交付、部署

6.2.1 通过标签控制版本信息

  • 配置构建环境

  • 配置gitlab中的tag,首先给目前版本创建tag为v1

  • 更新代码并提交代码修增加tag为v2可以参考上面教程,提交代码和给代码提交版本
#修改docker-compose.yml
    image: demohello:v2.0.0
#修改src/main/java/com/example/demohello/controller/HelloController.java
 public String helloWorld() {
        return "Hello World v2.0.0";
    }
  • 可以看到构建按钮可以动态选择

  • 执行构建任务并检查结果

[root@jenkins docker]# docker images
REPOSITORY                 TAG           IMAGE ID       CREATED          SIZE
demohello                  v2.0.0        a5158a6c4e1f   22 minutes ago   846MB
demohello                  v1.0.0        9a623fcc1385   23 minutes ago   846MB
[root@jenkins docker]# docker ps
CONTAINER ID   IMAGE                         COMMAND                  CREATED          STATUS          PORTS                                                                                      NAMES
014179370a24   demohello:v2.0.0              "/bin/sh -c 'java -j…"   22 minutes ago   Up 22 minutes   0.0.0.0:8081->8081/tcp, :::8081->8081/tcp                                                  demohello
[root@jenkins docker]# curl  http://192.168.75.101:8081/hello
Hello World v2.0.0

七、集成Sonar Qube

7.1 sonarQube 介绍

SonarQube是一个开源的代码质量管理平台,旨在帮助开发团队提高代码的可靠性、可维护性和可扩展性。它提供了一系列的静态代码分析工具,能够自动检测代码中的潜在问题和缺陷,比如代码冗余、代码复杂度、潜在的安全漏洞等。

SonarQube不仅可以对多种编程语言进行分析,如Java、C#、C++、Python等,还支持与各种构建工具和持续集成平台集成,如Maven、Jenkins等。通过在代码开发过程中集成SonarQube,团队可以及早发现和修复潜在的问题,从而提高代码质量和开发效率。

除了代码分析功能,SonarQube还提供了可视化的仪表板和报告,帮助开发团队监控代码质量的趋势和改进的进展。它还支持规则定制和自定义,可以根据团队或项目的特定需求进行配置和扩展。

总的来说,SonarQube是一个功能强大、易于使用的工具,可以帮助开发团队不断提升代码质量,并促进持续的项目成功。

7.2 sonarQube 环境搭建

7.2.1 sonarQube 安装

  • 通过docker-compose搭建sonarQube
version: "3.1"
services:
  db:
    image: postgres
    container_name: db
    ports:
      - 5432:5432
    networks:
      - sonarnet
    environment:
      POSTGRES_USER: sonar
      POSTGRES_PASSWORD: sonar
  sonarqube:
    image: sonarqube:lts-community
    container_name: sonarqube
    depends_on:
      - db
    ports:
      - 9000:9000
    networks:
      - sonarnet
    environment:
      SONAR_JDBC_URL: jdbc:postgresql://db:5432/sonar
      SONAR_JDBC_USERNAME: sonar
      SONAR_JDBC_PASSWORD: sonar
networks:
  sonarnet:
    driver: bridge
  • 当执行docker-compose启动命令,看到sonarQube无法正常启动,修改bug的方法
#查看sonarQube无法启动是否这个原因
[root@jenkins sonarqube_docker]# docker ps -a
CONTAINER ID   IMAGE                         COMMAND                  CREATED          STATUS                     PORTS                                                                                      NAMES
6e0930750723   sonarqube:lts-community       "bin/run.sh bin/sona…"   2 minutes ago    Exited (0) 2 minutes ago
[root@jenkins sonarqube_docker]# docker restart 6e0930750723 |docker logs -f 6e0930750723
ERROR: [1] bootstrap checks failed. You must address the points described in the following [1] lines before starting Elasticsearch.
bootstrap check failure [1] of [1]: max virtual memory areas vm.max_map_count [65530] is too low, increase to at least [262144]
ERROR: Elasticsearch did not exit normally - check the logs at /opt/sonarqube/logs/sonarqube.log
#修改bug,在/etc/sysctl.conf参加vm.max_map_count=262144配置
[root@jenkins sonarqube_docker]# vim /etc/sysctl.conf
vm.max_map_count=262144
#使配置生效
[root@jenkins sonarqube_docker]# sysctl -p
vm.max_map_count = 262144
#重新启动sonarqube服务器,需要再sonarqube_docker目录
[root@jenkins sonarqube_docker]# docker-compose  restart

  • sonarQube服务汉化,需要安装汉化插件

  • 安装插件需要重新启动服务,需要耐心等待一会

7.2.2 sonarQube 使用

7.2.2.1 mave本地使用sonarQube服务

  • 可以通过配置maven,使用sonarQube
#在settings.xml配置和配置jdk的位置一样
<profile>
    <id>sonar</id>
    <activation>
        <activeByDefault>true</activeByDefault>
    </activation>
    <properties>
      <sonar.login>admin</sonar.login>
      <sonar.password>123456789</sonar.password>
      <sonar.host.url>http://192.168.75.101:9000</sonar.host.url>
    </properties>
</profile> 
    <activeProfile>sonar</activeProfile>
  • 在idea的终端输入命令
mvn sonar:sonar
  • 登陆sonarQube查看结果内容

7.2.2.2 sonar-scanner使用sonarQube服务

  • 将sonar-scanner压缩包解压,并配置环境
#解压
[root@jenkins ~]# unzip sonar-scanner-cli-4.8.0.2856-linux.zip
#配置环境
[root@jenkins ~]# mv sonar-scanner-cli-4.8.0.2856-linux ./data/sonar-scanner
#配置sonar-scanner使用sonarQube的文件
[root@jenkins ~]# vim data/sonar-scanner/conf/sonar-scanner.properties
sonar.host.url=http://192.168.75.101:9000
sonar.sourceEncoding=UTF-8
  • 由于sonar-scanner连接sonarQube服务需要秘钥或者用户账号,为了后面的持续集成,我们需要用sonarQube生成一个秘钥给sonar-scanner用

  • 验证sonar-scanner使用sonarQube服务
[root@jenkins ~]# cd data/workspace/demoHello/
[root@jenkins demoHello]# /root/data/sonar-scanner/bin/sonar-scanner -Dsoanr.sources=./ -Dsonar.projectname=demoHello -Dsonar.login=a0277c64b7c5f6c1e03700fdd9f881eb48c98633 -Dsonar.projectKey=demoHello -Dsonar.java.binaries=./target/
……………………
INFO: ------------------------------------------------------------------------
INFO: EXECUTION SUCCESS
INFO: ------------------------------------------------------------------------
INFO: Total time: 7.968s
INFO: Final Memory: 17M/60M
INFO: ------------------------------------------------------------------------
#删除测试生成目录,方便后续为构建jenkins任务排除bug
[root@jenkins demoHello]# rm -fr .scannerwork/

7.2.2.3 Jenkins使用 sonar-scanner配置

  • 需要给Jenkins安装sonarQube插件,我下面的图片是安装好的

  • 配置sonarQube系统环境

  • 安装sonar-scanner

  • 7.2.2.4 任务使用 sonar-scanner配置

  • 执行任务并验证sonar-scanner

八、集成harbor

8.1 安装harbor

  • 下载harbor安装包,在github网站上搜索harbor,回去下载链接

    wget https://github.com/goharbor/harbor/releases/download/v2.8.2/harbor-offline-installer-v2.8.2.tgz
  • 修改harbor配置文件

    #解压harbor
    tar -xvf harbor-offline-installer-v2.8.2.tgz -C /usr/local
    #进入harbor目录修改配置文件
    cd  /usr/local/harbor
    cp harbor.yml.tmpl harbor.yml
    vim harbor.yml
    hostname: 192.168.75.102 #修改服务器IP
    
    #https:
    #  # https port for harbor, default is 443  #注释无效配置
    #  port: 443
    #  # The path of cert and key files for nginx
    #  certificate: /your/certificate/path
    #  private_key: /your/private/key/path
  • 安装harbor,前提条件是服务器安装了docker和docker-compose

    #需要耐心等待
    bash install.sh
    ……………………
    
    ✔ ----Harbor has been installed and started successfully.----
  • 验证harbor服务的,服务效果浏览器访问192.168.75.102,默认账号和密码是admin和Harbor12345

  • 创建新仓库名称

  • 镜像上传harbor测试结果

#修改镜像仓库
[root@jenkins ~]# vim  /etc/docker/daemon.json
{
  "insecure-registries":["192.168.11.102:80"]
}
#重新启动服务,在这里重新启动镜像后,其他容器需要重新启动
[root@jenkins ~]# systemctl  restart docker
#给镜像重新打上标签
[root@jenkins ~]# docker tag 2ea870b320a0 192.168.75.102:80/jenkinstest/demohello:v1.0.0
#查看结果
[root@jenkins ~]# docker images
REPOSITORY                                TAG             IMAGE ID       CREATED         SIZE
192.168.75.102:80/jenkinstest/demohello   v1.0.0          2ea870b320a0   17 hours ago    846MB
docker login -u admin --password Harbor12345 http://192.168.75.102:80
#登陆harbor仓库
[root@jenkins ~]#  docker login -u admin --password Harbor12345 http://192.168.75.102:80
#上传镜像到harbor
[root@jenkins ~]# docker push 192.168.75.102:80/jenkinstest/demohello:v1.0.0
The push refers to repository [192.168.75.102:80/jenkinstest/demohello]
  • 登陆harbor查看上传镜像结果

8.2 Jenkins构建镜像推送到harbor

  • 配置Jenkins容器有docker功能

    [root@jenkins ~]# cd /var/run/
    [root@jenkins run]# ll docker.sock
    srw-rw---- 1 root docker 0 Jul 13 09:47 docker.sock
    [root@jenkins run]# chown  root:root docker.sock
    [root@jenkins run]# chmod  o+rw docker.sock
    [root@jenkins run]# ll docker.sock
    srw-rw-rw- 1 root root 0 Jul 13 09:47 docker.sock
    #更改关于jenkins的docker-compose文件
    version: "3.1"
    services:
      jenkins:
        image: jenkins/jenkins:2.413-jdk11
        container_name: jenkins
        ports:
          - 8080:8080
          - 50000:50000
        volumes:
          - ./data/:/var/jenkins_home/
          - /var/run/docker.sock:/var/run/docker.sock
          - /usr/bin/docker:/usr/bin/docker
          - /etc/docker/daemon.json:/etc/docker/daemon.json
     #重新启动Jenkins容器
     [root@jenkins ~]# docker-compose  up -d
    [+] Running 1/1
     ✔ Container jenkins  Started 
     #检查Jenkins容器里面是否有docker环境
     [root@jenkins ~]# docker exec -it jenkins docker version
    Client: Docker Engine - Community
     Version:           24.0.4
    ……………………
  • 配置构建任务自动构建镜像并推送到harbor仓库,执行构建任务,并查看harbor仓库

  • 并查看harbor仓库

8.3 服务部署

  • 在目标服务器编写部署代码
[root@jenkins ~]# vim /usr/bin/deploy.sh
#!/bin/bash
horbar_addr=$1
horbar_repo=$2
project=$3
version=$4
port=$5
imageName=$horbar_addr/$horbar_repo/$project:$version
echo $imageName
containerId=`docker ps -a |grep ${project}|awk '{print $1}'`
echo $containerId
if [ "$containerId" != "" ];then
docker stop $containerId
docker rm -f $containerId
fi
tag=`docker images |grep ${project} |awk '{print $2}'`
echo $tag
if [[ "$tag" =~ "$version" ]];then
docker rmi -f $imageName
fi
docker login -u admin -p Harbor12345 $horbar_addr
docker pull $imageName
docker run -d -p $port:$port --name $project $imageName
echo "SUCCESS"
#给脚本赋予执行权限
[root@jenkins ~]# chmod  a+x /usr/bin/deploy.sh
  • 修改构建任务信息

九、pipeline 集成构建任务

9.1 初识pipeline

  • 创建流水线任务,并测试

  • 执行构建任务

  • 编写Pipeline脚本,构建任务
//所有代码都放到pipeline
pipeline {
    //指定任务在那个集群节点中执行
    agent any
    //声明全局变量,方便后面使用
    environment {
        key = "value"
    }
    stages {
        stage('拉取git仓库代码') {
            steps {
                echo '拉取git仓库代码 - SUCCESS'
            }
        }
        stage('通过maven构建项目') {
            steps {
                echo '通过maven构建项目 - SUCCESS'
            }
        }
        stage('通过SonarQube做代码质量检查') {
            steps {
                echo '通过SonarQube做代码质量检查 - SUCCESS'
            }
        }
        stage('通过Docker制作自定义镜像') {
            steps {
                echo '通过Docker制作自定义镜像 - SUCCESS'
            }
        }
        stage('将自定义镜像推送到Harbor') {
            steps {
                echo '将自定义镜像推送到Harbor - SUCCESS'
            }
        }
        stage('通过Publish Over SSH通知目标服务器') {
            steps {
                echo '通过Publish Over SSH通知目标服务器 - SUCCESS'
            }
        }
    }
}

  • pipeline 集成构建任务编写语法

9.2 编写项目中的pipeline脚本

  • 本项目使用scm编写pipeline文件

在gitlab创建Jenkinsfile

  • 配置jenkins邮箱服务

//所有代码都放到pipeline
pipeline {
    //指定任务在那个集群节点中执行
    agent any
    //声明全局变量,方便后面使用
    environment {
        harborUser = 'admin'
        harborPasswd = 'Harbor12345'
        harborAddress = '192.168.75.102:80'
        harborRepo = 'jenkinstest'
    }
    stages {
        stage('拉取git仓库代码') {
            steps {
               checkout scmGit(branches: [[name: '${tag}']], extensions: [], userRemoteConfigs: [[url: 'http://192.168.75.100:8929/root/demoHello.git']])
            }
        }
        stage('通过maven构建项目') {
            steps {
                sh '/var/jenkins_home/maven/bin/mvn clean package -DskipTests'
                echo '通过maven构建项目 - SUCCESS'
            }
        }
        stage('通过SonarQube做代码质量检查') {
            steps {
                sh '/var/jenkins_home/sonar-scanner/bin/sonar-scanner   -Dsonar.projectname=${JOB_NAME}   -Dsonar.projectKey=${JOB_NAME}  -Dsonar.source=./   -Dsonar.java.binaries=target -Dsonar.login=a0277c64b7c5f6c1e03700fdd9f881eb48c98633'
                echo '通过SonarQube做代码质量检查 - SUCCESS'
            }
        }
        stage('通过Docker制作自定义镜像') {
            steps {
                sh '''mv ./target/*.jar docker/
docker build -t 192.168.75.102:80/jenkinstest/${JOB_NAME}:$tag docker/
docker image prune -f'''
            }
        }
        stage('将自定义镜像推送到Harbor') {
            steps {
                sh '''docker login -u ${harborUser} -p ${harborPasswd} ${harborAddress}
docker push ${harborAddress}/${harborRepo}/${JOB_NAME}:$tag'''
            }
        }
        stage('通过Publish Over SSH通知目标服务器') {
            steps {
                //这边有个坑,默认生成的脚步命令是单引号需要改成双引号
sshPublisher(publishers: [sshPublisherDesc(configName: 'test', transfers: [sshTransfer(cleanRemote: false, excludes: '', execCommand: "deploy.sh  ${harborAddress}  ${harborRepo}  ${JOB_NAME}  $tag  $port", execTimeout: 120000, flatten: false, makeEmptyDirs: false, noDefaultExcludes: false, patternSeparator: '[, ]+', remoteDirectory: '', remoteDirectorySDF: false, removePrefix: '', sourceFiles: '')], usePromotionTimestamp: false, useWorkspaceInPromotion: false, verbose: true)])
            }
        }
        }
        //需要配置jenkin邮箱服务
    post{
        success {
            emailext body: '构建成功', subject: '构建成功', to: '[email protected]'
        }
        failure{
            emailext body: '构建失败', subject: '构建失败', to: '[email protected]'
        }
    }
}

十、 Kubernetes持续集成和持续交付

10.1 搭建 Kubernetes集群

10.2 构建 Kubernetes持续集成和持续交付任务

10.2.1 持续交付任务

  • 编写k8s使用的编排文件pipeline.yml放到gitlab仓库
apiVersion: apps/v1
kind: Deployment
metadata:
  name: pipeline-deployment
  namespace: test
  labels:
    app: pipeline
spec:
  replicas: 3
  selector:
    matchLabels:
      app: pipeline
  template:
    metadata:
      labels:
        app: pipeline
    spec:
      containers:
      - name: pipeline
        image: 192.168.75.102:80/jenkinstest/pipeline:v6
        ports:
        - containerPort: 8081
---
apiVersion: v1
kind: Service
metadata:
  namespace: test
  name: pipeline-deployment
  labels:
    app: pipeline-deployment
spec:
  selector:
    app: pipeline
  ports:
  - port: 8888
    targetPort: 8081
  type: NodePort
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  namespace: test
  name: pipeline-ingress
spec:
  ingressClassName: ingress
  rules:
  - host: bobo.nginx.com
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service:
            name: pipeline-deployment
            port:
              number: 8888

修改Jenkinsfile文件,删除ssh推送任务,

//所有代码都放到pipeline
pipeline {
    //指定任务在那个集群节点中执行
    agent any
    //声明全局变量,方便后面使用
    environment {
        harborUser = 'admin'
        harborPasswd = 'Harbor12345'
        harborAddress = '192.168.75.102:80'
        harborRepo = 'jenkinstest'
    }
    stages {
        stage('拉取git仓库代码') {
            steps {
               checkout scmGit(branches: [[name: '${tag}']], extensions: [], userRemoteConfigs: [[url: 'http://192.168.75.100:8929/root/demoHello.git']])
            }
        }
        stage('通过maven构建项目') {
            steps {
                sh '/var/jenkins_home/maven/bin/mvn clean package -DskipTests'
                echo '通过maven构建项目 - SUCCESS'
            }
        }
        stage('通过SonarQube做代码质量检查') {
            steps {
                sh '/var/jenkins_home/sonar-scanner/bin/sonar-scanner   -Dsonar.projectname=${JOB_NAME}   -Dsonar.projectKey=${JOB_NAME}  -Dsonar.source=./   -Dsonar.java.binaries=target -Dsonar.login=a0277c64b7c5f6c1e03700fdd9f881eb48c98633'
                echo '通过SonarQube做代码质量检查 - SUCCESS'
            }
        }
        stage('通过Docker制作自定义镜像') {
            steps {
                sh '''mv ./target/*.jar docker/
docker build -t 192.168.75.102:80/jenkinstest/${JOB_NAME}:$tag docker/
docker image prune -f'''
            }
        }
        stage('将自定义镜像推送到Harbor') {
            steps {
                sh '''docker login -u ${harborUser} -p ${harborPasswd} ${harborAddress}
docker push ${harborAddress}/${harborRepo}/${JOB_NAME}:$tag'''
            }
        }
        stage('复制pipeline.yml文件到 masternode') {
            steps {
               sshPublisher(publishers: [sshPublisherDesc(configName: 'k8s', transfers: [sshTransfer(cleanRemote: false, excludes: '', execCommand: '', execTimeout: 120000, flatten: false, makeEmptyDirs: false, noDefaultExcludes: false, patternSeparator: '[, ]+', remoteDirectory: '', remoteDirectorySDF: false, removePrefix: '', sourceFiles: 'pipeline.yml')], usePromotionTimestamp: false, useWorkspaceInPromotion: false, verbose: false)])
            }
        }
        }
    post{
        success {
            emailext body: '构建成功', subject: '构建成功', to: '[email protected]'
        }
        failure{
            emailext body: '构建失败', subject: '构建失败', to: '[email protected]'
        }
    }
}
  • 配置新主机在系统配置里面

  • 由于jenkins无法自动输入服务器的密码信息,需要给Jenkins容器添加服务器的免没有登陆

    [root@jenkins controller]# docker exec -it  jenkins /bin/bash
    jenkins@0a06591b1a48:/$ ssh-keygen #一直回车处理
    jenkins@0a06591b1a48:/$ ssh-copy-id [email protected] #需要输入服务器密码账号
  • 给新代码打上v6标签,并构建v6版本任务

    [root@masternode ~]# kubectl  get svc -n test
    NAME                  TYPE       CLUSTER-IP     EXTERNAL-IP   PORT(S)          AGE
    pipeline-deployment   NodePort   10.96.85.191   <none>        8888:32460/TCP   3h5m
    [root@masternode ~]# curl  10.96.85.191:8888/hello
    Hello World v6.0.0

10.2.2 配置持续集成任务

  • Jenkins项目配置

  • GitLab配置

  • 编写构建任务的Jenkinsfile文件,将tag变量改成相关参数,*/master和latest
//所有代码都放到pipeline
pipeline {
    //指定任务在那个集群节点中执行
    agent any
    //声明全局变量,方便后面使用
    environment {
        harborUser = 'admin'
        harborPasswd = 'Harbor12345'
        harborAddress = '192.168.75.102:80'
        harborRepo = 'jenkinstest'
    }
    stages {
        stage('拉取git仓库代码') {
            steps {
               checkout scmGit(branches: [[name: '*/master']], extensions: [], userRemoteConfigs: [[url: 'http://192.168.75.100:8929/root/demoHello.git']])
            }
        }
        stage('通过maven构建项目') {
            steps {
                sh '/var/jenkins_home/maven/bin/mvn clean package -DskipTests'
                echo '通过maven构建项目 - SUCCESS'
            }
        }
        stage('通过SonarQube做代码质量检查') {
            steps {
                sh '/var/jenkins_home/sonar-scanner/bin/sonar-scanner   -Dsonar.projectname=${JOB_NAME}   -Dsonar.projectKey=${JOB_NAME}  -Dsonar.source=./   -Dsonar.java.binaries=target -Dsonar.login=a0277c64b7c5f6c1e03700fdd9f881eb48c98633'
                echo '通过SonarQube做代码质量检查 - SUCCESS'
            }
        }
        stage('通过Docker制作自定义镜像') {
            steps {
                sh '''mv ./target/*.jar docker/
docker build -t 192.168.75.102:80/jenkinstest/${JOB_NAME}:latest docker/
docker image prune -f'''
            }
        }
        stage('将自定义镜像推送到Harbor') {
            steps {
                sh '''docker login -u ${harborUser} -p ${harborPasswd} ${harborAddress}
docker push ${harborAddress}/${harborRepo}/${JOB_NAME}:latest'''
            }
        }
        stage('复制pipeline.yml文件到 masternode') {
            steps {
               sshPublisher(publishers: [sshPublisherDesc(configName: 'k8s', transfers: [sshTransfer(cleanRemote: false, excludes: '', execCommand: '', execTimeout: 120000, flatten: false, makeEmptyDirs: false, noDefaultExcludes: false, patternSeparator: '[, ]+', remoteDirectory: '', remoteDirectorySDF: false, removePrefix: '', sourceFiles: 'pipeline.yml')], usePromotionTimestamp: false, useWorkspaceInPromotion: false, verbose: false)])
            }
        }
    stage('构建看k8s环境任务') {
        steps {
            sh 'ssh [email protected] kubectl apply -f /usr/local/k8s/pipeline.yml'
            }
        }
        }
    post{
        success {
            emailext body: '构建成功', subject: '构建成功', to: '[email protected]'
        }
        failure{
            emailext body: '构建失败', subject: '构建失败', to: '[email protected]'
        }
    }
}
  • 更新pipeline.yml文件
image: 192.168.75.102:80/jenkinstest/pipeline:latest #更改镜像版本号
  • 更改源代码
public String helloWorld() {
       return "Hello World v7.0.0";
   }
  • gitlab上传更新代码,并查看结果
[root@masternode ~]# curl  10.96.85.191:8888/hello
Hello World v7.0.0

十一、需要本课程的资料文件,请关注微信公众号获取,回复“小张DevOps”

支付宝打赏 微信打赏

赞赏是不耍流氓的鼓励

-->