Exclude a particular class from Spring Component scan Integration Test - spring

I have a Spring Rest Application built using Spring Boot framework.
Now while writing Spring Integration Test, I wanted to exclude a class
from being get component scanned.my this class contains the dependency for Apache Kafka.
if this class loads while container start up it start looking for Kafka running instances.
so while running Integration test I will not be starting my Kafka server,so I wanted to run
Integration test making Kafka shutdown.
any help is appreciated.

You can exclude the cafka configuration from your test configuration. You haven't shared your code but it would be something like this
#SpringBootApplication(exclude = CafkaConfiguration.class)
public class IntegrationTestConfig {
}
On the other thought you can sure mock the kafka
How can I instanciate a Mock Kafka Topic for junit tests?

The easiest way to do this is to use profiles. In the bean that you only want to be visible to the intergration test add :
#Profile("integration=test")
At the top of the integration test, activate the profile:
#ActiveProfile("integration-test")
Any beans which do not specify a profile (all the other beans) will be present in both test and default profiles. Default is the name of the profile if none is given.

Related

Spring integration test has different behaviour when started via IntelliJ run configuration and via mvn verify

I am working on the Spring application based on Spring Boot 2.6.7 (Spring framework version 5.3.19). I noticed that when I run the integration test via IntelliJ run configuration (basically created only by the right clicking on the test method name and choosing Run test) then the same instance of the ApplicationContext is used in the integration test class and in the actual SpringBootApplication which is tested by the integration test.
But when the same integration test is executed from the command line via mvn verify command, then the different instance of the ApplicationContext is active in the Spring Boot Application from the one which is active in the integration test class.
That for example has a consequence that spring data repository which I added as a field to the integration test class with #SpyBean annotation is not not applied in the Spring boot application. In the applicationContext of the integration test class, that spring data repository is registered as a spy but in the application context of the Spring Boot Application there is no spy proxy but the regular repository.
On the other hand when the test is running via IntelliJ run configuration, the applicationContext is same everywhere and the spy bean is active in the Spring Boot Application flow.
So I want to achieve the same behavior when I run mvn verify as I achieve when I run the test from IntelliJ. Any ideas?

PF4J Spring - not able to load any components in the plugin other than the beans declared in configuration class

We are using plugin architecture for one of our projects and we decided to use Spring pf4j for the same.
When we load the plugin via extensions - the application context is not able to find the beans created using #component in the plugin project- but the beans declared in #configuration classes are injected properly when we configure the plugin using register method - Is there anyway to scan and load the spring components in the plugin?
#Component in plugin is registered to main ApplicationContext via SpringExtensionFactory, make sure you set it up correctly in DefaultPluginManager correctly.
If you are going to use pf4j in SpringBoot, I would suggest you take a look sbp project. It is built upon pf4j and provides better integration with SpringBoot.

Not able to write Test cases for Spring Boot application with actual DB connection from Service to DAO

Can anyone let me know, how to write JUnit test cases for Spring Boot application with actual DB connection?
I mean to say, when we right click on #Test class in src/test/java, and click on Run as JUnit Test, we need to Autowire all the beans of Service and DAO which we had developed in src/main/java and control should flow from #Test class to Service and Service to DAO and queries should be executed using #PersistenceContext Entitymanager and return successfully with the desired results.
The stack specifications
Spring Boot 1.5.10
JPA
Please help me...
You can first refer to the documentation of the SpringBootTest
Spring Boot testing instruments allow you to 'slice' application into pieces, test it separately and test application as a whole. If you want to concentrate on database testing - consider using #DataJpaTest.
As for databases: it is a more common case to use in-memory databases like H2 during testing. But, if you want to test against the real databases, take a look at TestContainers or it's particular implementation (test container spring boot)

Using Spring Boot Configuration in a custom JUnit test runner that does not otherwise use Spring

I have a custom JUnit test runner that executes acceptance-level tests using a test specification format specific to my project. The system under test is using Spring Boot and takes advantage of its configuration facility. I'd like the tests to be able to read the same configuration files in the same way. Obviously, using Spring Boot Configuration itself is an answer.
I'd like to just use Spring Boot Configuration as a stand-alone library, but I'm willing to fire up Spring Boot if that's what it takes. I'm not in control of the top-level application - JUnit is. So, I don't know how to start Spring Boot when I get control inside my test runner.
I've looked at extending SpringJunit4ClassRunner but I can't keep it from looking for #Test annotations and failing when it doesn't find any. I've started to look into merging code from SpringJunit4ClassRunner into my custom runner. Before I go too far down that path, I'd appreciate input from the community.
It sounds like you simply want the application running for a standalone webservice testing. This can be done simply by scripting the "java -jar" command to run the spring boot application. However, I would question why you don't want to leverage the testing tools built into spring boot? You can fire up the entire spring boot application and write some very logical looking tests.
For example a rest api test case:
#Test
public void homePage() throwsException () {
mockMvc.perform(get("/readingList"))
.andExpect(status().isOk())
.andExpect(view().name("readingList"))
.andExpect((model().attribute("books", is(empty()))));
}

End to end test across multi Spring Boot applications

Currently in our project, we are using Spring Integration to integrate many service and some protocol related endpoints.
The project is a multi Spring Boot applications, more than one executable jars will be deployed in production.
The question is:
How to run an end to end test which needs to run cross some of these applications, I have to run the one by one manually? In before none-Spring-Boot applications, I can use Maven tomcat7 plugin to complete this work(deploy the wars into an embedded tomcat and run it in pre-integration-test phase), now how to start up all related applications before I run my test. Assume I do not use Docker/Vagrant now.
Similar question found on stackoverflow, End to end integration test for multiple spring boot applications under Maven
How to run the end2end test automatically?
In an Spring Integration test, sometime I have to mock a http endpoint, so I wrote a simple Controller in test package to archive this purpose, but I want to run it at a different port, which make it more like an outside resource. How to run different #SpringBootApplicaiton classes at varied ports at the same time in the test for this purpose?
I am using the latest Maven, Java 8, Spring Boot 1.3.1.RELEASE.
Actually, Spring Boot comes with the embedded Servlet Container support. One of them is exactly Tomcat. The default on for the org.springframework.boot:spring-boot-starter-web.
With the org.springframework.boot:spring-boot-starter-test and its #SpringApplicationConfiguration and #WebIntegrationTest you can achieve your requirements, even with the random port.
Please, refer to the Spring Boot Reference Manual for more information:
To change the port you can add environment properties to #WebIntegrationTest as colon- or equals-separated name-value pairs, e.g. #WebIntegrationTest("server.port:9000"). Additionally you can set the server.port and management.port properties to 0 in order to run your integration tests using random ports.
With that your #SpringBootApplicaiton will be deployed to that embedded Tomcat and your test can get access to the ran services/controllers.
Note: it doesn't matter if your Spring Boot application has Spring Integration facilities. The behavior is the same: embedded Servlet Container and integration tests against #Value("${local.server.port}").

Resources