Uploaded image for project: 'Jenkins'
  1. Jenkins
  2. JENKINS-75648

Recording Clover XML Report generated by PHPUnit crashes

XMLWordPrintable

    • Icon: Bug Bug
    • Resolution: Fixed
    • Icon: Major Major
    • coverage-model
    • Ubunut Server 22.04 (not relevant, though)
      PHP 7.4 (not relevant, though)
      PHPUnit 6.5 or 8.5 (not relevant, though)
      Jenkins LTS 2.504.1 (not relevant, though)
      Coverage Plugin Version 2.5.0
      Coverage Model Library 0.54.0

      As PHP develoeprs, we test our code with PHPUnit.
      We currently use PHPUnit 6.5 or 8.5 on PHP 7.4 but the problem should exist with the most current version of PHPUnit, too.

      First, we let Jenkins run our test suite and generate a Clover report XML (among others) through PHPUnit.

      php vendor/bin/phpunit  --log-junit build/logs/junit.xml --coverage-html build/coverage --coverage-clover build/logs/clover.xml

      Then, we try to record the test coverage from that Clover report XML through recordCoverage().

      recordCoverage(
          ignoreParsingErrors: true,
          tools: [
              [parser: 'CLOVER', pattern: 'build/logs/clover.xml']
          ]
      ) 

      This leadsto the following crash:

      Found unhandled java.util.NoSuchElementException exception:Could not obtain attribute 'name' from element ''
          PluginClassLoader for coverage//edu.hm.hafner.coverage.CoverageParser.lambda$getValueOf$0(CoverageParser.java:195)
          java.base/java.util.Optional.orElseThrow(Optional.java:403)
          PluginClassLoader for coverage//edu.hm.hafner.coverage.CoverageParser.getValueOf(CoverageParser.java:194)
          PluginClassLoader for coverage//edu.hm.hafner.coverage.parser.CloverParser.readCoverage(CloverParser.java:101)
          PluginClassLoader for coverage//edu.hm.hafner.coverage.parser.CloverParser.parseReport(CloverParser.java:73)
          PluginClassLoader for coverage//edu.hm.hafner.coverage.CoverageParser.parse(CoverageParser.java:83)
          PluginClassLoader for coverage//io.jenkins.plugins.coverage.metrics.steps.CoverageReportScanner.processFile(CoverageReportScanner.java:64)
          PluginClassLoader for plugin-util-api//io.jenkins.plugins.util.AgentFileVisitor.scanFiles(AgentFileVisitor.java:116)
          PluginClassLoader for plugin-util-api//io.jenkins.plugins.util.AgentFileVisitor.invoke(AgentFileVisitor.java:95)
          PluginClassLoader for plugin-util-api//io.jenkins.plugins.util.AgentFileVisitor.invoke(AgentFileVisitor.java:40)
          hudson.FilePath.act(FilePath.java:1213)
          hudson.FilePath.act(FilePath.java:1196)
          PluginClassLoader for coverage//io.jenkins.plugins.coverage.metrics.steps.CoverageRecorder.recordCoverageResults(CoverageRecorder.java:498)
          PluginClassLoader for coverage//io.jenkins.plugins.coverage.metrics.steps.CoverageRecorder.perform(CoverageRecorder.java:418)
          PluginClassLoader for coverage//io.jenkins.plugins.coverage.metrics.steps.CoverageRecorder.perform(CoverageRecorder.java:408)
          PluginClassLoader for coverage//io.jenkins.plugins.coverage.metrics.steps.CoverageStep$Execution.run(CoverageStep.java:366)
          PluginClassLoader for coverage//io.jenkins.plugins.coverage.metrics.steps.CoverageStep$Execution.run(CoverageStep.java:334)
          PluginClassLoader for workflow-step-api//org.jenkinsci.plugins.workflow.steps.SynchronousNonBlockingStepExecution.lambda$start$0(SynchronousNonBlockingStepExecution.java:49)
          java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:572)
          java.base/java.util.concurrent.FutureTask.run(FutureTask.java:317)
          java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144)
          java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642)
          java.base/java.lang.Thread.run(Thread.java:1583)

      Ignoreing parsing erros with "ignoreParsingErrors: true," seems to have no effect, either.

      The beginning of the generated clover.xml looks like this:

      <?xml version="1.0" encoding="UTF-8"?>
      <coverage generated="1746729026">
        <project timestamp="1746729026"> 

      As you can see, the project element has no name attribute.

      It seems the relevant Code Coverage Library has the necessary code, though it is never triggered through PHPUnit:

      https://github.com/sebastianbergmann/phpunit/blob/23234840e0ecfbc575153f480f74fb7589765b9b/src/Runner/CodeCoverage.php#L290
      https://github.com/sebastianbergmann/php-code-coverage/blob/448f2c504d86dbff3949dcd02c95aa85db2c7617/src/Report/Clover.php#L46-L48

      Unfortunately, the Coverage Model library which the Coerage Jenkins plugin uses, expects the project to have such an attribute:

      https://github.com/jenkinsci/coverage-model/blob/v0.54.0/src/main/java/edu/hm/hafner/coverage/CoverageParser.java#L193-L195
      https://github.com/jenkinsci/coverage-model/blob/v0.54.0/src/main/java/edu/hm/hafner/coverage/parser/CloverParser.java#L101

      Would it be possible to make this attribute optinal to ease the compatibility?
      E.g. by assuming a placeholder name?

      If I manually set a project name, the coverage can be recorded successfully.

      https://issues.jenkins.io/browse/JENKINS-42759 is somewhat related.

       

            Unassigned Unassigned
            ravage Marc Würth
            Votes:
            0 Vote for this issue
            Watchers:
            2 Start watching this issue

              Created:
              Updated:
              Resolved: