Surefire marks tests as failed when they set SecurityManager - maven

I have some tests that need to check if the main code did a System.exit(...). This works very nicely with suggestions from https://stackoverflow.com/a/309427/1023341. But when running these tests in Jenkins (in stead of in my IDE Eclipse) and later when trying them on the command-line using Maven-Surefire (as Jenkins does) the tests fail without telling me why. It only tells me: Error occurred in starting fork, check output in log.

When setting a SecurityManager during JUnit (5) using System.setSecurityManager and using Surefire plugin, you should restore the SecurityManager after the test.
SecurityManager origSecurityManager = System.getSecurityManager();
try {
// ... code under test here ...
} finally {
System.setSecurityManager(origSecurityManager);
}
or some other more suitable form. This makes sure that Maven-Surefire-plugin stays happy.
Edit for suggested pre-baked solutions:
There are two pre-baked libraries for this:
junit5-system-exit
system-lambda
As the name suggests: the system-lambda is a Java 8+ solution. Both are JUnit 5 compatible. My personal preference lies with the lambda solution.
More background information

Related

Springboot and maven: how to launch unit tests automatically with two profiles

This question is the continuation of question "SpringBoot: how to run tests twice, with two different config files".
I use to compile my project using mvn clean install. Doing that, maven also launches my unit tests and I immediately knows whether my development is correct.
I am actually working on a module that embeds a JMS connection. my module supports two JMS buses: EMS and AMQ. The bus to be used is specified in the configuration of my module
As a consequence, I need to create two profiles, one for EMS and one for AMQ.
However, when I launch my mvn clean install I want that maven launches automatically the tests using the two profiles, not only one; I don't want to have to launch it twice: mvn clean test -Dspring.profiles.active=ems ; mvn clean test -Dspring.profiles.active=amq
Thank you for help
You can pass the two profiles separated by a comma:
mvn clean install -Dspring.profiles.active=ems,amq
And then you'll have two active profiles:
The following profiles are active: ems,amq
I think that there is a miss-understanding; It seems that when I run my tests with spring.profiles.active=ems,amq:
all tests are launched one time
both profiles are enabled
What I want is different:
launch all tests TWO TIMES
first time with ems (and only ems) profile enabled
second time with amq (and only amq) profile enabled
For the moment, I do not succeed to find a solution; evey clue is welcome
Regards
I found a solution for my issue; a kind of trick based on:
overloading the SpringJUnit4ClassRunner
redefining the run() method in order to:
call force the use of the first profile
call the origial run() method
do the same with the other profile
public class MultiProfileTestRunner extends SpringJUnit4ClassRunner {
...
public void run(RunNotifier notifier) {
System.setProperty("spring.profiles.active", "ems");
super.run(notifier);
System.setProperty("spring.profiles.active", "amq");
super.run(notifier);
}
Between both calls to super.run() we have to 'force' Spring to reload its context, otherwize the profile change is not taken into account
I did it by using the annotation #DirtiesContext(classMode = AFTER_CLASS) on my tests
You can also specify in the src/test/resources/application.properties specific properties that apply every time Spring tests are run. Seems cleaner to me than specifying them on Maven command line. For your case :
spring.profiles.active=ems,amq

maven-surefire-plugin converted to gradle for Geb/Spock parallel test execution

I found this page that explains how to run Geb/Spock tests at the method level which is what I would like to do with my tests, but I am using gradle. Is there a way to convert this to gradle or is it strictly a maven plugin? I can import the maven-surefire-plugin with gradle just fine, however I can't figure out how to convert the configuration block, or if it is even possible.
I've tried something like below but it doesn't work.
tests {
options {
parallel = "methods"
forkCount = 4
}
}
I can execute the tests at the class (spec) level by using gradle maxParallelForks property, but I'd like to run parallel at the test level.
If you are able to run tests in parallel on the method level depends on what test framework you are using.
As far as I know, only TestNG supports it out of the box.
See here: https://docs.gradle.org/current/javadoc/org/gradle/api/tasks/testing/testng/TestNGOptions.html#setParallel-java.lang.String-
There is way to make it work independently of the test framework, using only Gradle, but this way you can only do it on the class level.
In your Gradle test task, set the maxParallelForks property.
See manual: https://docs.gradle.org/current/dsl/org.gradle.api.tasks.testing.Test.html#org.gradle.api.tasks.testing.Test:maxParallelForks`

how is junit related to maven sure fire plugin

I am fairly new to writing Maven pom files and JUnit tests. I have following in my pom and it is calling my test scripts as expected.
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.16</version>
</plugin>
It seems JUnit is more popular than sure fire plugin.
1) How is JUnit similar/different from maven sure fire plugin's default behavior (that is working for me from above plugin configuration). I can imagine JUnit having additional API/library; but what do they give me in addition to sure fire plugin
2)what is the easiest way to change my current tests that are running with sure fire plugin to JUnit. I came across following link which sort of implies that adding few lines to pom would be sufficient (?)
http://maven.apache.org/surefire/maven-surefire-plugin/examples/junit.html
3)about previous bullet, what benefits would I have if I convert sure fire plugin tests to JUnit.
Hopefully, I am unambiguous (with my intro background to maven and JUnit)
maven-surefire-plugin is not itself a test framework: it's a Maven plugin that will run tests written with a test framework, either JUnit or TestNG.
I have following in my pom and it is calling my test scripts as expected.
If this is already running your tests then, as Surefire only knows about those two test frameworks, it means you're already using either JUnit or TestNG. You should be able to tell which from the classes you're importing to write your test classes.
(that is working for me from above plugin configuration)
Unless you have a particular requirement there's little reason to move away from the framework you're already using; it doesn't sound like you need to change anything.
As it says right here:
To get started with JUnit, you need to add the required version of JUnit to your project ... This is the only step that is required to get started - you can now create tests in your test source directory (eg, src/test/java).
Your question is confusing and suggests you haven't done any preliminary research yet. When you say "surefire tests" you may mean Pojo tests. If you know what a JUnit test is, it's pretty common sense thing to convert the Pojo tests to JUnit tests. Just put #Test before the Pojo test methods. You may also want to convert assert into the appropriate JUnit assert methods. In summary, just read a JUnit tutorial and the rest will be straight forward.

Report failures in TestNG framework

I have developed TestNG framework and implemented Maven
When I run the script, the results are generated and in the target folder, when I open index.html, all the scripts are displayed as Pass though it failed.
I have used java verifications (reporter.log)
Can someone suggest me on how to change the java verifications to TestNG to view the failures?
Thank in advance
Reporter.log is just for logging statements in the report. You need to use assertions to do your verifications. Try out the Assert class in Testng.

Bamboo doesn't recognize test in my Spring project

I have a Spring project (Apache CXF, Spring, Hibernate, Maven ...) hosted on BitBucket and I'm trying to use Bamboo as my CI server. My idea is deploying the code directly to Heroku from Bamboo so that deploying time is automated.
I made a plan with a couple of tasks to achieve this. First I have a Source Code Checkout task and a builder task. Both of them are working, code is compiling and test are passing, I can see that in the task log. The problem is that Bamboo doesn't seem to recognize the tests (it marks the task are testless).
I have also tried to create a new JUnit test task and it's even worst. Log shows that everything is working properly but Bamboo marks the plan as a failure after the test task is executed.
Any ideas?
Not sure which version of Bamboo you're using, but in the version that we have, you have to turn on unit test result evaluation on the Builder tab. Please see the attached screenshot, and make sure that this is enabled, and the directory setting is pointing to the directory where Maven Surefire creates the test results (in XML format).

Resources