Jacoco и Jetty Maven плагин получает 0% покрытия

Я пытаюсь настроить Jacoco, чтобы получить покрытие для моих интеграционных тестов. Я запускаю свои интеграционные тесты против Jetty (используя плагин maven). Но даже если я передаю агент в аргументах варенья при запуске сервера Jetty, отчет jacoco показывает 0%. Вот мой pom.xml

<groupId>org.eclipse.jetty</groupId>
        <artifactId>jetty-maven-plugin</artifactId>
        <executions>
          <execution>
            <id>start-jetty</id>
            <phase>pre-integration-test</phase>
            <goals>
              <goal>run-forked</goal>
            </goals>
            <configuration>
              <waitForChild>false</waitForChild>
              <jvmArgs>-Denv=it -Djetty.port=8081 ${failsafeArgLine}</jvmArgs>
              <webApp>
                <contextPath>/myContext</contextPath>
              </webApp>
            </configuration>
          </execution>
          <execution>
            <id>stop-jetty</id>
            <phase>post-integration-test</phase>
            <goals>
              <goal>stop</goal>
            </goals>
          </execution>
        </executions>
        <configuration>
          <stopPort>8082</stopPort>
          <stopKey>test</stopKey>
        </configuration>
      </plugin>

<plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-failsafe-plugin</artifactId>
        <version>2.12.4</version>
        <configuration>
          <includes>
            <include>**/*IntegrationTest.java</include>
          </includes>
        </configuration>
        <executions>
          <execution>
            <goals>
              <goal>integration-test</goal>
              <goal>verify</goal>
            </goals>
            <configuration>
              <argLine>${failsafeArgLine}</argLine>
            </configuration>
          </execution>
        </executions>
      </plugin>

<plugin>
        <groupId>org.jacoco</groupId>
        <artifactId>jacoco-maven-plugin</artifactId>
        <executions>

          <execution>
            <id>pre-integration-test</id>
            <phase>pre-integration-test</phase>
            <goals>
              <goal>prepare-agent</goal>
            </goals>
            <configuration>

              <destFile>${project.build.directory}/coverage-reports/jacoco-it.exec</destFile>

              <propertyName>failsafeArgLine</propertyName>
            </configuration>
          </execution>

          <execution>
            <id>post-integration-test</id>
            <phase>post-integration-test</phase>
            <goals>
              <goal>report</goal>
            </goals>
            <configuration>

              <dataFile>${project.build.directory}/coverage-reports/jacoco-it.exec</dataFile>

              <outputDirectory>${project.reporting.outputDirectory}/jacoco-it</outputDirectory>
            </configuration>
          </execution>

        </executions>
      </plugin>

Как вы можете видеть, я управляю причалом в режиме форка, и я передаю агента jacoco в параметрах, но ничего...

Есть ли что-то еще, что мне нужно добавить?

2 ответа

Есть много ответов от людей, которые прочитали справку и ответили, не имея ни малейшего представления о том, что действительно нужно, чтобы заставить ее работать.

Так мы пошли..

Обо всем по порядку. Maven запускает вещи, основываясь на фазах, с которыми они связаны, однако, если у вас есть две вещи, связанные с одной и той же фазой, Maven выполнит их в порядке их появления в файле POM, поэтому в этом случае порядок имеет значение.

Вот как выглядит мой POM-файл:

        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-surefire-plugin</artifactId>
            <version>2.17</version>
            <configuration>
                <argLine>${surefireArgLine}</argLine>
                <skipTests>${skip.unit.tests}</skipTests>
                <excludes>
                    <exclude>**/*TestSuite*</exclude>
                    <exclude>**/*ITest*</exclude>
                </excludes>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-failsafe-plugin</artifactId>
            <version>2.12</version>
            <configuration>
                <skipTests>${skip.integration.tests}</skipTests>
                <includes>
                    <include>**/*TestSuite*</include>
                    <include>**/*ITest*</include>
                </includes>
                <systemPropertyVariables>
                     ... //Whatever you need to configure on your integration test, if any.
                </systemPropertyVariables>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.jacoco</groupId>
            <artifactId>jacoco-maven-plugin</artifactId>
            <version>0.7.5.201505241946</version>
            <executions>
                <execution>
                    <id>pre-unit-test</id>
                    <goals>
                        <goal>prepare-agent</goal>
                    </goals>
                    <configuration>
                        <destFile>${project.build.directory}/coverage-reports/jacoco-ut.exec</destFile>
                        <excludes>
                            <exclude>**/*Test*</exclude>
                        </excludes>
                        <propertyName>surefireArgLine</propertyName>
                    </configuration>
                </execution>
                <execution>
                    <id>post-unit-test</id>
                    <goals>
                        <goal>report</goal>
                    </goals>
                    <configuration>
                        <dataFile>${project.build.directory}/coverage-reports/jacoco-ut.exec</dataFile>
                        <outputDirectory>${project.reporting.outputDirectory}/jacoco-ut</outputDirectory>
                    </configuration>
                </execution>
                <execution>
                    <id>pre-integration-test</id>
                    <phase>pre-integration-test</phase>
                    <goals>
                        <goal>prepare-agent</goal>
                    </goals>
                    <configuration>
                        <destFile>${project.build.directory}/coverage-reports/jacoco-it.exec</destFile>
                        <excludes>
                            <exclude>**/*Test*</exclude>
                        </excludes>
                        <propertyName>jacoco.agent.itArgLine</propertyName>
                    </configuration>
                </execution>
                <execution>
                    <id>post-integration-test</id>
                    <phase>verify</phase>
                    <goals>
                        <goal>report</goal>
                    </goals>
                    <configuration>
                        <dataFile>${project.build.directory}/coverage-reports/jacoco-it.exec</dataFile>
                        <outputDirectory>${project.reporting.outputDirectory}/jacoco-it</outputDirectory>
                    </configuration>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.eclipse.jetty</groupId>
            <artifactId>jetty-maven-plugin</artifactId>
            <version>9.2.10.v20150310</version>
            <configuration>
                <scanIntervalSeconds>10</scanIntervalSeconds>
                <stopKey>foo</stopKey>
                <stopPort>9999</stopPort>
                <httpConnector>
                    <port>${it.server.port}</port>
                </httpConnector>
                <contextXml>jetty_context.xml</contextXml>
            </configuration>
            <executions>
                <execution>
                    <id>start-jetty</id>
                    <phase>pre-integration-test</phase>
                    <goals>
                        <goal>run-forked</goal>
                    </goals>
                    <configuration>
                        <scanIntervalSeconds>0</scanIntervalSeconds>
                        <daemon>true</daemon>
                        <waitForChild>false</waitForChild>
                        <maxStartupLines>200</maxStartupLines>
                        <jvmArgs>${jacoco.agent.itArgLine} -Djetty.port=${it.server.port}</jvmArgs>
                    </configuration>
                </execution>
                <execution>
                    <id>stop-jetty</id>
                    <phase>post-integration-test</phase>
                    <goals>
                        <goal>stop</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>

Это фактическая рабочая конфигурация POM.xml. Теперь давайте перейдем к важным деталям:

  1. Плагин Jacoco должен продолжить плагин Jetty, иначе у вас не будет свойства с конфигурацией javaagent
  2. Вы должны запустить Jetty разветвленный, иначе Jetty не примет конфигурацию javaagent.
  3. Так как вы запускаете Jetty разветвленный, вы не можете использовать <webApp>...</webApp> определить контекстный путь. Для этого вам понадобится файл context.xml. Я использую один для Jetty и другой для Tomcat (производство). Смотрите содержание ниже.
  4. Отчеты Jacoco о интеграционных тестах не могут быть привязаны к фазе после интеграционного тестирования, в противном случае вы будете сообщать о результатах до фактического их сбора. (Предполагая, что вы хотите, чтобы Jacoco сообщал, если вы не пропустите это). Таким образом, вы должны привязать его к следующему доступному этапу, который будет проверен.
  5. MaxStartupLines используется, чтобы сообщить Jetty, сколько строк инициализации он может игнорировать, прежде чем допустить, что произошла ошибка инициализации. Возможно, вам придется настроить это.

Context.xml (jetty_context.xml):

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE Configure PUBLIC "-//Jetty//Configure//EN"     "http://www.eclipse.org/jetty/configure_9_0.dtd">
<Configure class="org.eclipse.jetty.webapp.WebAppContext">
  <Set name="contextPath">/myApp</Set>
  <Set name="extraClasspath">comma-separated list of additional classpaths, such as resources</Set>
</Configure>

Если вы хотите также сообщить о своем покрытии кода в SonarQube:

<properties>
    <sonar.jacoco.reportPath>${project.build.directory}/coverage-reports/jacoco-ut.exec</sonar.jacoco.reportPath>
    <sonar.jacoco.itReportPath>${project.build.directory}/coverage-reports/jacoco-it.exec</sonar.jacoco.itReportPath>
</properties>

Если все остальное правильно, вы сможете запустить:mvn clean install sonar:sonar

Я сам немного поработал с этим в последние пару дней и приведу рабочий пример:

https://github.com/daniellundmark/jetty-jacoco-example

Может быть, это может помочь вам.

При запуске вашего примера выше, я получил эту ошибку:

[INFO] Forked process starting
[INFO] Forked process startup errors

Я получил ваш пример работы (с некоторым записанным покрытием), переключившись на подготовку агентов, интеграцию отчетов и перемещение плагина перед подключаемым модулем в файле pom.

Было полезно запустить mvn -X pre-интеграционный тест, чтобы увидеть, что произошло. Но взгляните и на приведенный выше пример. Надеюсь, это поможет вам.

Вот плагины, которые я использовал в файле pom.xml при изменении вашего примера:

            <plugin>
            <groupId>org.eclipse.jetty</groupId>
            <artifactId>jetty-maven-plugin</artifactId>
            <executions>
                <execution>
                    <id>start-jetty</id>
                    <phase>pre-integration-test</phase>
                    <goals>
                        <goal>run-forked</goal>
                    </goals>
                    <configuration>
                        <waitForChild>false</waitForChild>
                        <jvmArgs>${failsafeArgLine} -Denv=it -Djetty.port=8081</jvmArgs>
                        <webApp>
                            <contextPath>/myContext</contextPath>
                        </webApp>
                    </configuration>
                </execution>
                <execution>
                    <id>stop-jetty</id>
                    <phase>post-integration-test</phase>
                    <goals>
                        <goal>stop</goal>
                    </goals>
                </execution>
            </executions>
            <configuration>
                <stopPort>8082</stopPort>
                <stopKey>test</stopKey>
            </configuration>
        </plugin>

        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-failsafe-plugin</artifactId>
            <version>2.12.4</version>
            <configuration>
                <includes>
                    <include>**/*IT.java</include>
                </includes>
            </configuration>
            <executions>
                <execution>
                    <goals>
                        <goal>integration-test</goal>
                        <goal>verify</goal>
                    </goals>
                    <configuration>
                        <argLine>${failsafeArgLine}</argLine>
                    </configuration>
                </execution>
            </executions>
        </plugin>
Другие вопросы по тегам