Unable to autowire bean in Spring integration test - junit

I am trying to autowire a bean for unit testing purpose.
I'm working with annotation based configuration classes and not using xml based application-context.
Porblem: It says Failed to load ApplicationContext
Here is my code.
#RunWith(SpringJUnit4ClassRunner.class)
#ContextConfiguration(classes = AppContextLoader.class, loader = AnnotationConfigContextLoader.class)
public class StockTest
{
static Logger logger = Logger.getLogger(StockTest.class);
#Autowired
private StockGenerator generator;
#Test
public void someTest()
{//some code here}
}
}
And my configuration class looks like this
#Configuration
public class AppContextLoader
{
#Bean
public StockGenerator stockProvider()
{
StockGenerator stock = new StockGenerator();
return stock;
}
}
Note: StockGenerator is spring managed so I am not sure how to handle it here. I am following this example.
Or is there any other way to autowire beans when one is not using xml based approach.

Related

How to verify an internal method call using Powermock?

I am trying to use PowerMockito to test a save method by verifying an internal audit() method call.
This internal call is made by auditor object which is being instantiated in an init() method of the class. As it is not injected I will not be able to mock it directly. When I used Mockito to verify it always said "There were zero interaction with the mock".
Question:How exactly do I test the save feature? Kindly help!
public class DaoImpl implements Dao{
private Auditor auditor;
#InjectValue
private ObjectLoader loader;
#InjectValue
private ConfigurationProvider confProvider;
#PostConstruct
public void init() {
//Mock this object instantiation and verify audit is called once
auditor = new SyncAuditor(confProvider.getClientConfiguration(), new EventRegProvider());
}
#Override
public void save(final AuditEvt auditEvt) {
final AuditedEvent auditedEvent = builder.build();
auditor.audit(auditedEvent);
}
Test :
#RunWith(PowerMockRunner.class)
#PrepareForTest({ DaoImplTest.class })
#PowerMockIgnore("javax.management.*")
public class DaoImplTest extends PowerMockito {
#InjectMocks
private DaoImpl dataAccess;
#Mock
private SynchAuditor auditorMock;
#Before
public void setUp() throws Exception {
loader = ObjectLoader.init("JUNIT");
loader.bind(ConfigurationProvider.class, configurationProviderMock);
dataAccess = loader.newInstance(DaoImpl.class);
}
#After
public void tearDown() {
loader.release(dataAccess);
ConnectionMgr.disconnect("JUNIT");
}
#Test
public void testSaveAuditEvent() throws Exception {
PowerMockito.whenNew(SynchAuditor.class).
withArguments(Matchers.any(ClientConfiguration.class), Matchers.any(EventRegProvider.class)).thenReturn(this.auditorMock);
final AuditEvent event = AuditEvent.from(null, "principal", UUID.randomUUID().toString(), "randomText",
new AuditEvtDefn((long) 522, "234242", "234242fdgd", true), SUCCESS, null, new GregorianCalendar());
dataAccess.save(event);
Mockito.verify(auditorMock, times(1)).audit(Matchers.any(AuditedEvent.class));
}
Even PowerMockito.verifyNew says there were zero interaction
PowerMockito.verifyNew(SynchronousAuditor.class,times(1)).withArguments(Matchers.any(AuditorClientConfiguration.class),Matchers.any(EventRegistrationProvider.class));
So, I figured out that java reflection will help in such a situation. You will have to get hold onto the real object and then set mocked object to it.
final Field privateAuditorField = DaoImpl.class.getDeclaredField("auditor");
privateAuditorField.setAccessible(true);
privateAuditorField.set(dataAccess, auditorMock);
Now verify will run sucessfully.
Mockito.verify(auditorMock, Mockito.times(1)).audit(Matchers.any(AuditedEvent.class));

Unit testing spring mvc with spring-test and junit

I am new to unit testing with spring-test. I have a spring-mvc-rest application. I am able to mock the environment using MockMvc.
My question is do I need to build the MockMvc object in every class of testing?
Would that not be repetitive configuration.
Is there a way to define this in one class and use it across every testing class?
If we go by single configuration or multiple configuration then which is the best way (by design and by maintenance)?
It's called inhertance
for example
Base Class
#ContextConfiguration(initializers = ConfigFileApplicationContextInitializer.class)
public class BaseTest
{
protected MockMvc mockMvc;
#Before
public void setup()
{
mockMvc = MockMvcBuilders.standaloneSetup().build();
}
}
Extend
public class ExtendedTest extends BaseTest
{
#Test
public void test()
{
//execute test here we have access to the mockMVC
}
}

Multiple #Test method in a java class fails with java.lang.Exception: No runnable methods

I have multiple #Test method in a class while running the paxexam it fails with the below Exception
java.lang.Exception: No runnable methods
at org.junit.runners.BlockJUnit4ClassRunner.validateInstanceMethods(BlockJUnit4ClassRunner.java:169)
at org.junit.runners.BlockJUnit4ClassRunner.collectInitializationErrors(BlockJUnit4ClassRunner.java:104)
at org.junit.runners.ParentRunner.validate(ParentRunner.java:355)
at org.junit.runners.ParentRunner.<init>(ParentRunner.java:76)
at org.junit.runners.BlockJUnit4ClassRunner.<init>(BlockJUnit4ClassRunner.java:57)
at org.ops4j.pax.exam.invoker.junit.internal.ContainerTestRunner.<init>(ContainerTestRunner.java:54)
at org.ops4j.pax.exam.invoker.junit.internal.ContainerTestRunnerBuilder.runnerForClass(ContainerTestRunnerBuilder.java:48)
at org.junit.runners.model.RunnerBuilder.safeRunnerForClass(RunnerBuilder.java:59)
at org.ops4j.pax.exam.invoker.junit.internal.ContainerTestRunnerClassRequest.getRunner(ContainerTestRunnerClassRequest.java:61)
at org.junit.internal.requests.FilterRequest.getRunner(FilterRequest.java:31)
at org.junit.runner.JUnitCore.run(JUnitCore.java:138)
The below is the pax exam code. When i run this code i get an exception. Adding one more point if i change this annotation #ExamReactorStrategy(PerClass.class) to #ExamReactorStrategy(PerMethod.class) this will work the problem is test container restarts after every method
#RunWith(PaxExam.class)
#ExamReactorStrategy(PerClass.class)
public class Integration5TestCases {
private static Logger LOG = LoggerFactory.getLogger(IntegrationTestCases.class);
#Inject
private BundleContext bc;
#Inject
protected FeaturesService featuresService;
/**
* To make sure the tests run only when the boot features are fully
* installed
*/
#Inject
BootFinished bootFinished;
#Configuration
public static Option[] configuration() throws Exception {
MavenUrlReference oracleLib = maven()
.groupId("com.oracle")
.artifactId("ojdbc6")
.version("11.2.0")
.type("jar");
MavenUrlReference dbHandler = maven().groupId("Oracle")
.artifactId("DBHandler")
.versionAsInProject()
.type("xml")
.classifier("features");
return new Option[] {
returnNewKarafInstance(),
systemProperty(PaxExamConstants.ORCALESYSPROPNAME).value(dbHandler.getURL()),
KarafDistributionOption.debugConfiguration("8898", true),
bootClasspathLibrary(oracleLib),
configureConsole().ignoreLocalConsole(),
logLevel(LogLevel.INFO),
keepRuntimeFolder(),
};
}
private static KarafDistributionBaseConfigurationOption returnNewKarafInstance(){
return karafDistributionConfiguration().frameworkUrl(maven().groupId("org.apache.karaf").artifactId("apache-karaf")
.type("zip").versionAsInProject())
.unpackDirectory(new File("target/paxexam/unpack/"))
.useDeployFolder(false);
}
#Inject
SessionFactory commandProcessor;
#Test
public void test1() throws Exception {
System.out.println("sd");
}
#Test
public void test2() throws Exception {
System.out.println("sd");
}
}
This was happening because junit lib was initialized twice inside the karaf container. Thanks for the help guys.

Creating Aspect bean in Spring Java Config file causes another bean to not be autowired

Having a weird issue with attempting to test a Spring AOP class.
Here is a similar setup since I cannot put the actual code on here.
Test Class:
#RunWith(SpringJUnit4ClassRunner.class)
#DirtiesContext(classMode = ClassMode.AFTER_EACH_TEST_METHOD)
#ContextConfiguration(classes = {MyTestConfiguration.class})
public class MyTest {
#Autowired
private MyService1 myService1;
#Autowired
private MyService2 myService2;
#Test
public void testAop() {
myService1.methodToBeIntercepted();
verify(myService2).create();
}
}
Spring Java Configuration File:
#EnableAspectJAutoProxy
#Configuration
public class MyTestConfiguration {
#Bean
public MyService1 myService1() {
return new MyService1Impl();
}
#Bean
public MyService2 myService2() {
return Mockito.mock(MyService2.class);
}
}
AOP Class:
#Aspect
#Component
public class MyAop {
#Autowired
private MyService2 myService2;
#Around("execution(* package.MyService1.methodToBeIntercepted(..))")
public void interception(ProceedingJoinPoint joinPoint) {
// do stuff
MyReturn myReturn = (MyReturn) joinPoint.proceed();
myService2.create();
}
}
With this setup I get an error saying that the test wanted 1 execution of myService2.create() but there was none. This means the AOP class is not intercepting the call properly and that the Spring configuration is correct in that all beans are found.
Next I added the following to MyTestConfiguration to create the bean for the AOP class:
#Bean
public MyAop myAop() {
return new MyAop();
}
Now I get a Spring error saying it can't find the MyService1 bean so the test never runs. Simply adding the myAop bean to MyTestConfiguration now causes the MyService1 bean to no longer be recognized by Spring.
Am I doing something wrong and if so, what?

How to start Spring Boot server in #BeforeClass of junit

We need to use Spring Boot in our project for testing only at present. The Spring app configuration and test app configuration are as below:
#TransactionConfiguration(transactionManager = "transactionManager")
#Transactional
#RunWith(SpringJUnit4ClassRunner.class)
#WebAppConfiguration
#IntegrationTest
#DirtiesContext
public abstract class TestApplicationContext {
}
#SpringBootApplication
public class TestApplication extends SpringBootServletInitializer {
#Bean
public EmbeddedServletContainerFactory embeddedServletContainerFactory() {
...
}
}
Now we need to ensure the Spring Boot server starts in #BeforeClass so that a client can connect to it before any tests run. How do I enable the Spring Boot server to run this way? Removing #SpringapplicationConfiguration and manually starting the server in #BeforeClass like this does not work (it says ContextLoader is NULL). Can someone point out how to achieve this?
public class TestClass extends TestApplicationContext {
...
ConfigurableApplicationContext appContext;
#Beforeclass
public void setup() {
appContext = SpringApplication.run(TestApplication.class, "");
...
}
...
}