詹金斯只建立没有改变整体解决方案的项目

时间:2018-06-19 13:57:12

标签: c# .net jenkins

我们有一个大型仓库,其中包含许多C#项目,但我们只想构建已进行更改的项目。 因此,如果将变更提交给项目A,则它将仅构建项目A,而不是解决方案中的所有项目。

使用詹金斯有可能吗?

谢谢。

2 个答案:

答案 0 :(得分:0)

是的,有可能。但是,您必须在Jenkins中将所有项目配置为单独的作业。

答案 1 :(得分:0)

我们在一个解决方案中做到了这一点,该解决方案将165个项目分为30个单独的服务和Web应用程序。但是,我们没有使用msbuild构建特定项目,而是根据各自的服务和Web应用程序域创建了单独的解决方案。结果就是像JenkinsBuild_Project1.slnJenkinsBuild_Project2.sln这样的解决方案。

https://stackoverflow.com/a/19534376/3850405

下面的代码可以进行修改,以使用msbuild进行较小的更改。

Jenkinsfile:

#!groovy
import groovy.json.*
pipeline {
    agent {
        node {
            label 'msbuild'
        }
    }

    environment {
        OCTOPUS_PUBLISH_KEY = credentials('OctoPackPublishApiKey')
        //Global variable where we save what to build
        BUILD_LIST =''
    }

    stages {
        stage('What to build?') {
            steps {
                script {

                    GIT_DIFF = bat (
                        script: 'git diff --name-status HEAD..HEAD~1',
                        returnStdout: true
                    ).trim()
                    echo "From batscript: ${GIT_DIFF}"
                    //Environment variable values must either be single quoted, double quoted, or function calls and therefore a json string is used to save the array
                    //https://stackoverflow.com/a/53745878/3850405
                    BUILD_LIST = new JsonBuilder(whatToBuild("${GIT_DIFF}")).toPrettyString()
                    echo BUILD_LIST
                }
            }
        }
        stage('Prepare') {
            steps {
                script {
                    def buildList = new JsonSlurper().parseText(BUILD_LIST)
                    for (i = 0; i < buildList.size(); i++){
                        bat "C:\\Program\\NuGet\\nuget_4.4.1.exe restore Source\\${buildList[i]}\\${buildList[i]}.sln"
                    }
                }
            }
        }
        stage('Build') {
            steps {
                script {
                    def buildList = new JsonSlurper().parseText(BUILD_LIST)
                    for (i = 0; i < buildList.size(); i++){
                        bat "\"${tool 'Build Tools 2019'}\" /t:Clean;Build /p:Configuration=JenkinsBuild JenkinsBuild\\JenkinsBuild_${buildList[i]}.sln"
                    }
                }
            }
        }
        stage('Publish') {
            when {
                anyOf { 
                    branch 'master';
                }
            }
            steps {
                script {
                    def buildList = new JsonSlurper().parseText(BUILD_LIST)
                    for (i = 0; i < buildList.size(); i++){
                        bat """\"${tool 'Build Tools 2019'}\" ^
                        /t:Build ^
                        /p:Configuration=JenkinsBuild ^
                        /p:RunOctoPack=true ^
                        /p:OctoPackEnforceAddingFiles=true ^
                        /p:AllowedReferenceRelatedFileExtensions=none ^
                        /p:OctoPackNuGetProperties=env=${env.BRANCH_NAME};change=${env.CHANGE_ID} ^
                        /p:OctoPackPackageVersion=2.1.${BUILD_NUMBER}-${env.BRANCH_NAME}1 ^
                        /p:OctoPackPublishPackageToHttp=https://OurOctopusServer:1337/nuget/packages ^
                        /p:OctoPackPublishApiKey=${env.OCTOPUS_PUBLISH_KEY} ^
                        JenkinsBuild\\JenkinsBuild_${buildList[i]}.sln"""
                        }
                }
            }
        }
    }
    post {
        always {
            //Clean and notify
        }
    }
}

Groovy脚本从git命令git diff --name-status HEAD..HEAD~1获取文件列表,并从下面的路径中过滤出诸如Project1Project2之类的唯一项目值。

/Source/Project1/Project1.Data/Properties/AssemblyInfo.cs /Source/Project2/Project2.Clients.WinService/Services/Project2.Designer.cs

whatToBuild.groovy:

#!/usr/bin/env groovy

def call(String fileList) {
    println "Printing filelist in whatToBuild()"
    println fileList
    def lines = fileList.tokenize('\n')
    println lines
    def list = []
    lines.eachWithIndex{ value, key -> 
        println "Printing value"
        println value
        if (value.contains("Source")) {
        def result = value =~ /Source\/([A-Z]*)\//
        println "Printing result"
        println result[0][1]
        list.add(result[0][1])
        }
    }
    def listUnique = list as Set
    println listUnique
    return listUnique
}