第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)

第1集,环境搭建

第2集,LNMP项目准备

第3集,WebHook触发mvn打包

第4集,SonarQube实现CodeReview

第5集,build image

第7集,模拟版本更新,在测试环境验证

第8集,部署到生产环境

第9集,流水线部署到测试环境

一、准备一键式部署包

目录结构如下
在这里插入图片描述

1.部署脚本autoinstall.sh

#!/bin/bash
#AUTHOR:anqixiang
#DATE:2020-03-23
#MODIFY:
#FUNCTION:docker-compose部署LNMP
#VERSION:V1.0
#SYSTEM:Ubuntu 16  RedHat7.2/7.4  CentOS7.2/7.4  SUSE12 SP3(启动docker-compose系统会重启)

export LC_ALL=en_US.UTF-8
[ `whoami` != "root" ] && echo "######## Please Use root Install......" && exit 71                   
current_dir=$(cd `dirname $0` && pwd)   #当前工作目录/home/secneo/install_yyjg
data_dir=/data     #数据目录/data

source ${current_dir}/function		#加载工具库

######################工具函数######################
#DISCRIPTION:设置debug值且范围为1-9开启调试;step=1为出现错误被挂起;step=2为每次调用函数后都会被挂起
Alert(){    
    local ret_code=$?
    debug=0
    step=0
    if [ -z "${debug}" ] || [ "${debug}" -eq 0 ];then
        return
    fi
    if [ "${ret_code}" -ne 0 ];then
        cecho 31 "Warn:$* failed return ${ret_code}" >&2
        [ "${debug}" -gt 9 ] && exit "${ret_code}"
        [ "${step}" -eq 1 ] && {
            echo "Press [Enter] to continue" >&2;read x
        }
    else
        cecho 96 "############ $* excute is success..."
    fi
    [ "${step}" -eq 2 ] && {
        echo "Press [Enter] to continue" >&2;read x
    }
}

######################功能函数######################
#检测系统
Detect_Os(){
    Check_Os
    system_flag=0		#用作系统标识,表示为ubuntu系统
    if echo ${os_version} |egrep -i 'red|centos' &>/dev/null;then
	system_flag=1		#表示redhat或者CentOS
    elif echo ${os_version} |grep -i 'suse' &>/dev/null;then
	system_flag=2		#表示SUSE系统
    fi	
}

#初始化系统环境
Init_System(){
    echo "############ Init_System..."
    umask 0022
    sed -i "s/%sudo\tALL=(ALL:ALL) ALL/%sudo\tALL=(ALL:ALL) NOPASSWD:ALL/" /etc/sudoers
    cp /usr/share/zoneinfo/Asia/Shanghai  /etc/localtime
    hwclock -w
    if [ ${system_flag} -eq 0 ];then 
        ufw disable &>/dev/null         #关闭防火墙
    elif [ ${system_flag} -eq 1 ];then
	Security_Conf_Redhat		#关闭防火墙,禁用selinux
    else
	systemctl disable SuSEfirewall2.service
	systemctl stop SuSEfirewall2.service
    fi
    Alert Init_System
}

#安装docker
Install_Docker(){
    echo "############ Install_Docker..."
    if ! which docker &>/dev/null;then
        [ ! -f ${current_dir}/install_docker.sh ] && cecho 31 "install_docker.sh不存在" && exit 71
	sed -i "/ExecStart/c ExecStart=/usr/bin/dockerd --graph ${data_dir}/docker_dir -H unix://var/run/docker.sock" ${current_dir}/install_docker.sh	#设置doker存储路径为${data_dir}/docker
        /bin/bash ${current_dir}/install_docker.sh
    else
        cecho 96 "docker已安装"
    fi
    Alert Install_Docker
}

#安装docker-compose
Install_Docker_compose(){
    echo "############ Install_Docker_compose..."
    [ ! -f ${current_dir}/docker-compose ] && cecho 31 "docker-compose不存在" && exit 71
    chmod +x ${current_dir}/docker-compose
    \cp ${current_dir}/docker-compose /usr/bin/
    if ! /usr/bin/docker-compose -v;then
	cecho 31 "docker-compose安装失败" && exit 71
    fi
    Alert Install_Docker-compose
}

#安装工具(mysql-client,lrzsz,unzip,dos2unix)
Install_Kits(){
    echo "############ Install_Kits..."
    if [ ${system_flag} -eq 0 ];then
        dpkg -i ${current_dir}/debs/*.deb
    elif [ ${system_flag} -eq 1 ];then
	rpm -ivh ${current_dir}/rpms/*.rpm --nodeps --force
    else
	rpm -ivh ${current_dir}/rpms/*.rpm --nodeps --force
    fi
    Alert Install_Kits
}

#初始化数据卷
Deploy_Init_Data(){
    echo "############ Deploy_Init_Data..."
    [ ! -d ${data_dir}/docker ] && mkdir -pv ${data_dir}/docker
    echo "tar xf ${current_dir}/init_data.tgz -C ${data_dir}/docker/......"
    tar xf ${current_dir}/init_data.tgz -C ${data_dir}/docker/
    Alert Deploy_Init_Date
}

#导入镜像
#如果在公司,去私有仓库pull镜像
Import_Images(){
    echo "############ Import_Images..."
    repository_ip=172.16.38.202
    repository_port=8010
    if  curl http://${repository_ip}:${repository_port}/v2/_catalog &>/dev/null;then
        Docker_Insecure
    else
        cd $(dirname ${current_dir})
        [ ! -f docker_images.tgz ] && cecho 31 "docker_images.tgz不存在" && exit 71
        echo "tar xvf docker_images.tgz......"
        tar xvf docker_images.tgz 
        for i in $(ls docker_images/)
        do
            docker load < docker_images/${i}
        done
        rm -rf  docker_images/
    fi
    Alert Import_Images
}

#启动服务
Start_Service(){
    echo "############ Start_Service..."
    cd ${current_dir}
    sed -i "/\/data\// s#/data/#${data_dir}/#" docker-compose.yml
    /usr/bin/docker-compose up -d
    Alert Start_Service
}

#设置静态IP(ubuntu系统)
Config_Ip(){
    echo "############ Config_Ip..."
    if [ ${system_flag} -eq 0 ];then
	CONFIG_IP_UBUNTU
    elif [ ${system_flag} -eq 1 ];then
	CONFIG_IP_REDHAT
    else
        CONFIG_IP_SUSE
    fi

    Alert Config_Ip
}

Excute_All(){
    Init_System
    Install_Docker
    Install_Docker_compose
    Install_Kits
    Deploy_Init_Data
    Import_Images
    Start_Service
    Config_Ip
    cecho 96 "部署完成,访问地址:http://${IP}/wordpress"
}

#传入镜像名,修改docker-compose.yml文件,实现镜像版本的控制
Modify_Yml(){
    compose_conf="${current_dir}/docker-compose.yml"
    [ ! -f ${compose_conf}.bak ] && cp ${compose_conf}{,.bak} 
    for i in $@
    do
	if [ "x${i}" == "x-v" ];then
		continue
	fi
	image_name=$(echo ${i%:*})	#提取镜像的名字
	tag_name=$(echo ${i##*:})	#提取镜像的tag
        case ${image_name} in
	    #sed -ri "/aptsource_bg_aptsource/ s#^(.{11})(.*)#\1${i}#" ${compose_conf};;
	nginx-php-fpm)
	    sed -ri "/nginx-php-fpm/ s#^(.*)(:)(.*)#\1\2${tag_name}#" ${compose_conf};;
	*)
	    cecho 31 "Invalid option:bash `basename $0` [-h]"
	esac
    done
    dos2unix ${compose_conf}
}

#帮助信息
help(){
	cat << EOF
optional arguments
    -h:		查看帮助
    -c:		
	system	初始化系统
	docker	安装docker
	compose	安装docker-compose
	kit	安装基础工具
	data	部署数据卷
	image	导入镜像
	start	启动服务
	ip	配置静态IP
	reset	回滚操作(删除所有数据,慎用)
    -v:
	172.16.38.202:8010/lnmp/nginx-php-fpm:ver1.0_20200323  	#镜像名
EXAMPLE:
	sudo ./autoinstall.sh -v 172.16.38.202:8010/lnmp/nginx-php-fpm:ver1.0_20200323
	sudo ./autoinstall.sh	#全部安装
	sudo ./autoinstall.sh -c system
EOF
}

######################主函数######################
Detect_Os
if [ $# -eq 0 ];then
    Excute_All
elif [ "x$1" == "x-c" -a "$#" -eq 2 ];then
    case $2 in
    system)
	Init_System;;
    docker)
	Install_Docker;;
    compose)
	Install_Docker_compose;;
    kit)
	Install_Kits;;
    data)
	Deploy_Init_Data;;
    image)
	Import_Images;;
    start)
	Start_Service;;
    ip)
	Config_Ip;;
    reset)
	Delete_Docker && exit 0;;
    *)
	cecho 31 "Invalid option:sudo ./`basename $0` [-h]" 
    esac
elif [ "x$1" == "x-h" ];then
    help
elif [ "x$1" == "x-v" -a "$#" -gt 1 ];then
    Modify_Yml $@
else
    help && exit 71
fi

2.function功能函数

#!/bin/bash
#AUTHOR:anqixiang
#VERSION:1.1.0
#DATE:2020-02-06
#MODIFY:
#FUNCTION:

cecho(){
	echo -e "\033[$1m$2\033[0m"
}

#检测操作系统
Check_Os() {
    local os_flag=false
    if [ -e /etc/redhat-release ]; then        
        os_flag=true
        os_version=$(cat /etc/redhat-release)
        cecho 92 "操作系统为: ${os_version}"       
    fi

    if [ "${os_flag}" == "false" ] && [ -e /etc/issue ]; then        
        if [ `grep -i 'Ubuntu' /etc/issue|wc -l` == '1' ]; then
            os_flag=true
            os_name=$(cat /etc/os-release |grep "^NAME" |awk -F'"' '{print $2}')
	    os_version="${os_name} $(cat /etc/os-release |grep "^VERSION=" |awk -F'"' '{print $2}')"
            cecho 92 "操作系统为: ${os_version}"
        fi       
    fi

    if [ "${os_flag}" == "false" ] && [ -e /etc/issue ]; then
        suse_flag=`cat /etc/issue | grep 'SUSE Linux Enterprise Server 12 SP3'|wc -l`
        if [ "${suse_flag}" == "1" ]; then
            os_flag=true
            os_version="SUSE12 SP3"
            cecho 92 "操作系统为: ${os_version}"
        fi
    fi
}

#关闭防火墙,禁用selinux(RedHat系列)
Security_Conf_Redhat(){
   systemctl disable firewalld  &>/dev/null
   systemctl stop firewalld &>/dev/null
   local selinux_mode=$(grep '^SELINUX=' /etc/selinux/config |awk -F'=' '{print $2}')
   if [ ${selinux_mode} != "disabled" ];then
      setenforce 0
      sed -i '/^SELINUX=/c SELINUX=disabled' /etc/selinux/config
      cecho 92 "selinux需重启系统才能生效"
   fi
}

#配置docker信任私有仓库
Docker_Insecure(){
    local user=admin
    local pwd=admin
    [ ! -f /etc/docker/daemon.json.bak ] && cp /etc/docker/daemon.json{,.bak}
    tee /etc/docker/daemon.json << EOF
{
    "insecure-registries": ["${repository_ip}:${repository_port}"]
}
EOF
systemctl restart docker
    docker login http://${repository_ip}:${repository_port} -u ${user} -p ${pwd} &>/dev/null
    [ "$?" -ne 0 ] && cecho 31 "docker登陆失败" && exit 71
    return 0
}

#设置静态IP
CONFIG_IP_UBUNTU(){
    IP=`ip addr |awk '/inet /' |sed -n '2p' |awk -F' ' '{print $2}' |awk -F'/' '{print $1}'`
    MASK=`ifconfig  | sed -n 2p | awk -F ':' '{print $4}'`
    GATEWAY=`route | grep 'default' | awk '{print $2}'`
    INNETO=` ip addr  | awk  -F '^2:' '{print $2}' |awk  -F ':' '{print $1}'  | awk NF|awk '{sub("^ *","");sub(" *$","");print}'  |sed -n 1p`    
    INNETW=`ip addr  | awk  -F '^3:' '{print $2}' |awk  -F ':' '{print $1}'  | awk NF|awk '{sub("^ *","");sub(" *$","");print}'  |sed -n 1p`
    local net_name1=$(echo ${INNETO%%[0-9]*})		#截取网卡非数字部分,如eth
    local net_name2=$(echo ${INNETW%%[0-9]*})  
if ! egrep '\bstatic\b' /etc/network/interfaces &>/dev/null;then
    cp -r /etc/network/interfaces /etc/network/interfaces-backup
    cat >/etc/network/interfaces<> /etc/network/interfaces </dev/null;then
        cat >> /etc/network/interfaces </dev/null;then
        [ ! -f ${eth_conf}.bak ] && cp ${eth_conf}{,.bak}        
        sed -i '/BOOTPROTO/ s/dhcp/static/' ${eth_conf}
        sed -i "/BOOTPROTO/a GATEWAY=${GATEWAY}" ${eth_conf}
        sed -i "/BOOTPROTO/a NETMASK=255.255.255.0" ${eth_conf}
        sed -i "/BOOTPROTO/a IPADDR=${IP}" ${eth_conf}
        boot_value=$(grep '^ONBOOT' ${eth_conf} |awk -F'"' '{print $2}')
    if [ ${boot_value} != "yes" ];then
    	sed -i '/ONBOOT/s /no/yes/' ${eth_conf}
    fi
	service network restart
	[ ! -f /etc/resolv.conf.bak ] && cp /etc/resolv.conf{,.bak}
        echo "nameserver 223.5.5.5" > /etc/resolv.conf
    else
      echo "already config static IP"
    fi
}

CONFIG_IP_SUSE(){
    #提取IP地址和网关
    IP=`ip addr |awk '/inet /' |sed -n '2p' |awk -F' ' '{print $2}' |awk -F'/' '{print $1}'`
    #MASK=`ifconfig |grep 'inet '|grep -v '127.0.0.1'|awk '{print $4}'`
    GATEWAY=`route -n |sed -n '3p'|awk '{print $2}'`
    INNETO=`ip addr  | awk  -F '^2:' '{print $2}' |awk  -F ':' '{print $1}'  | awk NF|awk '{sub("^ *","");sub(" *$","");print}'  |sed -n 1p`
    INNETW=`ip addr  | awk  -F '^3:' '{print $2}' |awk  -F ':' '{print $1}'  | awk NF|awk '{sub("^ *","");sub(" *$","");print}'  |sed -n 1p`
    local eth_conf=/etc/sysconfig/network/ifcfg-${INNETO}
    if grep "dhcp" ${eth_conf} &>/dev/null;then
        [ ! -f ${eth_conf}.bak ] && cp ${eth_conf}{,.bak}
        cat > ${eth_conf} << EOF
BOOTPROTO='static'
IPADDR=${IP}
NETMASK=255.255.255.0
STARTMODE='auto'
EOF
        [ ! -f /etc/sysconfig/network/routes.bak ] && cp /etc/sysconfig/network/routes{,.bak}
        echo "default ${GATEWAY}" > /etc/sysconfig/network/routes
	service network restart
    else
      echo "already config static IP"
    fi
}

Delete_Docker(){
    cd ${current_dir}
    /usr/bin/docker-compose down
    docker system prune -a -f
    systemctl stop docker
    rm -rf ${data_dir}
    [ ! -d /usr/bin.bak ] && cp -rp /usr/bin{,.bak}
    rm -rf /usr/bin/docker*
    rm -rf /etc/systemd/system/docker.service
}

3.安装Docker

docker-18.06.3-ce.tgz百度网盘地址:

链接:https://pan.baidu.com/s/1IYKIpqlrsjrxRlqXkpcGTQ 
提取码:kmkm

install_docker.sh脚本【默认路径为/data/docker_dir】

#!/bin/bash

#setup
echo "######install docker......"
tar zxf  docker-18.06.3-ce.tgz && mv docker/* /usr/bin/ && rm -rf docker/

#systemd config
cat >/etc/systemd/system/docker.service <<-EOF
[Unit]
Description=Docker Application Container Engine
Documentation=https://docs.docker.com
After=network-online.target firewalld.service
Wants=network-online.target

[Service]
Type=notify
# the default is not to use systemd for cgroups because the delegate issues still
# exists and systemd currently does not support the cgroup feature set required
# for containers run by docker
ExecStart=/usr/bin/dockerd --graph /data/docker_dir -H unix://var/run/docker.sock
ExecReload=/bin/kill -s HUP $MAINPID
# Having non-zero Limit*s causes performance problems due to accounting overhead
# in the kernel. We recommend using cgroups to do container-local accounting.
LimitNOFILE=infinity
LimitNPROC=infinity
LimitCORE=infinity
# Uncomment TasksMax if your systemd version supports it.
# Only systemd 226 and above support this version.
#TasksMax=infinity
TimeoutStartSec=0
# set delegate yes so that systemd does not reset the cgroups of docker containers
Delegate=yes
# kill only the docker process, not all processes in the cgroup
KillMode=process
# restart the docker process if it exits prematurely
Restart=on-failure
StartLimitBurst=3
StartLimitInterval=60s

[Install]
WantedBy=multi-user.target
EOF

#start
chmod +x /etc/systemd/system/docker.service
systemctl daemon-reload && systemctl start docker && systemctl enable docker.service

#testing
docker -v && echo "######docker install success!!!"

4.debs和rpms下是一些常用包,如lrzsz、dos2unix

在这里插入图片描述

5.docker-compose二进制包

curl -L "https://github.com/docker/compose/releases/download/1.25.0/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose

6.README.txt

#注意事项
    1.如果/分区不是最大,需要修改脚本data_dir变量的值,或者做软链接
    2../autoinstall.sh -h  查看帮助
#执行脚本
./autoinstall.sh

7.docker-compose.yml和init_data.tgz从gitlab上拿

yum -y install git
git clone http://172.16.38.31/root/dev_lnmp.git

二、在Jenkins机器上准备habor_taglist.sh脚本,获取habor仓库的镜像tag,自定义镜像版本

1.脚本内容

#!/bin/bash
Username="admin"
Passwd="admin"
HaborUrl="http://172.16.38.202:8010"
RepoName=$1
Ttoken=`curl -iksL -X GET -u ${Username}:${Passwd} ${HaborUrl}/service/token?account=${Username}\&service=harbor-registry\&scope=repository:${RepoName}:pull --insecure|grep "token" |awk -F '"' '{print $4}'`
Llist=`curl -ksL -X GET -H "Content-Type: application/json" -H "Authorization: Bearer $Ttoken" ${HaborUrl}/v2/${RepoName}/tags/list|awk -F '[' '{print $2}'|awk -F ']' '{print $1}'|sed 's/"//g'`
echo $Llist|sed 's/,/\n/g' |sort -rn

2.拷贝到Jenkins容器里面

docker cp habor_taglist.sh jenkins:.

3.执行效果

docker exec -it jenkins bash
./habor_taglist.sh lnmp/nginx-php-fpm

在这里插入图片描述

三、在172.16.38.210部署Selenium

Docker+Selenium+Jenkins 实现web自动化测试

sele.py脚本内容:

#!/usr/bin/env python3
# -*- coding:utf-8 -*-

from selenium import webdriver

selenium_url = "http://172.16.38.210:4444/wd/hub"               #selenium的访问地址
access_url = "http://172.16.38.165/wordpress"                           #测试地址

chrome_capabilities ={
    "browserName": "chrome",
    "version": "",
    "platform": "ANY",
    "javascriptEnabled": True,
}

browser = webdriver.Remote(selenium_url, desired_capabilities=chrome_capabilities)
browser.get(access_url)
result = str(browser.get_screenshot_as_base64())
#print(result)
if result[-1] != "C":                   #如果访问成功最后一位的值是"="号
    print("访问失败")
    browser.quit()
    exit(1)
print("访问成功")
browser.quit()
exit(0)

四、Jenkins配置

1.添加测试机器的SSH remote hosts

第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第1张图片
第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第2张图片

2.添加Selenium机器的SSH remote hosts

添加凭据
第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第3张图片
第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第4张图片
第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第5张图片
第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第6张图片

3.安装Active Choices插件,用于参数化构建

在这里插入图片描述

4.创建item

第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第7张图片
第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第8张图片

Groovy Script脚本内容:"/bin/bash  /habor_taglist.sh lnmp/nginx-php-fpm".execute().text.readLines()

第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第9张图片
部署命令:

cd /root/install_lnmp  &&  ./autoinstall.sh -c reset
cd /root/dev_lnmp && git pull
\cp /root/dev_lnmp/docker-compose.yml  /root/install_lnmp/
\cp /root/dev_lnmp/init_data.tgz   /root/install_lnmp/

cd /root/install_lnmp/
./autoinstall.sh -v "nginx-php-fpm:${nginx}"
./autoinstall.sh

第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第10张图片

5.执行构建

第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第11张图片

6.WEB访问

第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第12张图片
第6集(GItlab+Jenkins+SonarQube+Docker+Harbor+Selenium实现CI/CD之部署到测试环境,Selenium自动测试)_第13张图片

你可能感兴趣的:(CI/CD,项目)