CI/CD介紹

發布流程設計

| 服務器 | IP地址 | 主機名 |
|---|---|---|
| Git/Harbor | 192.168.200.70 | git-harbor |
| Docker | 192.168.200.111 | docker |
| Jenkins | 192.168.200.112 | jenkins |
| 工具 | 版本 |
|---|---|
| CentOS | 7.5_x64 |
| Maven | 3.5 |
| Tomcat | 8 |
| JDK | 1.8 |
| Jenkins | 2.6 |
| Docker CE | 18.03.1 |
cat /etc/redhat-release
uname -r

Jenkins+Docker+Git所有包
鏈接:https://pan.baidu.com/s/10GWHTqAx9E9d1hhJNuI1gw
提取碼:py3b
部署Harbor鏡像倉庫
| 服務器 | IP地址 |
|---|---|
| Git/Harbor | 192.168.200.70 |
創建ca證書
mkdir -p /data/ssl
cd /data/ssl
which openssl
openssl req -newkey rsa:4096 -nodes -sha256 -keyout ca.key -x509 -days 365 -out ca.crt
Generating a 4096 bit RSA private key.................................................++......................................................................................................................++writing new private key to 'ca.key'-----You are about to be asked to enter information that will be incorporatedinto your certificate request.What you are about to enter is what is called a Distinguished Name or a DN.There are quite a few fields but you can leave some blankFor some fields there will be a default value,If you enter '.', the field will be left blank.-----Country Name (2 letter code) [XX]:CNState or Province Name (full name) []:BeijingLocality Name (eg, city) [Default City]:BeijingOrganization Name (eg, company) [Default Company Ltd]:yunjisuanOrganizational Unit Name (eg, section) []:yunjisuanCommon Name (eg, your name or your servers hostname) []:www.yunjisuan.comEmail Address []:

生成證書請求
openssl req -newkey rsa:4096 -nodes -sha256 -keyout www.yunjisuan.com.key -out www.yunjisuan.com.csr
Generating a 4096 bit RSA private key..........................................................++.......................................................................................................................++writing new private key to 'www.yunjisuan.com.key'-----You are about to be asked to enter information that will be incorporatedinto your certificate request.What you are about to enter is what is called a Distinguished Name or a DN.There are quite a few fields but you can leave some blankFor some fields there will be a default value,If you enter '.', the field will be left blank.-----Country Name (2 letter code) [XX]:CNState or Province Name (full name) []:BeijingLocality Name (eg, city) [Default City]:BeijingOrganization Name (eg, company) [Default Company Ltd]:yunjisuanOrganizational Unit Name (eg, section) []:yunjisuanCommon Name (eg, your name or your servers hostname) []:www.yunjisuan.comEmail Address []:Please enter the following 'extra' attributesto be sent with your certificate requestA challenge password []:An optional company name []:

生成注冊表主機的證書
openssl x509 -req -days 365 -in www.yunjisuan.com.csr -CA ca.crt -CAkey ca.key -CAcreateserial -out www.yunjisuan.com.crt
Signature oksubject=/C=CN/ST=Beijing/L=Beijing/O=yunjisuan/OU=yunjisuan/CN=www.yunjisuan.comGetting CA Private Key
ll

信任自簽發的證書
cp www.yunjisuan.com.crt /etc/pki/ca-trust/source/anchors/
update-ca-trust enable
update-ca-trust extract

安裝docker-ce社區版
setenforce 0
yum -y install yum-utils device-mapper-persistent-data lvm2
curl https://download.docker.com/linux/centos/docker-ce.repo -o /etc/yum.repos.d/docker-ce.repo
yum -y install docker-ce
systemctl start docker
systemctl enable docker
docker version


安裝harbor倉庫
mkdir -p /etc/ssl/harbor
cp /data/ssl/www.yunjisuan.com.key /etc/ssl/harbor/
cp /data/ssl/www.yunjisuan.com.crt /etc/ssl/harbor/
wget http://harbor.orientsoft.cn/harbor-v1.5.0/harbor-offline-installer-v1.5.0.tgz
上文有下載包,這里就沒有wget下載。mkdir -p /data/install
cd /data/install
ls
tar xf harbor-offline-installer-v1.5.0.tgz
cd harbor
cp harbor.cfg{,.bak}
vim harbor.cfg
cat -n harbor.cfg | sed -n '7p;11p;23p;24p;68p'
7 hostname = www.yunjisuan.com11 ui_url_protocol = https23 ssl_cert = /etc/ssl/harbor/www.yunjisuan.com.crt24 ssl_cert_key = /etc/ssl/harbor/www.yunjisuan.com.key68 harbor_admin_password = Harbor12345

安裝命令docker-compose(需要1.21版本)
curl -L https://github.com/docker/compose/releases/download/1.21.2/docker-compose-$(uname-s)-$(uname -m) -o /usr/local/bin/docker-compose上文有下載包,這里就沒有下載
cd /usr/local/bin/
ls
chmod +x /usr/local/bin/docker-compose
which docker-compose
docker-compose -version

啟動harbor私有鏡像倉庫
cd /data/install/harbor
./install.sh --with-clair

為其他服務器下發證書,並映射域名
為其他服務器下發證書
scp /data/ssl/www.yunjisuan.com.crt 192.168.200.111:/etc/pki/ca-trust/source/anchors/
scp /data/ssl/www.yunjisuan.com.crt 192.168.200.112:/etc/pki/ca-trust/source/anchors/

在Docker客戶端上(192.168.200.111)
update-ca-trust enable
update-ca-trust extract
vim /etc/hosts
tail -1 /etc/hosts
192.168.200.70 www.yunjisuan.com

在jenkins服務器上(192.168.200.203)
update-ca-trust enable
update-ca-trust extract
vim /etc/hosts
tail -1 /etc/hosts
192.168.200.70 www.yunjisuan.com

部署Git服務器
| 服務器 | IP地址 | 主機名 |
|---|---|---|
| Git/Harbor | 192.168.200.70 | git-harbor |
| Jenkins服務器 | 192.168.200.112 | jenkins |
以下操作在Harbor/Git上(192.168.200.70)
yum -y install git
which git

創建git用戶密碼
useradd git
passwd git
su - git

創建git項目目錄
mkdir solo.git
cd solo.git/
初始化git目錄
git --bare init
ls

以下的操作在Jenkins上(192.168.200.112)
在192.168.200.112上也安裝git模擬項目代碼提交
yum -y install git
which git

創建用於提交的git目錄
mkdir -p /code
cd /code
git clone root@192.168.200.70:/home/git/solo.git
ls

將solo項目的源碼拷貝到git的上傳目錄下(solo源代碼在上文有下載鏈接)
mv ~/solo/* solo/
ls solo/

添加需要提交的文件目標
cd solo
git add .

進行代碼提交
git commit -m "all"
*** Please tell me who you are. #出現這個提示是讓你補充提交信息Rungit config --global user.email "you@example.com" #你的郵箱git config --global user.name "Your Name" #你的名字to set your account's default identity.Omit --global to set the identity only in this repository.fatal: unable to auto-detect email address (got 'root@JenkinsServer.(none)')
git config --global user.email "1123400300@qq.com"
git config --global user.name "Mr.sun"
git commit -m "all" #補充信息后,即可提交成功

提交完代碼之后,需要推送到git服務端
git push origin master --->origin master版本信息

為了最后的solo項目測試,我們需要修改一下solo項目源代碼的某個配置文件
cd /code/solo/src/main/resources
ls
cat -n latke.properties | sed -n '29p;31p'
29 serverHost=localhost31 serverPort=8080

將文件的上邊兩行代碼修改成如下所示
vim latke.properties
cat -n latke.properties | sed -n '29p;31p'
29 serverHost=192.168.200.111 #修改成docker的IP地址31 serverPort=8888

再次進行git版本提交
cd /code/solo/
git add .
git commit -m "latke.properties"
git push origin master

構建業務基礎鏡像(tomcat:v1)
在后邊構建
| 服務器 | IP地址 | 主機名 |
|---|---|---|
| Docker | 192.168.200.111 | docker |
安裝docker
yum -y install yum-utils device-mapper-persistent-data lvm2
curl https://download.docker.com/linux/centos/docker-ce.repo -o /etc/yum.repos.d/docker-ce.repo
yum -y install docker-ce
docker --version


添加docker國內鏡像源
mkdir -p /etc/docker
vim /etc/docker/daemon.json
cat /etc/docker/daemon.json
{"registry-mirrors":[ "https://registry.docker-cn.com" ]}
systemctl daemon-reload
systemctl restart docker

部署jdk環境(不需要添加環境變量)
ls
tar xf jdk-8u45-linux-x64.tar.gz -C /usr/local/

cd /usr/local
ls
ln -s jdk1.8.0_45 jdk

Jenkins安裝
| 服務器 | IP地址 | 主機名 |
|---|---|---|
| Jenkins服務器 | 192.168.200.112 | jenkins |
安裝docker-ce環境
yum -y install yum-utils device-mapper-persistent-data lvm2
curl https://download.docker.com/linux/centos/docker-ce.repo -o /etc/yum.repos.d/docker-ce.repo
yum -y install docker-ce
mkdir -p /etc/docker
vim /etc/docker/daemon.json
cat /etc/docker/daemon.json
{"registry-mirrors":[ "https://registry.docker-cn.com" ]}
systemctl daemon-reload
systemctl restart docker


安裝JDK環境(因為是要用在容器中,因此宿主機不配PATH)
ls
tar xf jdk-8u45-linux-x64.tar.gz -C /usr/local/

cd /usr/local
ls
ln -s jdk1.8.0_45 jdk

安裝maven-3.5.0
ls
tar xf apache-maven-3.5.0-bin.tar.gz -C /usr/local/

cd /usr/local
ls
ln -s apache-maven-3.5.0 maven

創建jenkins鏡像的Dockerfile
沒有wget命令需要提前yum安裝
mkdir -p dockerfile/jenkins
cd dockerfile/jenkins
vim Dockerfile
cat Dockerfile
FROM jenkinsUSER rootRUN echo "" > /etc/apt/sources.list.d/jessie-backports.list && \wget http://mirrors.163.com/.help/sources.list.jessie -O /etc/apt/sources.listRUN apt-get update && apt-get install -y git libltdl-dev

創建jenkins鏡像
docker build -t jenkins:v1 .
docker images

由於我們是在鏡像中去構建Jenkins的,所以
jenkins容器的數據目錄我們需要從宿主機上掛載(避免容器數據丟失)
jenkins的運行需要jdk環境,所以我們直接掛載宿主機上的jdk
jenkins構建java代碼需要maven支持,所以我們直接掛載宿主機上的maven
Jenkins需要docker支持
Jenkins需要免交互拉取git代碼,因此掛載本地的ssh密鑰
創建jenkins數據目錄
mkdir -p /var/jenkins_home

進行ssh免密鑰交互驗證
ssh-keygen --->一律回車即可
ssh-copy-id git@192.168.200.70

進行免交互測試
ssh git@192.168.200.70

啟動jenkins容器
docker run -dit --name jenkins -p 8080:8080 -v /var/jenkins_home/:/var/jenkins_home/ -v /usr/local/apache-maven-3.5.0:/usr/local/maven -v /usr/local/jdk1.8.0_45:/usr/local/jdk -v /var/run/docker.sock:/var/run/docker.sock -v /usr/bin/docker:/usr/bin/docker -v ~/.ssh:/root/.ssh jenkins:v1

利用瀏覽器訪問Jenkins容器

docker exec jenkins cat /var/jenkins_home/secrets/initialAdminPassword
c7e4ae00fd5941d6b20f1e45ab6835b6 #這就是密碼,輸入到瀏覽器里

選擇所有插件后,直接點install即可


我們現在構建一個可以運行solo代碼的tomcat鏡像
mkdir -p /root/dockerfile/solo
cd /root/dockerfile/solo
vim Dockerfile
cat Dockerfile
FROM centos:7MAINTAINER www.yunjisuan.comRUN yum install unzip iproute -yENV JAVA_HOME /usr/local/jdkADD apache-tomcat-8.0.46.tar.gz /usr/localRUN mv /usr/local/apache-tomcat-8.0.46 /usr/local/tomcatWORKDIR /usr/local/tomcatEXPOSE 8080ENTRYPOINT ["./bin/catalina.sh", "run"]

ls

構建鏡像
docker build -t tomcat:v1 .
docker images

登陸harbor私有倉庫
docker login -uadmin -pHarbor12345 www.yunjisuan.com

推送鏡像到harbor倉庫(如果推送失敗請查看證書驗證或者docker是否登陸)
docker images
docker tag tomcat:v1 www.yunjisuan.com/library/tomcat:v1
docker push www.yunjisuan.com/library/tomcat:v1


Jenkins基本配置
用戶名:admin 密碼:linyaonie

設定全局配置




設定ssh連接憑據
jenkins連接Docker測試服務器免交互驗證
ssh-copy-id root@192.168.200.111
ssh root@192.168.200.111

在Jenkins的Web界面上添加憑據



cat ~/.ssh/id_rsa #就是把這些內容復制



Jenkins創建項目
我們先開始一個新的任務


圖片說明

圖片說明
到這里我們先來測試一下maven構建java代碼的效果
點擊solo_blog項目的立刻構建,查看構建信息

在Jenkins服務器上查看構建后的結果
cd /var/jenkins_home/workspace/solo_blog/target
ls
ll solo.war --->這就是構建出來的war包
2.[root@JenkinsServer target]# pwd3./var/jenkins_home/workspace/solo_blog/target4.[root@JenkinsServer target]# ls5.classes generated-test-sources maven-status solo_h2_test surefire-reports6.generated-sources maven-archiver solo solo.war test-classes7.[root@JenkinsServer target]# ll solo.war #這就是構建出來的war包8.-rw-r--r-- 1 root root 43037193 7月 25 22:12 solo.war
通過腳本將war包封裝進一個tomcat的鏡像中,然后推送到harbor
所以利用maven構建java的源代碼實際上就是生成可以在tomcat等容器中運行的war包
現在我們重新修改一下項目的配置,增加POST Steps(構建之后的操作)
其實,構建之后,我們只需要通過腳本將war包封裝進一個tomcat的鏡像中,然后推送到harbor里即可。

這就是需要添加進去的腳本內容
cd $WORKSPACE--->這是jenkins的可用變量,具體可以在上圖下邊查看
cd $WORKSPACEcat > Dockerfile << FOFFROM www.yunjisuan.com/library/tomcat:v1MAINTAINER www.yunjisuan.comCOPY target/solo.war /tmp/ROOT.warRUN rm -rf /usr/local/tomcat/webapps/* && \unzip /tmp/ROOT.war -d /usr/local/tomcat/webapps/ROOT && \rm -f /tmp/ROOT.warWORKDIR /usr/local/tomcatEXPOSE 8080ENTRYPOINT ["./bin/catalina.sh","run"]FOFdocker build -t www.yunjisuan.com/library/solo:v1 .docker login -uadmin -pHarbor12345 www.yunjisuan.comdocker push www.yunjisuan.com/library/solo:v1
然后我們再次進行構建查看

至此我們就完成了以下幾步
git拉取java的solo項目源代碼
maven構建java的solo項目war包
將war包封裝成tomcat的容器啟動鏡像
將鏡像上傳harbor私有鏡像倉庫
我們還需要能夠直接部署到遠程測試主機
(192.168.200.111)上,因此我們繼續設置

在遠程主機(Docker測試服務器)執行的腳本如下
docker rm -f solo #清理舊的solo容器進程docker rmi -f www.yunjisuan.com/library/solo:v1 #清理舊的solo:v1鏡像(不清理就不拉取鏡像了)docker login -uadmin -pHarbor12345 www.yunjisuan.comdocker run -d --name solo -p 8888:8080 -v /usr/local/jdk1.8.0_45/:/usr/local/jdk www.yunjisuan.com/library/solo:v1
再次進行構建,並在docker主機上查看構建結果
docker images --->docker測試服務器上有鏡像了
2.REPOSITORY TAG IMAGE ID CREATED SIZE3.www.yunjisuan.com/library/solo v1 e1b0d010c11b 11 minutes ago 408MB4.redis latest f06a5773f01e 8 days ago 83.4MB5.centos latest 49f7960eb7e4 7 weeks ago 200MB
docker ps -a --->啟動容器進程了
7.CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES8.c4dba5567fd5 www.yunjisuan.com/library/solo:v1 "./bin/catalina.sh r…" 11 minutes ago Up 11 minutes 0.0.0.0:8888->8080/tcp solo
我們通過瀏覽器訪問

