Gitlab CI Code Coverage with Jacoco Issue - gitlab-ci

Im trying to set up Gitlab CI. It is working, but Im facing issues while trying to add Jacoco code coverage.
My Jacoco plugin in pom.xml is this.
...
<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>
</execution>
<execution>
<id>post-unit-test</id>
<phase>test</phase>
<goals>
<goal>report</goal>
</goals>
</execution>
</executions>
</plugin>
....
My .gitlab-ci.yml file is this.
....
codecoverage:
image: kaiwinter/docker-java8-maven
script:
- mvn install -B
- cat target/site/jacoco/index.html
....
However, Im not able to generate and display the code coverage. I'm getting the following error.
cat: target/site/jacoco/index.html: No such file or directory
Please help.

Can you remove the cat target/site/jacoco/index.html line and check if it is working. That line won't work, as it is running inside docker and you are trying accessing its filesystem.
Quickly let me know if it works.

Related

How do I Use the Local Maven Repository in IntelliJ

I want to use the local repo provided by IntelliJ to add several jar files to a Maven project, but I have no clue how. I tried to look at the guides on apache.org but they were extremely unclear to me.
What I gathered from the guides was that I had to put something like this in the pom.xml...
...
<build>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-install-plugin</artifactId>
<version>2.4</version>
<executions>
<execution>
<id>cb-1.12</id>
<goals>
<goal>install-file</goal>
</goals>
<configuration>
<file>F:\path\to\file.jar</file>
<groupId>agroup</groupId>
<artifactId>anartifact</artifactId>
<version>1.12</version>
</configuration>
</execution>
<execution>
<id>cb-1.11</id>
<goals>
<goal>install-file</goal>
</goals>
<configuration>
<file>F:\path\to\file.jar</file>
<groupId>agroup</groupId>
<artifactId>anartifact</artifactId>
<version>1.11</version>
</configuration>
</execution>
...the same thing several more times...
</executions>
</plugin>
</build>
...
I added that and tried adding the dependencies but IntelliJ was unable to resolve them. I tried running it anyway thinking maybe the plugin had to add them first and nothing happened except for the wall of errors about classes not being found. The local repo folder didn't have the new group either. I'm not sure what else to try.

Duplicate class error when both axistools and clover plugin are included in maven project

We have a maven project which uses clover and axistools-wsdl2java plugin. Platfrom is windows.
We are using clover 2.4.0 plugin to get code coverage which integrated in project's pom.xml.
Configured the clover plugin as shown below.
<plugin>
<groupId>com.atlassian.maven.plugins</groupId>
<artifactId>maven-clover2-plugin</artifactId>
<version>2.4.0</version>
<configuration> <generatePdf>true</generatePdf>
<generateXml>true</generateXml>
<generateHtml>true</generateHtml>
<licenseLocation>C:/EcasSVNCO/ews/ews-mvn/ewsbase/src/test/resources/license/clover.license</licenseLocation>
<reportDescriptor>C:/EcasSVNCO/ews/ews-mvn/ewsbase/src/test/resources/descriptor/default-clover-report.xml</reportDescriptor>
<excludes>
<exclude>${basedir}/src/main/java/*.java</exclude>
</excludes>
</configuration>
<executions>
<execution>
<id>install</id>
<phase>install</phase>
<goals>
<goal>instrument</goal>
<goal>clover</goal>
</goals>
</execution>
<!--
<execution>
<id>test</id>
<phase>test</phase>
<goals>
<goal>instrument</goal>
<goal>clover</goal>
</goals>
</execution>
<execution>
<id>site</id>
<phase>pre-site</phase>
<goals>
<goal>instrument</goal>
<goal>clover</goal>
</goals>
</execution>
-->
</executions>
</plugin>
Also, there is axistools plugin used to generate classes using wsdl file, which is configured as below.
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>axistools-maven-plugin</artifactId>
<version>1.4</version>
<configuration>
<sourceDirectory>${base.dir}/src/main/resources/wsdl</sourceDirectory>
<outputDirectory>${base.dir}/src/main/java</outputDirectory>
<wsdlFiles>
<wsdlFiles>wsecas.wsdl</wsdlFiles>
</wsdlFiles>
<packageSpace>com.symantec.wsecas</packageSpace>
<testCases>true</testCases>
<serverSide>true</serverSide>
<phase>install</phase>
<subPackageByFileName>true</subPackageByFileName>
</configuration>
<executions>
<execution>
<goals>
<goal>wsdl2java</goal>
</goals>
</execution>
</executions>
</plugin>
When we execute a command 'mvn clean install' , compilation will go fine. Then first axistool's wsdl2java goal is ran and source files are generated in respective directory.
Next clover plugin tries to instrument the source code by running unit test cases, when this plugin places the instrumented source code under
{basedir}/target/clover/src/main/java/...
Then it fires "compile" goal to compile all the source code. While compiling the source code, two source paths are getting added i.e.
{basedir}/src/main/java/... and {basedir}/target/clover/src/main/java/... , both have same classes.
When maven compiler tries to compile these sources compilation is failing by throwing "Duplicate Class Error".
But when we comment out axistools plugin, clover instrumentation and report generation goes fine.
If any of you have come across similar issue 'Duplicate class error', please guide us on this regard.
Any suggestion and help will be greatly appreciated.
It seems that the problem is that your Axis plugin generates sources to src/main/java (it should be rather a target/src-generated).
When the Clover is invoked it will first take 'normal' sources from src/main/java, instrument them and put into target/clover/java. Next Clover will change list of source roots replacing src/main/java by target/clover/java.
Next the AXIS code generation comes into play and it generates new sources again into src/main/java adding also this directory as extra source root.
As a consequence a compiler sees the same set of sources (i.e. non-generated ones) in two locations and complains about it.
This case is very similar to the one described in Clover's Knowledge Base:
https://confluence.atlassian.com/display/CLOVERKB/Duplicate+class+errors+with+Clover+and+JAXB+or+JAXB2+plugin
https://confluence.atlassian.com/display/CLOVERKB/Duplicate+class+errors+with+Clover+and+jaxws-maven+plugin
you will find possible solutions in these articles.

Maven: copying directories using exec plugin

I'm using Maven 3.0.3. I'm having trouble using the Maven exec plugin to copy the contents of one directory to another. Sadly, when I include this plugin in my pom.xml …
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>exec-maven-plugin</artifactId>
<version>1.1.1</version>
<configuration>
<executable>cp</executable>
<arguments>
<argument>-r</argument>
<argument>web-app/*</argument>
<argument>src/main/webapp</argument>
</arguments>
</configuration>
<executions>
<execution>
<phase>verify</phase>
<goals>
<goal>exec</goal>
</goals>
</execution>
</executions>
</plugin>
It isn't working. I get the error below …
[ERROR] Failed to execute goal org.codehaus.mojo:exec-maven-plugin:1.1.1:exec (default-cli) on project jx: Result of /bin/sh -c cd /Users/davea/Documents/workspace/mycoUSA2/Technology/nna/myco2usa/jx && cp -r 'web-app/*' src/main/webapp execution is: '1'. -> [Help 1]
Does anyone know how I can modify my plugin config to copy the contents of one directory to another? Thanks, - Dave
If you are using bash, try the following:
<executable>bash</executable>
<arguments>
<argument>-c</argument>
<argument>cp -r web-app/* src/main/webapp</argument>
</arguments>
This spawns a new bash and gives it the command cp -r web-app/* src/main/webapp to execute.
You can also test if it works for you by inputting this into a normal Terminal window first:
bash -c "cp -r web-app/* src/main/webapp"
Note that the " signs do make a difference as the exec-maven-plugin does insert them automatically, thus they are not included in the <argument>-tag.
Note the command it ran. From the error output:
cp -r 'web-app/*' src/main/webapp
Note in particular the 'web-app/*' file it has tried to copy. Because it has quoted this argument the cp command is looking for a specific file with the name * in the web-app directory. Because you don't have a file with this name it has exited with the error code 1.
The maven-resources-plugin has a goal designed to perform this task. Why not give it a try? It would have the added benefit of making your build platform independent.
<plugin>
<artifactId>maven-resources-plugin</artifactId>
<version>2.5</version>
<executions>
<execution>
<phase>validate</phase>
<goals>
<goal>copy-resources</goal>
</goals>
<configuration>
<outputDirectory>${basedir}/src/main/web-app</outputDirectory>
<resources>
<resource>
<directory>web-app</directory>
</resource>
</resources>
</configuration>
</execution>
</executions>
</plugin>
mvn -X might be more revealing
Many people would use the maven-antrun-plugin and script this in ant so as to get a portable solution.

Is it possible to single out and run a specific goal bound to a maven phase?

Updated to (hopefully) clarify: If a goal is defined to run during a given phase, is it possible to run the individual goal without running thru all phases. In other words would it be possible to run the antrun:run goal (which is defined as part of the install phase below) without getting dependencies, generate-resources, compiling, testing, package, etc?
I'm using the antrun plugin to create a zip file during the package phase and to delete and copy some files during the install phase. I understand how to run single maven plugin goals, for example: mvn antrun:run. However, is there a way to run a specific execution's goal? Something like mvn antrun:run:execution-id, or mvn phase:antrun:run?
Basically, I'd be nice if I can tell maven to do nothing else but run the ant tasks defined below inside the deploy phase, for example. It's kind of tedious having to wait for maven to go thru all the phases just to check if the ant tasks in the deploy phase are working correctly.
<executions>
<!-- create zip file -->
<execution>
<id>create-zip</id>
<phase>package</phase>
<configuration>
<tasks>
...create zip...
</tasks>
</configuration>
<goals>
<goal>run</goal>
</goals>
</execution>
<!-- do some other stuff -->
<execution>
<id>copy-files</id>
<phase>install</phase>
<configuration>
<tasks>
...delete some files, copy some files ...
</tasks>
</configuration>
<goals>
<goal>run</goal>
</goals>
</execution>
</executions>
In other words would it be possible to run the antrun:run goal (which is defined as part of the install phase below) without getting dependencies, generate-resources, compiling, testing, package, etc?
No it's not. While you can configure a plugin (with a <configuration> section under the <plugin> element) and call in on the command line, you can't invoke a specific executionid (and consequently the <configuration> specific to an <execution>).
The only solution in your case would be to declare the antrun plugin in a profile, let's say my-profile, to duplicate the following part of the configuration to configure the plugin in this profile:
<plugin>
<artifactId>maven-antrun-plugin</artifactId>
<version>1.3</version>
<configuration>
<tasks>
... delete some files, copy some files ...
</tasks>
</configuration>
</plugin>
and to call with the right active profile:
mvn antrun:run -Pmy-profile
Try the exec maven plugin...
For ex:
When you run jboss with maven, you can't see the jboss console output, but I need it to display, so what I did is I wrote a java file that reads in server.log(the server console output) as it changes to display the changes so it appears that jboss console is actually showing(a bit hack-ish but working). So I come to the point of answering your question, during the pre-integration-test I executed a java goal which starts my java program. Here is how , using execute plugin of course :
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>exec-maven-plugin</artifactId>
<version>1.1</version>
<executions>
<execution>
<id>console-start</id>
<phase>pre-integration-test</phase>
<goals>
<goal>java</goal>
</goals>
</execution>
</executions>
<configuration>
<mainClass>org.eclipse.console.Main</mainClass>
</configuration>
</plugin>
You just run the install and it executes during the pre-integration-test, however if you just want to execute something like java, use the execute plugin. Sorry if the answer not appropriate, I didn't have the patience to read your question in details, my work hours are over .. cheers

How to run individual test in the integration-test target in maven

We have a hundreds of tests defined for our integration-test phase lifecycle in maven, and they take a long time to finish.
What I want to do is run just one test in the integration-test. I tried doing :
mvn -Dtest=<my-test> integration-test
but that does not work. The -Dtest runs only the tests in the unit test goal, not the integration-test phase. I tried the -Dintegration-test=<my-test> instead, and that was ignored.
Is there a way to do that ?
My configuration is:
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<executions>
<execution>
<id>surefire-it</id>
<phase>integration-test</phase>
<goals>
<goal>test</goal>
</goals>
<configuration>
<excludes>
<exclude>none</exclude>
</excludes>
<includes>
<include>**/api/**</include>
</includes>
.....
If you're using the Maven failsafe plugin, you can run a single integration test by setting the it.test property to your fully qualified test class name:
mvn -D it.test=your.TestCase verify
See the failsafe plugin docs for more info.
The Failsafe documentation would have you specify the test like so:
mvn -Dit.test=BrokenIT verify
However, -Dit.test does not appear to work any longer. Rather, the same parameter used to specify a Surefire test will apparently work for Failsafe as well. For example:
mvn -Dtest=WorksIT verify
I've filed a bug (EDIT: which was closed as "Cannot Reproduce" in 2.12) to correct the documentation.
just add -DfailIfNoTests=false works for me with testNG. Something like this:
mvn integration-test -Dtest=aITest -DfailIfNoTests=false
I struggled through this, and I created an additional profile to use when I wanted to run just one integration test. I hope that I've successfully extracted just the right part here:
<profile>
<id>integrationTestSingle</id>
<build>
<plugins>
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<executions>
<execution>
<id>surefire-it</id>
<phase>integration-test</phase>
<goals>
<goal>test</goal>
</goals>
<configuration>
<includes>
<include>**/integration/**/${test}.java</include>
</includes>
<skipTests>false</skipTests>
</configuration>
</execution>
</executions>
<configuration>
<argLine>-Xms256M -Xmx768M -XX:MaxPermSize=256M</argLine>
</configuration>
</plugin>
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<executions>
<execution>
<id>default-test</id>
<configuration>
<skipTests>true</skipTests>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</profile>
Now, I call maven with the integrationTestSingle profile and with -DfailIfNoTests=false -Dtest=NameOfTest, and it doesn't run any of the regular tests during the regular "test" phase, and runs just the NameOfTest test during the integration-test phase.
I'm not sure about JUnit, but for TestNG the strategy would be to define a suite XML file with only the one test, and then in your POM configure the surefire plugin to only run that. In your POM, you would have something like this (disclaimer, this is untested):
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<executions>
<execution>
<phase>integration-test</phase>
<configuration>
<suiteXmlFiles>
<suiteXmlFile>single-test.xml</suiteXmlFile>
</suiteXmlFiles>
</configuration>
<goals>
<goal>run</goal>
</goals>
</execution>
</executions>
</plugin>
To configure the suite file, see http://testng.org/doc/documentation-main.html
Just ran into this myself. Something like this worked well for me:
mvn -Pintegration-test -Dtest=<my-test>
The trick was to ensure that the test-group was mentioned before the -Dtest portion.
I am using:
Apache Maven 3.6.3
openjdk version "11.0.2" 2019-01-15
<groupId>org.codehaus.mojo</groupId>
<artifactId>failsafe-maven-plugin</artifactId>
<version>2.4.3-alpha-1</version>
This command worked for me:
mvn failsafe:integration-test -Dsurefire.skip=true -DskipIntegrationTests=false -DskipTests=false -Dtest=com.myxyz.func.ITestGate
Was actually simpler that the answers above by going back to basics with the actual documentation.
Running Junit 5 integration tests:
openjdk version "11.0.11" 2021-04-20
Apache Maven 3.6.3
In the main build just drop in documented failsafe config:
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-failsafe-plugin</artifactId>
<version>3.0.0-M5</version>
<executions>
<execution>
<goals>
<goal>integration-test</goal>
<goal>verify</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
Then you can run only a specific integration test with:
mvn -Dtest=\*cs1_\* verify
Note that this version will run your tests in the target folder and if you need to load any external files that are something like src\test\resources\x.y then they are copied to target\test-classes\x.y
This works for me, when I gonna run only one test method in integration test
mvn clean -Dit.test=some.package.SomeTestClass#testMethodName integration-test