8
votes

Maven clean install generate new html file in following location

/var/lib/jenkins/workspace/Docs_LoadTest/target/jmeter/reports/DocsJmeterTests_20170601_151330/index.html

Here "DocsJmeterTests_20170601_151330" will change for every run. So i am trying to publish html report using publish html report plugin. Following is my Pipeline script

node {
build job: 'Docs_LoadTest'
stage('Results') {
publishHTML([allowMissing: false,
         alwaysLinkToLastBuild: true,
         keepAll: true,
         reportDir: 
        '/var/lib/jenkins/workspace/Docs_LoadTest/target/jmeter/reports/*/',
         reportFiles: 'index.html',
         reportName: 'Docs Loadtest Dashboard'
         ])

 }
 }

Getting following error while running the job

[htmlpublisher] Archiving HTML reports...
[htmlpublisher] Archiving at BUILD level /var/lib/jenkins/workspace/Docs_LoadTest/target/jmeter/reports/* to /var/lib/jenkins/jobs/Docs_Pipeline/builds/10/htmlreports/Docs_Loadtest_Dashboard
ERROR: Specified HTML directory '/var/lib/jenkins/workspace/Docs_LoadTest/target/jmeter/reports/*' does not exist.

Even we tried following options didnt worked

/var/lib/jenkins/workspace/Docs_LoadTest/target/jmeter/reports/**/ /var/lib/jenkins/workspace/Docs_LoadTest/target/jmeter/reports/DocsJmeterTests_* /var/lib/jenkins/workspace/Docs_LoadTest/target/jmeter/reports/DocsJmeterTests_* _*

3
Can you give a little more information about your jenkins setup? Are there multiple workers / slave nodes? Is your downstream job being triggered set to use a hardcoded workspace? Is the node label of your downstream job the same?Spencer Malone
@Saagar, See my answer, it can help: stackoverflow.com/a/54203222/5770004Gavriel Cohen

3 Answers

11
votes

The HTML Publisher plugin does not seem to understand wildcards. What you could do in your Pipeline is using Linux's copy command, since that can work with wildcards.

This copies over the contents of all directories in the [Docs_LoadTest]/jmeter/reports folder to a jmeter_results folder in the local workspace:

sh 'cp -r /var/lib/jenkins/workspace/Docs_LoadTest/target/jmeter/reports/*/. target/jmeter_results/'

Note that you must clean both your target folder in the Docs_LoadTest folder and your Pipeline in between runs, else multiple reports will be copied over with this solution.

A better solution:

Would be to apply this trick in the Docs_LoadTest and use the Publish Artifact and Copy Artifact features. This works around having to hardcode the path to the other job and will work even if the Pipeline executes on another slave than the Docs_LoadTest. This does require the Copy Artifacts plugin.

Assuming Docs_LoadTest is a Freestyle job:

  1. Add an Execute Shell Build step that copies the results to a fixed folder, e.g. jmeter_results:

    mkdir -p target/jmeter_results/ cp -r target/jmeter/reports/*/. target/jmeter_results/

  2. Then add an Archive Artifacts Post Build Archive Step with the following files to archive:

    target/jmeter_results/*

In your Pipeline:

  1. Use the Copy Artifact step to copy the files to target/jmeter_results folder in the local workspace:

    step ([$class: 'CopyArtifact', projectName: 'Docs_LoadTest', filter: 'target/jmeter_results/*']);

  2. Change the call to the HTML publisher to use this folder:

    publishHTML([allowMissing: false, alwaysLinkToLastBuild: true, keepAll: true, reportDir: 'target/jmeter_results', reportFiles: 'index.html', reportName: 'Docs Loadtest Dashboard' ])

7
votes

I was having similar problem, only that I wanted to publish multiple reports.

What I ended up doing was I added simple groovy script to iterate through files in reports directory. You can use same/similar approach to get file name.

 stage('publish reports') {
        steps {
            unstash 'source'

            script {
                sh 'ls target/jmeter/reports > listFiles.txt'
                def files = readFile("listFiles.txt").split("\\r?\\n");
                sh 'rm -f listFiles.txt'

                for (i = 0; i < files.size(); i++) {
                    publishHTML target: [
                        allowMissing:false,
                        alwaysLinkToLastBuild: false,
                        keepAll:true,
                        reportDir: 'target/jmeter/reports/' + files[i],
                        reportFiles: 'index.html',
                        reportName: files[i]
                    ]
                }                   
            }           
        }
    }

Note: this example is used in declarative pipeline. Docs about readFile function.

1
votes

I have tried simply the followings.

stage('Test-Junit') {
        steps {
            sh 'gradle test'
        }
        post {
            always {
                script {
                    def moduleNames = ["app", "core", ...]
                    for(i=0; i<moduleNames.size(); i++ ) {
                        publishHTML target: [
                            allowMissing:false,
                            alwaysLinkToLastBuild: false,
                            keepAll:true,
                            reportDir: moduleNames[i] + '/build/reports/tests/test',
                            reportFiles: 'index.html',
                            reportName: 'Test Report:' + moduleNames[i]
                        ]
                    }
                }   
            }
        }
    }

It will make all modules report and thus you can find them on left nav-bar of project dash-board.