Unable to run spring-boot-test - spring

I am new to Spring-boot.
We are trying to practice spring-boot-test by adding the following Java class in this Spring guide for testing purpose.
However, it turns out that we are not able to trigger this Java class. In other words, there is no any test result showing up in the our eclipse console.
Could someone suggest us where we do wrong?
Thanks!
GreetingControllerTest.java
package hello;
#RunWith(SpringJUnit4ClassRunner.class)
#SpringApplicationConfiguration(classes = Application.class)
#WebAppConfiguration
#IntegrationTest
public class GreetingControllerTest {
private RestTemplate restTemplate = new RestTemplate();
#Test
public void testGreeting() {
System.out.println("Where is my TEST?????!!!!!!");
String url = "http://localhost:8080/greeting";
assertNotNull(restTemplate.getForObject(url, Greeting.class));
}
}

The Spring Framework does not run (trigger) tests. Rather, a testing framework like JUnit or TestNG runs tests.
Your code appears to be fine. So, assuming that the example you supplied compiles (i.e., has the correct package imports) and assuming that the #Test annotation you have declared is #org.junit.Test, then you simply need to run the test as a JUnit test.
Your IDE (e.g., Eclipse, IntelliJ, NetBeans) and build framework (e.g., Maven, Ant, Gradle) should provide support for running JUnit tests.
Regards,
Sam

Related

Cucumber does not work with #EnableIf annotation

I want to enable cucumber tests with #EnableIf annotation, but it is not working even if i add #EnabledIf("false")
here is the code that i use :
#EnabledIf("false")
#SpringBootTest(classes = Application.class, webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT)
#CucumberContextConfiguration
public class CucumberRoot {
private int port = 8080;
protected String DEFAULT_URL = "http://localhost:" + port + "/";
#Autowired
protected TestRestTemplate template;
}
for other integration tests beside cucumber i am able to use #EnableIf annotation.
Is there any way to achieve that ?
No.
https://junit.org/junit5/docs/current/user-guide/
1.1. What is JUnit 5?
Unlike previous versions of JUnit, JUnit 5 is composed of several different modules from three different sub-projects.
JUnit 5 = JUnit Platform + JUnit Jupiter + JUnit Vintage
The JUnit Platform serves as a foundation for launching testing frameworks on the JVM. It also defines the TestEngine API for developing a testing framework that runs on the platform. Furthermore, the platform provides a Console Launcher to launch the platform from the command line and a JUnit 4 based Runner for running any TestEngine on the platform in a JUnit 4 based environment. First-class support for the JUnit Platform also exists in popular IDEs (see IntelliJ IDEA, Eclipse, NetBeans, and Visual Studio Code) and build tools (see Gradle, Maven, and Ant).
JUnit Jupiter is the combination of the new programming model and extension model for writing tests and extensions in JUnit 5. The Jupiter sub-project provides a TestEngine for running Jupiter based tests on the platform.
JUnit Vintage provides a TestEngine for running JUnit 3 and JUnit 4 based tests on the platform.
And like JUnit Jupiter and JUnit Vintage, Cucumber is a test engine on the JUnit Platform. The annotation you are using is JUnit Jupiter annotation and can only be understood by JUnit Jupiter. Neither JUnit Vintage nor Cucumber can understand it.
However Cucumber does support OpenTest4Js TestAbortedException. So you can use a before hook to stop a scenario before any step are executed. Either by throwing the exception directly or using Assumptions from JUnit Jupiter.
#Before
public void before() {
boolean condition = // decide if tests should abort
if (condition)
throw new TestAbortedException()
}
#Before
public void before() {
boolean condition = // decide if tests should abort
Assumptions.assumeTrue(condition, "Condition not met");
}

SpringBoot Test - possible to run tests against the default application context?

Execution of the JUnit test of a Spring Boot application causes a testing context of the application to be started whenever the test is invoked. Is there a way to run this test against a spring boot application that has already started without having to spin up a second application context for the test? For example, can the testing framework be instructed to use an existing application context that has already been launched?
#SpringBootTest
#RunWith(SpringRunner.class)
public class MyAppTests {
#Autowired
public SomeService someService;
#Test
public void testInjection() throws AssertionError {
Assert.assertTrue(someService != null);
}
}
There is No way to run tests just using an already started application context, meanwhile without launching a second testing application, if on the premise that you describe.
It means JUnit test of a Spring Boot application is a kind of whitebox testing, the test case will only runs in the environment which is started by itself. The test case has nothing to do with other already running application context.
However, if you really want to run tests against a spring boot application (just like a running test environment) that has already started, maybe you could try some other blackbox testing, for example, API testing or GUI testing. But it will not allow you test SomeService class directly.
Update you test class as below and it should fix your problem.
#SpringBootTest
#RunWith(SpringRunner.class)
#SpringApplicationConfiguration(classes = YourApplication.class)
#ActiveProfiles(Constants.SPRING_PROFILE_DEVELOPMENT)
public class MyAppTests {

Junit5- jupiter all tests suite #BeforeAll #AfterAll not working

The before and after methods not working in JUnitPlatform.
The code is below.
import org.junit.jupiter.api.AfterAll;
import org.junit.jupiter.api.BeforeAll;
import org.junit.platform.runner.JUnitPlatform;
import org.junit.platform.suite.api.SelectClasses;
import org.junit.runner.RunWith;
#RunWith(JUnitPlatform.class)
#SelectClasses({
MyControllerTest.class
})
public class AdminAppTest {
#BeforeAll
public static void setUp() {
System.out.println("setting up");
}
#AfterAll
public static void tearDown() {
System.out.println("tearing down");
}
}
I just want to running before and after methods.
Thank you
Just came across this after running into the same problem, #AfterAll and also #AfterEach annotated methods weren't called. In my case the problem was that an incorrect import for JUnit4 sneaked into my test class, I was importing org.junit.Test instead of org.junit.jupiter.api.Test. Once I fixed this my annotated methods were happily called again.
I may cite the JUnit 5 migration tipps:
#Before and #After no longer exist; use #BeforeEach and #AfterEach instead.
#BeforeClass and #AfterClass no longer exist; use #BeforeAll and #AfterAll instead.
But these annotations should be used in your test class. The methods in your suite class will not be invoked this way. And you should be aware of the fact that suites and JUnit 5 are still work in progress (see Issue 744).
You may want to check that org.junit.jupiter:junit-jupiter-engine is in your classpath.
However, recent versions of build tools (Maven with surefire plugin, Gradle, Eclipse, IntelliJ, etc.) support junit-platform. Therefore you do not need to use JUnit4 with a backward-compatible runner.
Usually you can be in the following cases:
creating new project, in which case you can start directly using only JUnit-Jupiter (and without having JUnit4 in your classpath)
migrating a project from JUnit4 to JUnit5. Here you will want to have two engines: JUnit-Vintage, which covers retrocompatibility for existing tests using the JUnit4 API, and JUnit-Jupiter who offers more flexibility, including the composition of extensions (having Spring, Mockito and parameterized tests features at the same time for example)
Using a JUnit4 runner to run JUnit-Jupiter tests is really a corner case, when you are constrained by an environment (build tool and/or IDE) that you cannot change.
For more details, sample projects are made available by the JUnit team:
Gradle project with JUnit-Jupiter
Maven project with JUnit-Jupiter
Maven project migrating from JUnit4 to JUnit5
Hope this helps !

TestNG + Spring + Power mock Unit test

I have a Spring based application and am in the process of unit testing it. I'm using TestNG for unit tests. For my test i need to make use of PowerMockito to mock some static methods. I also need to make use of a test spring config file for only my unit test.
I'm unable to write my unit tests combining all the three i.e. TestNg, PowerMock and Spring.
I can combine TestNG and Spring by extending the class AbstractTestNGSpringContextTests, however cant mock static methods, instead it executes the actual static method. Something like the below:
#PrepareForTest(MyUtils.class)
#ContextConfiguration(locations = { "classpath:config/test-context.xml"})
public class MyImplTest extends AbstractTestNGSpringContextTests{
.....
}
I can combine TestNG with PowerMockito by extending the class PowerMockTestCase. But then the test spring config files are not resolved. Something like the below:
#PrepareForTest(MyUtils.class)
#ContextConfiguration(locations = { "classpath:config/test-context.xml"})
public class MyImplTest extends PowerMockTestCase{
.....
}
Is there any way for me to write my unit tests combining all the three, i.e. TestNg, PowerMockito and Spring context?
Rather than extending PowerMockTestCase, have you tried using the PowerMockObjectFactory by writing a method like below? Then you can extend AbstractTestNGSpringContextTests.
#ObjectFactory
public IObjectFactory getObjectFactory() {
return new org.powermock.modules.testng.PowerMockObjectFactory();
}
This is suggested by the Powermock GitHub docs.

Mock-service and Grails jaxrs integration test

I want to test a grails application(using jaxrs) and it's integrations. For this task I hope to use the awesome IntegrationTestCase-class from the jaxrs plugin.
This is challenging because I want to mock/replace a service within my application. With “pure” Spring I would create testcontext and manually wire up the mock. I have no idea how to do this in grails.
I’ve tried to access the ApplicationContext directly
Holders.grailsApplication.mainContext.registerMockBean("myService", new MyMock())
This does not seem to work as the mock is not used during the test. Any ideas?
Try to define in test class his way:
#Before
void before() {
Holders.grailsApplication = grailsApplication
defineBeans {
myService(MyMock)
}
}
It's for jUnit tests. If you use Spock, rename before() to setup() and see Spock basics Fixture Methods.

Resources