Here I have wrote a simple test case using Junit and Mockito.
import org.jbehave.core.annotations.Given;
import org.junit.After;
import org.junit.AfterClass;
import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
import static org.junit.Assert.assertEquals;
import static org.mockito.Mockito.*;
import com.test.dao.login.LoginDao;
import com.test.mapping.user.User;
import com.test.service.login.LoginService;
import com.test.service.login.impl.LoginServiceImpl;
import com.test.util.common.Common;
public class UserLoginSteps {
#Mock
Common common;
#Mock
LoginDao loginDao;
#InjectMocks
LoginService loginService =new LoginServiceImpl();
#BeforeClass
public static void beforeClass() {
System.out.println("#BeforeClass");
}
#Before
public void before() {
System.out.println("#Before");
MockitoAnnotations.initMocks(this);
}
#After
public void after() {
System.out.println("#After");
}
#AfterClass
public static void afterClass() {
System.out.println("#AfterClass");
}
#Given("$username username and $password password")
#Test
public void checkUser(String username, String password) throws Exception{
when(common.checkNullAndEmpty("admin")).thenReturn(true);
when(common.checkNullAndEmpty("password")).thenReturn(true);
when(loginDao.getUser("admin","password")).thenReturn(new User());
assertEquals(true,loginService.checkValidUser(username, password));
}
}
I have initialize the Mock objects inside the before() function.
But that function is not triggered out in running the test case.
I am using following dependencies.
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.11</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-core</artifactId>
<version>2.8.9</version>
<scope>test</scope>
</dependency>
I have seen similar questions to this scenario.
But the following suggestions does not fix the issue.
Is any one can describe why it happen and how to fix this issue it will be great helpful.
Thanks in advance.
After-before-not-working-in-testcase
Simple-junit-class-is-not-calling-the-before-method
Why-isnt-my-beforeclass-method-running
You should annotate your class with #RunWith(MockitoJUnitRunner.class) So the MickitoJunitRunner will take care of your Mocks and tests. But it will not work like this together with JBehave. You have to decide if you want to use JBehave or MockitoJUnitRunner.
In JBehave the correct annotations to use are: #BeforeScenario #AfterScenario #BeforeStory #AfterStory Please take a look at jbehave doc: http://jbehave.org/reference/stable/annotations.html
Related
I am trying to write unit tests for Quarkus using Mockito, but I fail mocking things.
Here is a minimal (not) working example :
package com.my.package;
import io.quarkus.test.junit.QuarkusTest;
import org.mockito.Mockito;
import org.mockito.Mock;
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
#QuarkusTest
public class LoadCalculatorServiceTest {
public class Foobar {
public int baz;
public void setBaz(int baz) {
this.baz = baz;
}
public int getBaz() {
return this.baz;
}
}
#Mock
Foobar foobar;
// Foobar foobar = new Foobar(); // doesn’t work either
#Test
public void myTest() {
Mockito.when(foobar.getBaz()).thenReturn(4); // NullPointer
Assertions.assertEquals(4,foobar.getBaz());
}
}
The test crashes on a NullPointer.
I read such issues may be fixed by annotating the test with #RunWith(MockitoJUnitRunner.class), #ExtendWith(MockitoExtension.class) (which for some reason I expected #QuarkusTest to do anyway ?), however I fail to find the correct imports to load them.
I tried org.junit.jupiter.api.MockitoExtension, org.junit.runner.RunWith and variations, without success.
Here is the relevant part of my pom.xml :
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-junit5</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-junit5-mockito</artifactId>
<scope>test</scope>
</dependency>
What am I missing ?
I figured the original code works with plain-style mocks :
Foobar foobar = Mockito.mock(Foobar.class);
So the question is actually how to make the #Mock annotation work ? There are several things needed for that :
The #RunWith annotation has been replaced (or should we say upgraded) by #ExtendWith in JUnit5. It can be imported in Quarkus using import org.junit.jupiter.api.extension.ExtendWith;.
#RunWith is usually used as #ExtendWith(MockitoExtension.class). MockitoExtension can be imported in Quarkus using import org.mockito.junit.jupiter.MockitoExtension;. Beware that the mockito-junit-jupiter dependency (from the org.mockito group) must be added to the pom.xml, since the quarkus-junit5-mockito packages do not depend on it.
Mocks have to be initialized by MockitoAnnotations.initMocks() before the tests. Note that although it may seem to make more sense to use #BeforeAll for the setup function, apparently it is not the point of this annotation and one should use #BeforeEach (the former needs the setup to be static, and IIUC the setup function will be called before each test anyway).
Then finally the #Mock annotation should work.
To summarize, the original code would become :
package com.my.package;
import io.quarkus.test.junit.QuarkusTest;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.MockitoAnnotations;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.junit.jupiter.MockitoExtension;
#QuarkusTest
#ExtendWith(MockitoExtension.class)
public class LoadCalculatorServiceTest {
public class Foobar {
public int baz;
public void setBaz(int baz) {
this.baz = baz;
}
public int getBaz() {
return this.baz;
}
}
#BeforeEach
public void setup() {
MockitoAnnotations.initMocks(this);
}
#Mock
Foobar foobar;
#Test
public void myTest() {
Mockito.when(foobar.getBaz()).thenReturn(4);
Assertions.assertEquals(4,foobar.getBaz());
}
}
with the following addition to the pom.xml :
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-junit-jupiter</artifactId>
<scope>test</scope>
</dependency>
I'm using quarkus 1.8.1.Final, with mockito 3.6.0, I had the same issue with #Mock annotation and I followed the answer from Skippy le Grand Gourou and it didn't work, so I deleted the #QuarkusTest annotation, and delete de MockitoAnnotations.initMocks(this) method, my mockito version has deprecated this, then the test run with the #Mock annotation. I'm new doing Quarkus so I don't know very well the side effects of removing #QuarkusTest
I'm building an automation framework using Cucumber for BDD, JUnit and Selenium, we have a testrail instance in the cloud for test management and I implemented the testrail API for getting all the test cases from there, the problem is I'm not able to run these steps for getting the test cases because cucumber always validate first feature file exist.
I've tried with #Before (Cucumber), #BeforeClass (JUnit) and the result is always the same:
No features found at [classpath:features]
0 Scenarios
0 Steps
0m0.019s
This is the main class starting the process:
import cucumber.api.CucumberOptions;
import cucumber.api.java.Before;
import cucumber.api.junit.Cucumber;
import org.apache.log4j.Logger;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.runner.RunWith;
import static
com.mps.framework.support.support.Property.BROWSER_NAME;
#RunWith(Cucumber.class)
#CucumberOptions(
plugin = "json:target/cucumber.json",
features = {"classpath:features"},
glue = {"com.selenium.test.stepdefinitions", "com.mps.selenium.hook"},
tags = {"not #ignore"})
public class SeleniumCukes {
private static final Logger LOG = Logger.getLogger(SeleniumCukes.class);
#BeforeClass
public static void startSelenium() {
LOG.info("### Starting Selenium " +
BROWSER_NAME.toString().toUpperCase() + " ###");
}
#AfterClass
public static void stopSelenium() {
LOG.info("### Stopping Selenium ###");
}
}
This is the hooks class:
import com.mps.selenium.base.SeleniumBase;
import cucumber.api.Scenario;
import cucumber.api.java.After;
import cucumber.api.java.Before;
import org.springframework.beans.factory.annotation.Autowired;
import static com.mps.framework.support.hook.Hooks.hookAfter;
import static com.mps.framework.support.hook.Hooks.hookBefore;
public class Hooks {
#Autowired
private SeleniumBase seleniumBase;
#After
public void after() {
hookAfter(seleniumBase.getDriver());
}
#Before
public void before(Scenario scenario) {
hookBefore(scenario);
}
}
I'm not sure what you are trying to achieve but it think what you are looking for is the annotation #BeforeSuite (use the import annotations.BeforeSuite)
I am trying to mock a final class
PowerMockito.mockStatic(TestFinalClass.class);
It is working from my eclipse when I run a single junit and add javaagent to my VM arguments
-javaagent:{path}/powermock-module-javaagent-1.6.4.jar
But when I try to run all test cases from command line using maven build command I am still getting "Cannot subclass final class"
Below is my snippet from pom.xml
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.4</version>
<configuration>
<argLine>-javaagent:{path}/powermock-module-javaagent-1.6.4.jar</argLine>
</configuration>
</plugin>
package test;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
#RunWith(PowerMockRunner.class)
#PrepareForTest(FinalClass.class)
public class Tests {
#Test
public void test() {
PowerMockito.mockStatic(FinalClass.class);
}
}
This works for me. If you add 'PowerMockRunner' and 'PrepareForTest' annotations you don`t need to use extra vm arguments.
import org.junit.Test;
import org.junit.runner.RunWith;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
#RunWith(PowerMockRunner.class)
#PrepareForTest(FinalClass.class)
public class TestFinalClass{
#Test
public void whenMockFinalClassMockWorks() {
FinalClass finalklass = PowerMockito.mock(FinalClass.class);
}
}
I got the code coverage using JaCoCo and need to make some changes related to it in the test class code. Those are as below:
I removed #RunWith annotation
Added #Rule and PowerMockRule class
Mentioned the Final and Static class in #PrepareForTest
#PrepareForTest(FinalClass.class, StaticClass.class)
public class Tests {
#Rule
public PowerMockRule rule = new PowerMockRule();
#Test
public void test() {
PowerMockito.mockStatic(FinalClass.class);
PowerMockito.mockStatic(StaticClass.class);
}
}
Also added the argline in surefire to overcome the final class problem while mocking.
<configuration>
<argLine>-javaagent:{path}/powermock-module-javaagent-1.6.4.jar</argLine>
</configuration>
Trying to use Powermock to mock out a static method on SystemTray. Not sure why this isn't working. I've checked the match of Powermock -> Mockito versions, and I think I've followed all the steps for adding the right annotations, and using the correct PowerMock methods to setup the static one.
The static method on SystemTray seems to be called without the stubbed functionality set by the when().
I am mixing Powermock and Mockito calls here, but according to the docs that is correct.
package CommissionChecker;
import org.apache.commons.logging.Log;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.runners.MockitoJUnitRunner;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import org.springframework.test.util.ReflectionTestUtils;
import java.awt.*;
import java.io.IOException;
import java.util.List;
import static org.mockito.Mockito.*;
import static org.powermock.api.mockito.PowerMockito.mockStatic;
#RunWith(PowerMockRunner.class)
#PrepareForTest(SystemTray.class)
public class DisplayManagerTest {
#Mock
Log logMock;
#Mock
Runner runnerMock;
#Test
public void display_manager_does_nothing_if_system_tray_is_not_supported() throws IOException, AWTException {
mockStatic(SystemTray.class);
when(SystemTray.isSupported()).thenReturn(false);
new DisplayManager(runnerMock);
verifyZeroInteractions(runnerMock);
}
}
These are my maven dependencies
<powermock.version>1.5.2</powermock.version>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-all</artifactId>
<version>1.9.5</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.powermock</groupId>
<artifactId>powermock-module-junit4</artifactId>
<version>${powermock.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.powermock</groupId>
<artifactId>powermock-api-mockito</artifactId>
<version>${powermock.version}</version>
<scope>test</scope>
</dependency>
Just needed to change this line
#RunWith(PowerMockRunner.class)
to
#RunWith(DisplayManager.class)
According to this https://code.google.com/p/powermock/wiki/MockSystem
Here is a simple example using PowerMock:
package test;
import static org.easymock.EasyMock.expect;
import static org.easymock.EasyMock.replay;
import static org.easymock.EasyMock.verify;
import static org.testng.Assert.*;
import org.junit.runner.RunWith;
import org.powermock.api.easymock.PowerMock;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import org.testng.IObjectFactory;
import org.testng.annotations.ObjectFactory;
import org.testng.annotations.Test;
import demo.powermock.IdGenerator;
import demo.powermock.ServiceRegistartor;
//import org.easymock.classextension
#RunWith(PowerMockRunner.class)
#PrepareForTest(IdGenerator.class)
public class Test111 {
#ObjectFactory
public IObjectFactory getObjectFactory() {
return new org.powermock.modules.testng.PowerMockObjectFactory();
}
#Test
//#org.testng.annotations.Test
public void testRegisterService() throws Exception {
long expectedId = 42;
// We create a new instance of test class under test as usually.
ServiceRegistartor tested = new ServiceRegistartor();
// This is the way to tell PowerMock to mock all static methods of a
// given class
PowerMock.mockStatic(IdGenerator.class);
/*
* The static method call to IdGenerator.generateNewId() expectation.
* This is why we need PowerMock.
*/
expect(IdGenerator.generateNewId()).andReturn(expectedId);
// Note how we replay the class, not the instance!
PowerMock.replay(IdGenerator.class);
long actualId = new ServiceRegistartor().registerService();
// Note how we verify the class, not the instance!
PowerMock.verify(IdGenerator.class);
// Assert that the ID is correct
assertEquals(expectedId, actualId);
}
}
I had the same problem but I added the import manually the problem disappeared.
import org.powermock.modules.junit4.PowerMockRunner;
I have some simple classes I'm using to see if I can get powermock to work:
import org.junit.Test;
import org.junit.runner.RunWith;
import org.powermock.api.easymock.PowerMock;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
#RunWith(PowerMockRunner.class)
#PrepareForTest(Foo.class)
public class FooTest
{
#Test
public void testFoobar(){
Foo test = PowerMock.createPartialMock(Foo.class, "foobar");
PowerMock.replay(test);
}
}
and
public class Foo
{
public String foobar(String aString){
return aString + " blah";
}
}
When I try to run this unit test, it tells me:
java.lang.NoClassDefFoundError: org/easymock/classextension/internal/ClassProxyFactory$MockMethodInterceptor
...
I have no idea why its doing this. Please help.
Make sure you're including EasyMock in your class path when using PowerMock... you can find the download page here.
According to the Wiki on PowerMock, it states that EasyMock is a dependency.