gitlab-ci java项目maven

Gitlab是企业常用的代码托管平台。

除了管理代码外,Gitlab还可以做持续集成和持续发布,这一点就需要依赖Gitlab-CI/CD的功能了。

首先要想使用该功能,就需要先安装gitlab-runner。gitlab-runner的下载 可以看这里

gitlab-runner的注册可以看这里。gitlab-runner 就是指某一台服务器(或docker容器,或k8s的节点)用来跑ci任务,当某台服务器安装了gitlab-runner,那么他就是gitlab-runner了。比如说,我们的仓库里有java后端项目 和vue的前端项目,那么我们就可以搞两台服务器跑ci任务,一台跑maven的,一台跑vue的

这里主要注意的两点就是

1.gitlab-runner Executor的选择,一般选择 Docker executor 或者 Kubernetes executor,选择Kubernetes executor 可以参照

2.runner 的TAG 设置(这个设置在gitlab上进行设置)

 

 这里TAG设置,不能为纯数字,否则会提示.gitlab-ci.yml 文件语法错误(这一点需要注意)  ,建议TAG的名字可以设置为构建的名称和ip。如果我这台机器 是跑maven的,服务器ip尾数为151,因此该Runner可以设置为maven-151。同样的,如果机器够多 同类型得也可以多搞几个,这样可以并发构建了。

 

 

本篇选择的是 Docker executor 。

安装完gitlab-runner 。可以查看gitlab-runner的配置文件。

[root@app01 ~]# cat /etc/gitlab-runner/config.toml

 

concurrent = 1
check_interval = 0

[[runners]]
 "name = "jie
  #这个url 是git的url
  url = "http://127.0.65.51:90/"
  #这个url是下载代码的url,如果发现无法下载代码,就手手动添加这个配置
  clone_url = "http://127.0.65.51:90"
  # gitlab的token,这个是在注册时就配置加上的,该token是gitlab提供的
  token = "bb21ebd38b0985b95fdada9024bb8e8"
  executor = "docker"
  [runners.docker]
    tls_verify = false
    image = "harbor.local/library/centos:centos7.5.1804"
    privileged = false
    disable_cache = false
    #这个配置很重要,我的这个runner是用来构建maven项目的,又因为使用的executor是docker,因此每次构建,都需要下载镜像,如果每次都去下载那会麻烦,因此做一个磁盘映射,/home/gitlab-runner/.m2 是宿主机的目录,该目录下 是所有的maven依赖
    volumes = ["/cache","/home/gitlab-runner/.m2:/root/.m2"]
    shm_size = 0
  [runners.cache]

  

上面的gitlab-runner配置文件中,有几个很重要的配置 一个是 clone_url  一个是 executor 最后一个是  volumes

可以查看一下 我的 /home/gitlab-runner/.m2 路径下都是什么

 

 

 

 

 其中repository文件夹下就是存放的各种jar依赖 ,而 settings.xml 则是 maven的配置文件,因此当我们在构建的时候就可以指定配置了。

下面就是.gitlab-ci.yml的配置信息了。

 

# 这个镜像很重要,因为我们是在docker内部使用docker命名,因此必须要能使用该镜像,最好runner上就存在该镜像
image: harbor.local/library/docker
variables:
  #这个指的是生成的docker镜像放在那里,当然选择放在宿主机上了,此处需要注意,如果runner机器跟要放docker的机器不一样的话,需要做互信
  DOCKER_HOST: tcp://172.98.60.152:2375
  DOCKER_DRIVER: overlay2
  #指定maven本地仓库地址
  MAVEN_OPTS: "-Dmaven.repo.local=/root/.m2/repository"
  # 定义build shell
  BUILD_SHELL: "mvn clean package -Dmaven.test.skip=true $MAVEN_OPTS  --settings=/root/.m2/settings.xml"


stages:
  - package
  - build
  - test
  - deploy


job-package:
  stage: package
  image: harbor.local/library/maven:3.6.3-ibmjava-8-alpine
  tags:
    #注意这里的tag,如果是纯数字,可能回报语法异常
    - runner-151
  script:
    - echo $CI_COMMIT_MESSAGE
    - echo `mvn --version`
    - echo $BUILD_SHELL
    - $BUILD_SHELL

  # 由于下一个job我们要使用该job打好的jar文件,因此加入artifacts
  artifacts:
    paths:
      - node-a1/target/*.jar
      - node-a2/target/*.jar
      - node-b1/target/*.jar
      - node-b2/target/*.jar

job-build:
  stage: build
  image: harbor.local/library/docker
  dependencies:
    - job-package
  tags:
   #注意这里的tag,如果是纯数字,可能回报语法异常
    - runner-151
  script:
    #打印git提交信息
    - echo $CI_COMMIT_MESSAGE
    - echo "###################"
  
    # 注意下面这一段script ,他是多行的。这里面做的事,就是判断提交信息是什么,然后选择性的就行ci。在docker build的时候 加入了一个参数DOCKER_JAVA_FILE_PATH,这是一个在Dockerfile中定义的一个参数 
    - if [ "$CI_COMMIT_MESSAGE" == "node-a1" ]; then
      pwd;
      ls;
      echo "=======";
      ls node-a1/target/ ;
      java_file_src=$(ls node-a1/target/ | sed "s:^:`pwd`/:");
      echo $java_file_src;
# 这里的node-a1/target/*.jar 就是上一个job中定义的 docker build --build-arg DOCKER_JAVA_FILE_PATH=node-a1/target/*.jar -t node-a1 . ; echo 'build imgage as node-a1'; fi - if [ "$CI_COMMIT_MESSAGE" == "node-b1" ]; then pwd; ls; echo "======="; ls node-b1/target/ ; java_file_src=$(ls node-b1/target/ | sed "s:^:`pwd`/:") echo $java_file_src; docker build --build-arg DOCKER_JAVA_FILE_PATH=node-b1/target/*.jar -t node-b1 . ; echo 'build imgage as node-b1'; fi # after_script: # - docker rm jdk_temp job-test: stage: test tags: - runner-151 script: # https://blog.csdn.net/github_35631540/article/details/107864258 # 完整的提交消息 - echo $CI_COMMIT_MESSAGE # 构建项目的分支或标记名称 - echo $CI_COMMIT_REF_NAME # 提交分支名称。仅在建立分支时显示 - echo $CI_COMMIT_BRANCH # 提交标记名称。仅在构建标签时显示 - echo $CI_COMMIT_TAG
# 当前的Git CommitId
- ccho $CI_COMMIT_SHA
   # 当前的Git CommitId 短ID 一般使用该值作为build镜像的TAG
- echo $CI_COMMIT_SHORT_SHA
# 上一次的commitid
- echo $CI_COMMIT_BEFORE_SHA


job-deploy:
  stage: deploy
  tags:
    - runner-151
  script:
    # 发布
    - echo $CI_COMMIT_MESSAGE
    - echo "###################"
    
    - if [ "$CI_COMMIT_MESSAGE" == "node-a1" ] ;then
      docker stop nodea1 || true;
      docker rm nodea1 || true;
      echo 'start nodea1 image';
      docker run -d -p 9090:9090 --name nodea1 -d node-a1:latest java -jar app.jar;
      fi
      
    - if [ "$CI_COMMIT_MESSAGE" == "node-b1" ] ;then
      docker stop nodeb1 || true;
      docker rm nodeb1 || true;
      echo 'start nodeb1 image';
      docker run   -p 8080:8080 --name nodeb1 -d node-b1:latest java -jar app.jar;
      fi

 

上面有几点是需要注意的。

1.是要自定义maven构建参数。指定 maven本地仓库地址,指定配置文件 settings.xml。这样可以在本地没有依赖的情况下,通过settings.xml中配置的中央仓库的地址去拉取依赖。

2.docker镜像。不要怀疑,镜像名字就是docker,要在docker中进行docker操作,需要docker in docker 也就是 dind 

3.artifacts 的配置,在job中传递构建物,使用artifacts是比较方便的,这里需要注意的就是在任务中取artifacts时的路径问题。

4.Dockerfile 在构建镜像的时候我们使用if判断,因此说明Dockerfile中有一个是变量,具体导本例就是Dockerfile 中的ADD 操作,就是ADD什么到镜像里,因此我们需要在Dockerfile中设置变量,同时在docker build 是设置该变量的值。

5.关于部署。本例中runner 和实际应用服务器其实是一台服务器,因为我们可以直接进行部署,如果运行服务器是其他服务器,那么我们还需要将构建好的镜像进行推送,然后一个简单的方案是使用watchtower 来动态更新服务

 

一些常见问题:

运行 提示:This job does not have a trace

 

 这个问题,花了很久时间才找到原因,之前是可用的,后来发现是docker hub的地址改变了,虽然本地有对应的镜像,但是runner服务器对应的docker hub中却没有镜像。因此解决方案就是将本地镜像push到docker hub中

 

posted @ 2021-04-25 15:50  陈无问  阅读(6174)  评论(0编辑  收藏  举报