java.lang.IllegalStateException: no last call on a mock available

1.7k views Asked by At

Hi im doing some unit testing using unitils and I always get this Exception

java.lang.IllegalStateException: no last call on a mock available
    at org.easymock.EasyMock.getControlForLastCall(EasyMock.java:175)
    at org.easymock.EasyMock.expect(EasyMock.java:157)
    at package.service.test.BlogspotServiceTest.testGetBlogSpotList(BlogspotServiceTest.java:52)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:606)
    at org.junit.internal.runners.TestMethod.invoke(TestMethod.java:59)
    at org.junit.internal.runners.MethodRoadie.runTestMethod(MethodRoadie.java:98)
    at org.unitils.UnitilsJUnit4TestClassRunner$TestListenerInvokingMethodRoadie.runTestMethod(UnitilsJUnit4TestClassRunner.java:174)
    at org.junit.internal.runners.MethodRoadie$2.run(MethodRoadie.java:79)
    at org.junit.internal.runners.MethodRoadie.runBeforesThenTestThenAfters(MethodRoadie.java:87)
    at org.unitils.UnitilsJUnit4TestClassRunner$TestListenerInvokingMethodRoadie.runBeforesThenTestThenAfters(UnitilsJUnit4TestClassRunner.java:156)
    at org.junit.internal.runners.MethodRoadie.runTest(MethodRoadie.java:77)
    at org.junit.internal.runners.MethodRoadie.run(MethodRoadie.java:42)
    at org.unitils.UnitilsJUnit4TestClassRunner.invokeTestMethod(UnitilsJUnit4TestClassRunner.java:95)
    at org.junit.internal.runners.JUnit4ClassRunner.runMethods(JUnit4ClassRunner.java:51)
    at org.unitils.UnitilsJUnit4TestClassRunner.access$000(UnitilsJUnit4TestClassRunner.java:44)
    at org.unitils.UnitilsJUnit4TestClassRunner$1.run(UnitilsJUnit4TestClassRunner.java:62)
    at org.junit.internal.runners.ClassRoadie.runUnprotected(ClassRoadie.java:27)
    at org.junit.internal.runners.ClassRoadie.runProtected(ClassRoadie.java:37)
    at org.unitils.UnitilsJUnit4TestClassRunner.run(UnitilsJUnit4TestClassRunner.java:68)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)

My Project;


-BlogspotTest
--src
---hibernate.cfg.xml
--test
---package.service.test
----BaseServiceTest
----BlogspotServiceTest
--web
---WEB-INF
----blogspot-servlet-test.xml
----jdbc-test.xml

Here is my BaseServiceTest

@SpringApplicationContext({"file:web/WEB-INF/blogspot-servlet-test.xml"})
public class BaseServiceTest extends UnitilsJUnit4 {
}

Here is my BlogspotServiceTest

public class BlogspotServiceTest extends BaseServiceTest{

    @Mock
    @InjectInto(property = "blogspotDAO")
    @SpringBean("blogspotDAO")
    private BlogspotDAO blogspotDAOMock;

    @TestedObject
    @SpringBean("blogspotService")
    private BlogspotService blogspotServiceMock;

    @Test
    public void testUpdateBlogSpot() {
    // to make it simple I try this but still i got the exception i mention above.
        expect(1).andReturn(1); 


    }
}

am i missing something ? please lead me to the right path. tnx

Inside my blogspot-service-test.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:aop="http://www.springframework.org/schema/aop"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:jee="http://www.springframework.org/schema/jee"
    xmlns:lang="http://www.springframework.org/schema/lang"
    xmlns:p="http://www.springframework.org/schema/p"
    xmlns:tx="http://www.springframework.org/schema/tx"
    xmlns:util="http://www.springframework.org/schema/util"
    xmlns:mvc="http://www.springframework.org/schema/mvc"
    xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd
        http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/jee http://www.springframework.org/schema/jee/spring-jee.xsd
        http://www.springframework.org/schema/lang http://www.springframework.org/schema/lang/spring-lang.xsd
        http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd
        http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util.xsd">

    <bean id="propertyConfigurer" 
          class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer"
          p:location="file:web/WEB-INF/jdbc-test.properties"/>

    <bean id="dataSource"
          class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close"
          p:driverClassName="${jdbc.driverClassName}"
          p:url="${jdbc.databaseurl}"
          p:username="${jdbc.username}"
          p:password="${jdbc.password}"/>

    <bean id="sessionFactory" class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
        <property name="dataSource" ref="dataSource"/>
        <property name="configLocation" value="classpath:hibernate.cfg.xml"/>
        <property name="hibernateProperties">
            <props>
                <prop key="hibernate.dialect">${jdbc.dialect}</prop>
                <prop key="hibernate.show_sql">true</prop>
                <prop key="hibernate.hbm2ddl.auto">update</prop>
            </props>
        </property>
     </bean>

     <!-- DAO'S -->
     <bean id="blogspotDAO" class="package.dao.impl.BlogspotDAOImpl"/>

     <!-- SERVICES -->
     <bean id="blogspotService" class="package.service.impl.BlogspotServiceImpl"/>


     <bean id="transactionManager" class="org.springframework.orm.hibernate4.HibernateTransactionManager">
        <property name="sessionFactory" ref="sessionFactory"/>
     </bean>

     <tx:annotation-driven transaction-manager="transactionManager"/>
</beans>

I dont think my jdbc-test.properties is necessary but for the sake of completing the requirements here it is,

jdbc.driverClassName=com.mysql.jdbc.Driver
jdbc.dialect=org.hibernate.dialect.MySQL5Dialect
jdbc.databaseurl=jdbc:mysql://127.0.0.1:3306/dbspringminiblogtest
jdbc.username=root
jdbc.password=

Update :

During my research I found this,

One little piece of advice when writing your test, is that the ‘expect’ method will throw an exception when you tend to do that on methods that are final. This might give you an IllegalStateException with the message : “no last call on a mock available”. This basically means “Help I could not mock this call, and now you want me to mock it anyway!”. Step back a bit and think how this EasyMock Class Extension would work in order to Mock existing classes? What would you do? Yes, you would extend this class, and override the methods! That is what the EasyMock Class Extension does. So what happens when you make a method final? You cannot override it! If you have any IllegalStateException from the EasyMock Class Extension, check your methods you tend to ‘expect’ (override) if they are marked “final”. Remove the “final” keyword and you will be able to continue your work. -Stefan Hendriks

i dont have any final class, and im using listed jar files:

easymock-2.3.jar
unitils-easymock-3.3.jar
easymockclassextension-2.3.jar

do in need to update my jar files ?

0

There are 0 answers