springboot集成docker實現自動化構建鏡像說明


springboot集成docker實現自動化構建鏡像說明

  • 文檔說明

    該文檔僅包括通過配置springboot、docker、jenkins、git、appollo等實現持續構建,持續發布的功能,不包括各個組件使用細節的講解。

  • 環境說明

    name version desc
    spring boot 2.0.2.RELEASE spring boot
    docker 1.13.1 docker
    harbor 1.7.0 鏡像倉庫
    jenkinsci/blueocean 1.9.0 jenkins的blueocean工具
    maven 3-alpine maven
    gitlab 10.2.3 gitlab
  • 自動化構建的構想圖

 

 

  • springboot配置文件

    • 包括測試服和正式服兩套服務,所以需要添加兩套配置文本
    • resources下面添加application-test.properties文本,內容同測試服的配置。
    • resources下面添加application-prod.properties文本,內容同slave10的配置。
    • 對於testprod的指定通過jvm參數 -Dspring.profiles.active=test
  • 日志配置

    • 日志文件保存地址統一為/var/log/jenkinsci/zsm-eprofile/eprofile.2019-01-02.log
    • 將鏡像的/var/log/jenkinsci/zsm-eprofile掛載到宿主機上對應的目錄/var/log/jenkinsci/zsm-eprofile。這樣方便隨時對日志監控。
    • logback配置示例 <property name="LOG_HOME" value="/var/log/jenkinsci/zsm-eprofile/logs" />
  • pom打包方式修改

    • pombuild下面將打包方式修改為如下

      <properties>
              <docker.image.prefix>bigdata-test.server.com</docker.image.prefix>
      </properties>
      <plugins>
          <!--這個插件是將所有的包打在一起-->
          <plugin>
              <groupId>org.springframework.boot</groupId>
              <artifactId>spring-boot-maven-plugin</artifactId>
          </plugin>
          <plugin>
              <!-- 這個插件主要是對打的包解壓到dependency目錄下 -->
               <groupId>org.apache.maven.plugins</groupId>
               <artifactId>maven-dependency-plugin</artifactId>
               <executions>
                   <execution>
                       <id>unpack</id>
                       <phase>package</phase>
                       <goals>
                           <goal>unpack</goal>
                       </goals>
                       <configuration>
                           <artifactItems>
                               <artifactItem>
                                   <groupId>${project.groupId}</groupId>
                                   <artifactId>${project.artifactId}</artifactId>
                                   <version>${project.version}</version>
                               </artifactItem>
                           </artifactItems>
                       </configuration>
                   </execution>
               </executions>
          </plugin>
          <!-- 根據 dockerfile 構建鏡像的mvn插件 -->
          <plugin>
              <groupId>com.spotify</groupId>
              <artifactId>dockerfile-maven-plugin</artifactId>
              <version>1.4.9</version>
              <configuration>
                  <!-- 鏡像名 -->
                  <repository>${docker.image.prefix}/${project.artifactId}</repository>
                  <!-- tag:默認使用當前版本 -->
                  <tag>${project.version}</tag>
              </configuration>
          </plugin>
      </plugins>

       

    • 注意:如果在build標簽下面有下面的配置,需要刪除或者其他處理,要保證配置文件都能夠打包到jar里面

      <resources>
          <resource>
              <directory>src/main/java</directory>
              <includes>
                  <include>**/**</include>
              </includes>
          </resource>
      </resources>

       

  • 在打包的pom文件同級目錄下創建Dockerfile文件

    • Dockerfile內容

      ##FROM指定依賴jdk8這個鏡像,VOLUME指定其掛載目錄
      FROM openjdk:8-jdk-alpine
      VOLUME /tmp
      ##將dependency下面的內容拷貝到容器中
      ARG DEPENDENCY=target/dependency
      COPY ${DEPENDENCY}/BOOT-INF/lib /app/lib
      COPY ${DEPENDENCY}/META-INF /app/META-INF
      COPY ${DEPENDENCY}/BOOT-INF/classes /app
      ##容器啟動時通過PARAMS指定jvm參數
      ENV PARAMS=""
      ## apk源
      RUN data="" \
      && sed -i 's/http:\/\/dl-cdn.alpinelinux.org\/alpine\//'"http:\/\/hub-mirror.c.163.com\/alpine\/"'/g' /etc/apk/repositories
      ## 字體包
      RUN set -xe \
      && apk --update add ttf-dejavu fontconfig
      ## 容器啟動時執行的命令
      ENTRYPOINT ["sh","-c","java -cp app:app/lib/* $PARAMS com.zsm.test.Application"]
       
    • 說明

      上面是一種的構建鏡像的方式:這種方式是將jar解壓之后分別拷貝lib和class到容器中,這種方式能夠靈活的對歷史版本鏡像進行配置修改等操作,方便鏡像在不同服務器之間的遷移。還有另外一種,直接將整個jar拷貝到容器中:這種方式構建簡單,但是將配置打包到jar里面,不方便對配置的修改。com.zsm.test.TestImageApplication每個項目對應的主類不一樣,需要進行修改。

    • dockerfile命令詳解

  • 在打包的pom文件同級目錄下創建Jenkinsfile

    • Jenkinsfile內容

      pipeline {
          parameters {
              booleanParam(name:'UPDATE_FORMUL', defaultValue:false,description:'默認false:不更新正式服; true:更新正式服')
              booleanParam(name:'NOT_SKIP_BUILD', defaultValue:true, description:'默認true:構建新的鏡像;false:跳過鏡像構建')
          }
          environment {
              BITBUCKET_COMMON_CREDS = credentials('docker-registry-up')
              RegistryName = 'bigdata-test.server.com'
              ImageName = 'test.zsm.com/enterprise-image'
              ImageTag = '1.0.1'
          }
          agent any
          stages {
              stage('Build') {
                  when {
                      expression { return params.NOT_SKIP_BUILD }
                  }
                  agent {
                      docker {
                          image 'maven:3-alpine'
                          args '-v /root/.m2:/root/.m2'
                      }
                  }
                  steps {
                      echo '開始mvn構建鏡像...'
                      sh 'cd .'
                      sh 'mvn -B -DskipTests clean package dockerfile:build'
                      echo '鏡像構建完成!'
                  }
              }
              stage('Push') {
                  when {
                      expression { return params.NOT_SKIP_BUILD }
                  }
                  steps {
                      echo 'push鏡像到私有倉庫...'
                      sh 'docker login -u $BITBUCKET_COMMON_CREDS_USR -p $BITBUCKET_COMMON_CREDS_PSW $RegistryName'
                      sh 'docker tag $RegistryName/$ImageName:$ImageTag $RegistryName/$ImageName:latest'
                      sh 'docker push $RegistryName/$ImageName:$ImageTag'
                      sh 'docker push $RegistryName/$ImageName:latest'
                      sh 'docker rmi $RegistryName/$ImageName:$ImageTag'
                      sh 'docker rmi $RegistryName/$ImageName:latest'
                      echo 'push鏡像到私有倉庫完成!'
                  }
              }
              stage('Pull_Test') {
                  steps {
                      echo '開始更新測試服...'
                      sh 'ssh root@bigdata02 "/opt/server/zsm-microservice/jenkins-remote-shell/zsm-eprofile.sh"'
                      echo '測試服更新完成!'
                  }
              }
              stage('Pull_Formal') {
                  when {
                      expression { return params.UPDATE_FORMUL }
                  }
                  steps {
                      echo '開始更新正式服...'
                      sh 'ssh bigdata@10.0.100.154 "/opt/server/zsm-microservice/jenkins-remote-shell/zsm-eprofile.sh"'
                      echo '正式服更新完成!'
                  }
              }
          }
      }
    • 說明

      1. 這個文件對每次版本的變動都需要修改ImageTag為對應的版本。
      2. 注意:這個文件里面不能寫注釋。
      3. 對於在項目的module下打包的情況,需要把 stage('Build') 下面的steps里面的 sh 'mvn -B -DskipTests clean package dockerfile:build -f pom.xml'改為對應的module下面。
      4. Jenkinspipline語法有Scripted PipelineDeclarative Pipeline兩種,這里使用的是聲明式piplinepipline語法詳情
  • gitlab項目設置

    • 添加為可訪問gitlab倉庫的賬號信息。
    • 通過setting -> members -> add member的方式添加。
  • Jenkins配置

    • jenkins訪問地址:http://192.168.1.100:8080,賬號密碼:admin/123456
    • jenkins pipline創建流程: new任務 -> enter an item name -> 流水線 -> okpipline -> definition -> pipline script from SCM -> SCM -> git -> Repository url -> credentials -> jenkins-gitlab-private -> 輸入分支,默認master分支 -> save
    • 如果Jenkinsfilemodule下面,請在Script Path指定對應的path
  • 遠端服務器腳本

    • 因為鏡像的pullrun都是通過Jenkins調用遠程的shell腳本來執行的,所以需要編寫對應的腳本。所以對於正式服和測試服的每一台服務器都需要對應的腳本。

    • 腳本內容

      #!/bin/bash
      ​
      docker login -u admin -p 123456 bigdata-test
      ​
      docker stop zsm-eprofile
      ​
      docker rm -f zsm-eprofile
      ​
      docker rmi bigdata-test.server.com/test.zsm.com/enterprise-image:latest
      ​
      docker pull bigdata-test.server.com/test.zsm.com/enterprise-image:latest
      ​
      docker run -d -p 9210:9210 -v /etc/hosts:/etc/hosts -v /var/log/jenkinsci/zsm-eprofile:/var/log/jenkinsci/zsm-eprofile --name zsm-eprofile -e PARAMS='-Dspring.profiles.active=test -Djava.security.egd=file:/dev/./urandom' --net=host bigdata-test.server.com/test.zsm.com/enterprise-image:latest
      ​

       

    • 說明:

      • 停止容器和刪除容器需要把名字和容器啟動的名字保持一致。
      • 刪除鏡像和pull鏡像需要改為自己項目構建的鏡像,tag使用latest不變。
      • 運行新的鏡像里面需要把-v /var/log/jenkinsci/zsm-eprofile:/var/log/jenkinsci/zsm-eprofile日志輸出改為自己項目對應的地址,--name zsm-eprofile也需要改成自己項目的名字(和停止刪除容器的名字保持一致),-e PARAMS='-Dspring.profiles.active=test -Djava.security.egd=file:/dev/./urandom'用來指定jvm運行參數。
  • 手動構建Jenkins pipline

    • 進入項目對應的任務,立即構建 -> build history -> 查看構建日志
  • 不足

    • 目前使用的是手動構建方式進行任務的啟動,后期優化成每一個項目都在git上有對應的生產分支,jenkins只需要webhook對應的生產分支就行。
    • 對於程序的版本和鏡像打包的tag,必須保持一致才能有效,版本的迭代每次需要改動兩個地方,有點麻煩。
zsm_test_jenkins.sh 腳本
#!/bin/bash
ssh root@bigdata01 "/opt/server/zsm-microservice/jenkins-remote-shell/zsm_test_jenkins.sh"
sudo docker login -u admin -p 123456 bigdata-test
sudo docker stop zsm_test_jenkins
sudo docker rm -f zsm_test_jenkins
sudo docker rmi bigdata-test.server.com/test.zsm.com/zsm_test_jenkins:latest
sudo docker pull bigdata-test.server.com/test.zsm.com/zsm_test_jenkins:latest
sudo docker run -d -p 9060:9060 -v /etc/hosts:/etc/hosts -v /var/log/jenkinsci/zsm_test_jenkins:/var/log/jenkinsci/zsm_test_jenkins --namezsm_test_jenkins -e PARAMS='-Dspring.profiles.active=test -Dapollo.configService=http://bigdata-test:8090 -Djava.security.egd=file:/dev/./urandom' --net=host bigdata-test.server.com/test.zsm.com/zsm_test_jenkins:latest

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM