如何在 Jenkins 管道(旧工作流程)中使用 VSTest 结果和其他 .NET 插件?

How to use VSTest results and other .NET plugins in Jenkins Pipeline (old workflow)?

由于一些公司变动,我们被迫切换到 Jenkins 作为 CI 工具。虽然这毕竟不是一个坏主意,但由于缺乏对非 Java 应用程序的支持,我们感到很头疼,尤其是对于 Pipeline(旧工作流)插件,当然还有我们的缺乏 Jenkins 知识(此时 none)。

node('master') 
{
    try 
    {
        stage('Checkout, restore, build') 
        {
            //Checkout the code from the repository
            git branch: '<branch_name>', credentialsId: '<credentials_ID>', url: '<repo_URL>'    

            //git clean
            bat returnStatus: true, script: 'git clean -fdx'

            //Perform dotnet restore and nuget restore
            bat returnStatus: true, script: '''for /f "tokens=*" %%a in (\'dir project.json /b /s\') do dotnet restore "%%a"
            "C:\Users\Administrator\.jenkins\workspace\nuget.exe" restore "C:\Users\Administrator\.jenkins\workspace\CI\<solution_name>.sln"'''

            //Build the solution
            bat returnStatus: true, script: '"C:\Program Files (x86)\MSBuild\14.0\Bin\msbuild.exe" /p:DebugType=full /p:platform=x64 /p:configuration=release /p:VisualStudioVersion=14.0 '
        }
    } catch(err)
    {
        currentBuild.result = 'FAILURE'
    }

    jobDsl("${env.JOB_NAME}") {
        steps {
            bat returnStatus: true, script: '"C:\Program Files (x86)\Microsoft Visual Studio 14.0\Common7\IDE\CommonExtensions\Microsoft\TestWindow\vstest.console.exe" "C:\Users\Administrator\.jenkins\workspace\CI\<path_to_tests_dll>"  /TestCaseFilter:"TestCategory=UnitTest|TestCategory=ContinuousTest" /EnableCodeCoverage /Platform:x64 /logger:trx'
        }
        publishers {
            archiveXUnit {
                msTest {
                    pattern('"C:\Users\Administrator\.jenkins\workspace\CI\TestResults"')
                }
            }
        }
    }
}

但是我收到 jobDsl:

的错误

java.lang.IllegalArgumentException: Expected named arguments but got [CI, org.jenkinsci.plugins.workflow.cps.CpsClosure2@1a706730] at org.jenkinsci.plugins.workflow.cps.DSL.parseArgs(DSL.java:442) at org.jenkinsci.plugins.workflow.cps.DSL.invokeDescribable(DSL.java:251) at org.jenkinsci.plugins.workflow.cps.DSL.invokeMethod(DSL.java:129) at org.jenkinsci.plugins.workflow.cps.CpsScript.invokeMethod(CpsScript.java:108) at groovy.lang.GroovyObject$invokeMethod.call(Unknown Source) at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:48) at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:113) at org.kohsuke.groovy.sandbox.impl.Checker.call(Checker.java:151) at org.kohsuke.groovy.sandbox.GroovyInterceptor.onMethodCall(GroovyInterceptor.java:21) at org.jenkinsci.plugins.scriptsecurity.sandbox.groovy.SandboxInterceptor.onMethodCall(SandboxInterceptor.java:115) at org.jenkinsci.plugins.scriptsecurity.sandbox.groovy.SandboxInterceptor.onMethodCall(SandboxInterceptor.java:103) at org.kohsuke.groovy.sandbox.impl.Checker.call(Checker.java:149) at org.kohsuke.groovy.sandbox.impl.Checker.checkedCall(Checker.java:146) at com.cloudbees.groovy.cps.sandbox.SandboxInvoker.methodCall(SandboxInvoker.java:16) at WorkflowScript.run(WorkflowScript:1) at cps.transform(Native Method) at com.cloudbees.groovy.cps.impl.ContinuationGroup.methodCall(ContinuationGroup.java:57) at com.cloudbees.groovy.cps.impl.FunctionCallBlock$ContinuationImpl.dispatchOrArg(FunctionCallBlock.java:109) at com.cloudbees.groovy.cps.impl.FunctionCallBlock$ContinuationImpl.fixArg(FunctionCallBlock.java:82) at sun.reflect.GeneratedMethodAccessor295.invoke(Unknown Source) at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) at java.lang.reflect.Method.invoke(Unknown Source) at com.cloudbees.groovy.cps.impl.ContinuationPtr$ContinuationImpl.receive(ContinuationPtr.java:72) at com.cloudbees.groovy.cps.impl.ClosureBlock.eval(ClosureBlock.java:46) at com.cloudbees.groovy.cps.Next.step(Next.java:74) at com.cloudbees.groovy.cps.Continuable.run0(Continuable.java:154) at org.jenkinsci.plugins.workflow.cps.SandboxContinuable.access[=12=]1(SandboxContinuable.java:18) at org.jenkinsci.plugins.workflow.cps.SandboxContinuable.call(SandboxContinuable.java:33) at org.jenkinsci.plugins.workflow.cps.SandboxContinuable.call(SandboxContinuable.java:30) at org.jenkinsci.plugins.scriptsecurity.sandbox.groovy.GroovySandbox.runInSandbox(GroovySandbox.java:108) at org.jenkinsci.plugins.workflow.cps.SandboxContinuable.run0(SandboxContinuable.java:30) at org.jenkinsci.plugins.workflow.cps.CpsThread.runNextChunk(CpsThread.java:165) at org.jenkinsci.plugins.workflow.cps.CpsThreadGroup.run(CpsThreadGroup.java:328) at org.jenkinsci.plugins.workflow.cps.CpsThreadGroup.access0(CpsThreadGroup.java:80) at org.jenkinsci.plugins.workflow.cps.CpsThreadGroup.call(CpsThreadGroup.java:240) at org.jenkinsci.plugins.workflow.cps.CpsThreadGroup.call(CpsThreadGroup.java:228) at org.jenkinsci.plugins.workflow.cps.CpsVmExecutorService.call(CpsVmExecutorService.java:64) at java.util.concurrent.FutureTask.run(Unknown Source) at hudson.remoting.SingleLaneExecutorService.run(SingleLaneExecutorService.java:112) at jenkins.util.ContextResettingExecutorService.run(ContextResettingExecutorService.java:28) at java.util.concurrent.Executors$RunnableAdapter.call(Unknown Source) at java.util.concurrent.FutureTask.run(Unknown Source) at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source) at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source) at java.lang.Thread.run(Unknown Source)

这真的让我觉得这不是一个好方法,所以有人可以阐明一点并指导我走上正确的道路吗?

不能混用Pipeline DSL and Job DSL。那是完全不同的东西。

XUnit Plugin has built-in support for Pipeline DSL since version 1.100, see JENKINS-27240了解详情。因此,您无需尝试在流水线脚本中嵌入作业 DSL 脚本。

我设法使用“MSTestPublisher”class,

所以最终的流水线是:

node {
stage 'Checkout'
    checkout scm

stage 'Build'
    bat "\"C:/Program Files/dotnet/dotnet.exe\" restore \"${workspace}/MyProg.sln\""
    bat "\"C:/Program Files/dotnet/dotnet.exe\" build \"${workspace}/MyProg.sln\""

stage 'UnitTests'
    bat returnStatus: true, script: "\"C:/Program Files/dotnet/dotnet.exe\" test \"${workspace}/MyProg.sln\" --logger \"trx;LogFileName=unit_tests.xml\" --no-build"
    step([$class: 'MSTestPublisher', testResultsFile:"**/unit_tests.xml", failOnError: true, keepLongStdio: true])
}

我把自己做的一些例子上传到我的GitHub,供大家使用和投稿,大家可以看看:

https://github.com/avrum/JenkinsFileFor.NETCore

那些管道 jenkinsfile 会将此管道模板添加到您的构建中: