Jenkins:Cobertura 插件找不到覆盖率报告
Jenkins: Cobertura plugin cannot find coverage report
这是我的构建日志。我绝对感到困惑,并希望得到任何帮助。
我正在使用 cobertura
插件版本 1.16
。
+ ls
Dockerfile
Jenkinsfile
README.md
babel.config.js
coverage
dev-server.sh
jenkins-agent.yaml
jest.config.ts
package-lock.json
package.json
src
tsconfig.json
webpack.config.js
+ ls ./coverage
cobertura-coverage.xml
+ pwd
/home/jenkins/agent/workspace/api_PR-8
+ cat ./coverage/cobertura-coverage.xml
<?xml version="1.0" ?>
<!DOCTYPE coverage SYSTEM "http://cobertura.sourceforge.net/xml/coverage-04.dtd">
<coverage lines-valid="129" lines-covered="46" line-rate="0.3566" branches-valid="1" branches-covered="1" branch-rate="1" timestamp="1609204078913" complexity="0" version="0.1">
<sources>
<source>/app</source>
</sources>
<packages>
...
</packages>
</coverage>
[Pipeline] cobertura
[Cobertura] Publishing Cobertura coverage report...
[Cobertura] No coverage results were found using the pattern './coverage/cobertura-coverage.xml' relative to '/home/jenkins/agent/workspace/api_PR-8'. Did you enter a pattern relative to the correct directory? Did you generate the XML report(s) for Cobertura?
我也试过使用模式'coverage/cobertura-coverage.xml'
,但我得到了同样的错误。
这是我Jenkinsfile
的相关部分:
stage('Test') {
steps {
sh '''
docker build . --target test
DOCKER_BUILDKIT=1 docker build . -o ./coverage --target coverage
ls
ls ./coverage
pwd
cat ./coverage/cobertura-coverage.xml
'''
cobertura(coberturaReportFile: './coverage/cobertura-coverage.xml')
}
}
更新 1
这很有趣...我尝试将 coberturaReportFile
的值更改为 coverage/*.xml
,并且构建产生了以下错误:
[Pipeline] cobertura
[Cobertura] Publishing Cobertura coverage report...
FATAL: Unable to find coverage results
java.io.IOException: IO error scanning directory '/home/jenkins/agent/workspace/api_PR-8/coverage'
at hudson.FilePath.glob(FilePath.java:1975)
at hudson.FilePath.access00(FilePath.java:212)
at hudson.FilePath$ListGlob.invoke(FilePath.java:1949)
at hudson.FilePath$ListGlob.invoke(FilePath.java:1937)
at hudson.FilePath.act(FilePath.java:1076)
at hudson.FilePath.act(FilePath.java:1059)
at hudson.FilePath.list(FilePath.java:1935)
at hudson.FilePath.list(FilePath.java:1919)
at hudson.FilePath.list(FilePath.java:1904)
at hudson.plugins.cobertura.CoberturaPublisher$ParseReportCallable.invoke(CoberturaPublisher.java:896)
at hudson.plugins.cobertura.CoberturaPublisher$ParseReportCallable.invoke(CoberturaPublisher.java:885)
at hudson.FilePath$FileCallableWrapper.call(FilePath.java:3122)
at hudson.remoting.UserRequest.perform(UserRequest.java:211)
at hudson.remoting.UserRequest.perform(UserRequest.java:54)
at hudson.remoting.Request.run(Request.java:369)
at hudson.remoting.InterceptingExecutorService.call(InterceptingExecutorService.java:72)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at hudson.remoting.Engine.lambda$newThread[=12=](Engine.java:117)
at java.lang.Thread.run(Thread.java:748)
Suppressed: hudson.remoting.Channel$CallSiteStackTrace: Remote call to JNLP4-connect connection from 10.0.4.46/10.0.4.46:49386
at hudson.remoting.Channel.attachCallSiteStackTrace(Channel.java:1800)
at hudson.remoting.UserRequest$ExceptionResponse.retrieve(UserRequest.java:357)
at hudson.remoting.Channel.call(Channel.java:1001)
at hudson.FilePath.act(FilePath.java:1070)
at hudson.FilePath.act(FilePath.java:1059)
at hudson.plugins.cobertura.CoberturaPublisher.perform(CoberturaPublisher.java:548)
at jenkins.tasks.SimpleBuildStep.perform(SimpleBuildStep.java:123)
at org.jenkinsci.plugins.workflow.steps.CoreStep$Execution.run(CoreStep.java:99)
at org.jenkinsci.plugins.workflow.steps.CoreStep$Execution.run(CoreStep.java:69)
at org.jenkinsci.plugins.workflow.steps.SynchronousNonBlockingStepExecution.lambda$start[=12=](SynchronousNonBlockingStepExecution.java:47)
at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
at java.base/java.lang.Thread.run(Thread.java:834)
所以可能在 Cobertura 插件代码中有一个 try-catch 阻止了这个 IO 错误。
我不清楚为什么会出现此 IO 错误或它的含义。每次构建都会重新创建工作区。
更新 2
我也尝试使用模式 **/cobertura-coverage.xml
,但出现了与我最初 post 相同的错误。
[Cobertura] Publishing Cobertura coverage report...
[Cobertura] No coverage results were found using the pattern '**/cobertura-coverage.xml' relative to '/home/jenkins/agent/workspace/api_PR-8'. Did you enter a pattern relative to the correct directory? Did you generate the XML report(s) for Cobertura?
这是一个文件所有权问题。将 ls -l
放入我的管道脚本中显示 coverage/
目录和 coverage/cobertura-coverage.xml
是在 root:root
所有权下生成的,而不是 1000:1000
(又名 jenkins:jenkins
) .这就是为什么 cobertura 跳过目录或未能从中读取的原因。
+ ls -alh
total 500K
drwxr-xr-x 5 1000 1000 4.0K Dec 29 02:59 .
drwxr-xr-x 4 1000 1000 4.0K Dec 29 02:58 ..
-rw-r--r-- 1 1000 1000 77 Dec 29 02:58 .dockerignore
drwxr-xr-x 8 1000 1000 4.0K Dec 29 02:59 .git
-rw-r--r-- 1 1000 1000 47 Dec 29 02:58 .gitignore
-rw-r--r-- 1 1000 1000 353 Dec 29 02:58 Dockerfile
-rw-r--r-- 1 1000 1000 1.5K Dec 29 02:58 Jenkinsfile
-rw-r--r-- 1 1000 1000 877 Dec 29 02:58 README.md
-rw-r--r-- 1 1000 1000 145 Dec 29 02:58 babel.config.js
drwx------ 2 root root 4.0K Dec 29 02:59 coverage
-rwxr-xr-x 1 1000 1000 316 Dec 29 02:58 dev-server.sh
-rw-r--r-- 1 1000 1000 289 Dec 29 02:58 jenkins-agent.yaml
-rw-r--r-- 1 1000 1000 6.5K Dec 29 02:58 jest.config.ts
-rw-r--r-- 1 1000 1000 420.5K Dec 29 02:58 package-lock.json
-rw-r--r-- 1 1000 1000 1.0K Dec 29 02:58 package.json
drwxr-xr-x 9 1000 1000 4.0K Dec 29 02:58 src
-rw-r--r-- 1 1000 1000 5.4K Dec 29 02:58 tsconfig.json
-rw-r--r-- 1 1000 1000 472 Dec 29 02:58 webpack.config.js
为了修复它,我在 运行 cobertura
之前更改了目录的所有权。这是我的最终解决方案:
stage('Test') {
steps {
sh '''
docker build . --target test
DOCKER_BUILDKIT=1 docker build . -o ./coverage --target coverage
chown -R 1000:1000 ./coverage
'''
cobertura(coberturaReportFile: 'coverage/cobertura-coverage.xml')
}
}
这是我的构建日志。我绝对感到困惑,并希望得到任何帮助。
我正在使用 cobertura
插件版本 1.16
。
+ ls
Dockerfile
Jenkinsfile
README.md
babel.config.js
coverage
dev-server.sh
jenkins-agent.yaml
jest.config.ts
package-lock.json
package.json
src
tsconfig.json
webpack.config.js
+ ls ./coverage
cobertura-coverage.xml
+ pwd
/home/jenkins/agent/workspace/api_PR-8
+ cat ./coverage/cobertura-coverage.xml
<?xml version="1.0" ?>
<!DOCTYPE coverage SYSTEM "http://cobertura.sourceforge.net/xml/coverage-04.dtd">
<coverage lines-valid="129" lines-covered="46" line-rate="0.3566" branches-valid="1" branches-covered="1" branch-rate="1" timestamp="1609204078913" complexity="0" version="0.1">
<sources>
<source>/app</source>
</sources>
<packages>
...
</packages>
</coverage>
[Pipeline] cobertura
[Cobertura] Publishing Cobertura coverage report...
[Cobertura] No coverage results were found using the pattern './coverage/cobertura-coverage.xml' relative to '/home/jenkins/agent/workspace/api_PR-8'. Did you enter a pattern relative to the correct directory? Did you generate the XML report(s) for Cobertura?
我也试过使用模式'coverage/cobertura-coverage.xml'
,但我得到了同样的错误。
这是我Jenkinsfile
的相关部分:
stage('Test') {
steps {
sh '''
docker build . --target test
DOCKER_BUILDKIT=1 docker build . -o ./coverage --target coverage
ls
ls ./coverage
pwd
cat ./coverage/cobertura-coverage.xml
'''
cobertura(coberturaReportFile: './coverage/cobertura-coverage.xml')
}
}
更新 1
这很有趣...我尝试将 coberturaReportFile
的值更改为 coverage/*.xml
,并且构建产生了以下错误:
[Pipeline] cobertura
[Cobertura] Publishing Cobertura coverage report...
FATAL: Unable to find coverage results
java.io.IOException: IO error scanning directory '/home/jenkins/agent/workspace/api_PR-8/coverage'
at hudson.FilePath.glob(FilePath.java:1975)
at hudson.FilePath.access00(FilePath.java:212)
at hudson.FilePath$ListGlob.invoke(FilePath.java:1949)
at hudson.FilePath$ListGlob.invoke(FilePath.java:1937)
at hudson.FilePath.act(FilePath.java:1076)
at hudson.FilePath.act(FilePath.java:1059)
at hudson.FilePath.list(FilePath.java:1935)
at hudson.FilePath.list(FilePath.java:1919)
at hudson.FilePath.list(FilePath.java:1904)
at hudson.plugins.cobertura.CoberturaPublisher$ParseReportCallable.invoke(CoberturaPublisher.java:896)
at hudson.plugins.cobertura.CoberturaPublisher$ParseReportCallable.invoke(CoberturaPublisher.java:885)
at hudson.FilePath$FileCallableWrapper.call(FilePath.java:3122)
at hudson.remoting.UserRequest.perform(UserRequest.java:211)
at hudson.remoting.UserRequest.perform(UserRequest.java:54)
at hudson.remoting.Request.run(Request.java:369)
at hudson.remoting.InterceptingExecutorService.call(InterceptingExecutorService.java:72)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at hudson.remoting.Engine.lambda$newThread[=12=](Engine.java:117)
at java.lang.Thread.run(Thread.java:748)
Suppressed: hudson.remoting.Channel$CallSiteStackTrace: Remote call to JNLP4-connect connection from 10.0.4.46/10.0.4.46:49386
at hudson.remoting.Channel.attachCallSiteStackTrace(Channel.java:1800)
at hudson.remoting.UserRequest$ExceptionResponse.retrieve(UserRequest.java:357)
at hudson.remoting.Channel.call(Channel.java:1001)
at hudson.FilePath.act(FilePath.java:1070)
at hudson.FilePath.act(FilePath.java:1059)
at hudson.plugins.cobertura.CoberturaPublisher.perform(CoberturaPublisher.java:548)
at jenkins.tasks.SimpleBuildStep.perform(SimpleBuildStep.java:123)
at org.jenkinsci.plugins.workflow.steps.CoreStep$Execution.run(CoreStep.java:99)
at org.jenkinsci.plugins.workflow.steps.CoreStep$Execution.run(CoreStep.java:69)
at org.jenkinsci.plugins.workflow.steps.SynchronousNonBlockingStepExecution.lambda$start[=12=](SynchronousNonBlockingStepExecution.java:47)
at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
at java.base/java.lang.Thread.run(Thread.java:834)
所以可能在 Cobertura 插件代码中有一个 try-catch 阻止了这个 IO 错误。
我不清楚为什么会出现此 IO 错误或它的含义。每次构建都会重新创建工作区。
更新 2
我也尝试使用模式 **/cobertura-coverage.xml
,但出现了与我最初 post 相同的错误。
[Cobertura] Publishing Cobertura coverage report...
[Cobertura] No coverage results were found using the pattern '**/cobertura-coverage.xml' relative to '/home/jenkins/agent/workspace/api_PR-8'. Did you enter a pattern relative to the correct directory? Did you generate the XML report(s) for Cobertura?
这是一个文件所有权问题。将 ls -l
放入我的管道脚本中显示 coverage/
目录和 coverage/cobertura-coverage.xml
是在 root:root
所有权下生成的,而不是 1000:1000
(又名 jenkins:jenkins
) .这就是为什么 cobertura 跳过目录或未能从中读取的原因。
+ ls -alh
total 500K
drwxr-xr-x 5 1000 1000 4.0K Dec 29 02:59 .
drwxr-xr-x 4 1000 1000 4.0K Dec 29 02:58 ..
-rw-r--r-- 1 1000 1000 77 Dec 29 02:58 .dockerignore
drwxr-xr-x 8 1000 1000 4.0K Dec 29 02:59 .git
-rw-r--r-- 1 1000 1000 47 Dec 29 02:58 .gitignore
-rw-r--r-- 1 1000 1000 353 Dec 29 02:58 Dockerfile
-rw-r--r-- 1 1000 1000 1.5K Dec 29 02:58 Jenkinsfile
-rw-r--r-- 1 1000 1000 877 Dec 29 02:58 README.md
-rw-r--r-- 1 1000 1000 145 Dec 29 02:58 babel.config.js
drwx------ 2 root root 4.0K Dec 29 02:59 coverage
-rwxr-xr-x 1 1000 1000 316 Dec 29 02:58 dev-server.sh
-rw-r--r-- 1 1000 1000 289 Dec 29 02:58 jenkins-agent.yaml
-rw-r--r-- 1 1000 1000 6.5K Dec 29 02:58 jest.config.ts
-rw-r--r-- 1 1000 1000 420.5K Dec 29 02:58 package-lock.json
-rw-r--r-- 1 1000 1000 1.0K Dec 29 02:58 package.json
drwxr-xr-x 9 1000 1000 4.0K Dec 29 02:58 src
-rw-r--r-- 1 1000 1000 5.4K Dec 29 02:58 tsconfig.json
-rw-r--r-- 1 1000 1000 472 Dec 29 02:58 webpack.config.js
为了修复它,我在 运行 cobertura
之前更改了目录的所有权。这是我的最终解决方案:
stage('Test') {
steps {
sh '''
docker build . --target test
DOCKER_BUILDKIT=1 docker build . -o ./coverage --target coverage
chown -R 1000:1000 ./coverage
'''
cobertura(coberturaReportFile: 'coverage/cobertura-coverage.xml')
}
}