Creating objects using Spring to test against production

Do you understand correctly that when using Spring you must use the Spring xml configuration to instantiate your objects for production and directly create objects during testing?

Eg.

MyMain.java

package org.world.hello;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class MyMain {

    private Room room;


    public static void speak(String str)
    {
        System.out.println(str);
    }

    public static void main(String[] args) {

        ApplicationContext context = new ClassPathXmlApplicationContext("Beans.xml");
        Room room = (Room) context.getBean("myRoom");

        speak(room.generatePoem());


    }

}

Room.java

package org.world.hello;

public class Room {

    private BottleCounter bottleCounter;
    private int numBottles;

    public String generatePoem()
    {
        String str = "";
        for (int i = numBottles; i>=0; i--)
        {
            str = str +  bottleCounter.countBottle(i) + "\n";

        }
        return str;
    }

    public BottleCounter getBottleCounter() {
        return bottleCounter;
    }

    public void setBottleCounter(BottleCounter bottleCounter) {
        this.bottleCounter = bottleCounter;
    }

    public int getNumBottles() {
        return numBottles;
    }

    public void setNumBottles(int numBottles) {
        this.numBottles = numBottles;
    }

}

BottleCounter.java

package org.world.hello;

public class BottleCounter {

    public String countBottle(int i)
    {
        return i + " bottles of beer on the wall" + i + " bottles of beer!";
    }

}

Beans.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"
    xsi:schemaLocation="http://www.springframework.org/schema/beans
    http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">

   <bean id="myRoom" class="org.world.hello.Room">
       <property name="bottleCounter">
            <bean id = "myBottleCounter" class = "org.world.hello.BottleCounter"/>     
       </property>
       <property name = "numBottles" value = "10"></property>

   </bean>

</beans>

Conclusion: (my apologies for the missing place)

10 bottles of beer on the wall10 bottles of beer!
9 bottles of beer on the wall9 bottles of beer!
8 bottles of beer on the wall8 bottles of beer!
7 bottles of beer on the wall7 bottles of beer!
6 bottles of beer on the wall6 bottles of beer!
5 bottles of beer on the wall5 bottles of beer!
4 bottles of beer on the wall4 bottles of beer!
3 bottles of beer on the wall3 bottles of beer!
2 bottles of beer on the wall2 bottles of beer!
1 bottles of beer on the wall1 bottles of beer!
0 bottles of beer on the wall0 bottles of beer!

Now for testing this:

BottleCounterTest.java

package org.world.hello;

import static org.junit.Assert.*;

import org.junit.Test;

public class BottleCounterTest {

    @Test
    public void testOneBottle() {
        BottleCounter b = new BottleCounter();
        assertEquals("1 bottles of beer on the wall1 bottles of beer!", b.countBottle(1));
    }

}

Pretty straight forward.

RoomTest.java:

package org.world.hello;

import static org.junit.Assert.*;
import org.mockito.Mockito;
import org.junit.Test;

public class RoomTest {

    @Test
    public void testThreeBottlesAreSeperatedByNewLines()
    {
        Room r = new Room();
        BottleCounter b = Mockito.mock(BottleCounter.class);
        Mockito.when(b.countBottle(Mockito.anyInt())).thenReturn("a");
        r.setBottleCounter(b);
        r.setNumBottles(3);
        assertEquals("a\na\na\na\n", r.generatePoem());
    }

}

Am I correctly creating test object instances this way?

+4
source share
5 answers

: spring @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration. @ContextConfiguration, , . , , beans @Autowired , , mocks , .

: , @ComponentScan, , ( @Component, xml @ContextConfiguration). , , , , . , , , .

: - , beans, , mocks, @ComponentScan , @Configuration beans @Primamry, bean . , @Configuration beans, , , , .

:

package org.world.hello;

import static org.junit.Assert.*;
import org.mockito.Mockito;
import org.junit.Test;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration
public class RoomTest {

    @Configuration
    //@ImportResource(value = {"path/to/resource.xml"}) if you need to load additional xml configuration
    static class TestConfig {
       @Bean
       public BottleCounter bottleCounter() {
        return Mockito.mock(BottleCounter.class);
       }

       @Bean
       public Room room(BottleCounter bottleCounter) {
         Room room = new Room();
         room.setBottleCounter(bottleCounter);
         //r.setNumBottles(3); if you need 3 in each test
         return room;           
       }
    }

    @Autowired
    private Room room;  //room defined in configuration with mocked bottlecounter

    @Test
    public void testThreeBottlesAreSeperatedByNewLines()
    {
        Mockito.when(b.countBottle(Mockito.anyInt())).thenReturn("a");
        r.setNumBottles(3);
        assertEquals("a\na\na\na\n", r.generatePoem());
    }

}
+13

, , :

  • , , , unit test, , , , , . - .

    @Before
    public void init(){
       room = new Room(Mockito.mock(BottleCounter.class)); //If you have a constructor that receive the dependencies
    }
    
  • -, (, ), , Mock, , Mockito.when

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:spring-config.xml")

beans, , . , , , :

@RunWith(MockitoJUnitRunner.class)
public class RoomTest {

@InjectMocks 
public Room room; //This will instantiate the real object for you
                  //So you wont need new operator anymore.

@Mock   //You wont need this in your class example
private AnyDependecyClass anyDependency;

@Test
public void testThreeBottlesAreSeperatedByNewLines(){
    BottleCounter b = Mockito.mock(BottleCounter.class);
    Mockito.when(b.countBottle(Mockito.anyInt())).thenReturn("a");
    room.setBottleCounter(b);
    room.setNumBottles(3);
    assertEquals("a\na\na\na\n", room.generatePoem());
   }
}
+4

, Junit Spring Room RoomTest.java.

, Beans.xml, bean Junit.

Spring @RunWith @ContextConfiguration . .

+3

oppinion Dependency Injectio , Java EE.

POJO, , JUnit TestNG, Spring .

:

import static org.mockito.Mockito.*;

@RunWith(MockitoJUnitRunner.class)
public class RoomTest {

    @Rule
    public MockitoRule rule = MockitoJUnit.rule();

    @Mock   //You wont need this in your class example
    private BottleCounter nameOfBottleCounterAttributeInsideRoom;

    @InjectMocks 
    public Room room;

   @Test
   public void testThreeBottlesAreSeperatedByNewLines(){
      when(b.countBottle(anyInt())).thenReturn("a");
      room.setBottleCounter(b);
      room.setNumBottles(3);
      assertEquals("a\na\na\na\n", room.generatePoem());
   }
}
+3

Spring,

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:test-context.xml")

Spring bean, , beans, , , (, BottleCounter),

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans
    http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">

    <!--Mock BottleCounter -->
    <bean id="myBottleCounter" name="myBottleCounter" class="org.mockito.Mockito" factory-method="mock">
        <constructor-arg value="org.world.hello.BottleCounter"/>
    </bean>

   <bean id="myRoom" class="org.world.hello.Room">
       <property name="bottleCounter" ref="myBottleCounter"></property>
       <property name = "numBottles" value = "10"></property>
   </bean>
</beans>

, , , beans, Spring path , xml. beans context:exclude-filter, -

<!--Mock BottleCounter -->
<bean id="myBottleCounter" name="myBottleCounter" class="org.mockito.Mockito" factory-method="mock">
   <constructor-arg value="org.world.hello.BottleCounter"/>
</bean>
<context:component-scan base-package="org.world.hello">
   <context:exclude-filter type="regex" expression="org\.world\.hello\.Bottle*"/>
</context:component-scan>

, . , , Spring xml Spring . , , , Spring.

, , - . , , unit test ( beans), . , unit test , , , , . Spring , , @Koitoer , , beans, ,

In practice, people are usually not bothered by the difference. Spring refers to its test as unit tests. The general case is what @Nenad Bozic calls a hybrid convention where you would like to bite off just a few objects, for example. connecting to a database or the like, and based on some of your comments, this is what you need.

+2
source

All Articles