2015-11-05 32 views
1

处理假设我有以下情形:嘲笑ClassUnderTest |中的公共方法调用用的ArrayList

public class ClassUnderTest() 
     { 

     private Service myService; 

     public SomeData method1(final InputData input) { 
      final SomeData result = method2(myservice.getOutput(input)); 
      return result; 
     } 

     public SomeData method2(final OutputData output){ 
      //Do something with the OutputData 
     } 
    } 

现在我想测试方法1()。由于它调用method2()我也需要保证method2()内的所有东西都正常工作。但事情是,因为我测试了所有的方法,我会单独测试method2()。

那么我怎么知道只测试method1()而不考虑method2()。我很想在method2()被调用时使用doNothing(),但因为它是我想测试的类而不是模拟的,所以我不能这样做。或者有可能吗?

2.)我该如何声明两个ArrayList的相等,当它们都应该只有两个具有相同值的对象时。例如:

@Test 
public void test(){ 
User user1 = new User(); 
User user2 = new User(); 

user1.setMail("mail"); 
user2.setMail("mail"); 

list<User> list1 = new ArrayList<User>(); 
list<User> list2 = new ArrayList<User>(); 

list1.add(user1); 
list2.add(user2); 

assertEquals(list1,list2); 

} 

这会失败,因为它们不相等对象。

+2

你在问一个2无关的问题。把它分成两个单独的问题会更好。 – Tunaki

+1

如果你正在彻底地测试method2(并且彻底地测试'myservice.getOutput(input)'),而method1只是一个方便的方法来调用method2,那么我可能只有一个方法来证明它确实有效在一些常见的情况下。为'method1'可能做的任何验证添加更多测试(例如'input'非空) –

+0

您是否使用任何类型的模拟框架?它可以在这里帮助,但是示例代码让我知道某处存在设计气味;为什么让一个班级返回两个完全无关的项目? – fge

回答

1

你真的应该分开问的问题,但我试着回答这两个:

1部分嘲弄与的Mockito

我真的不知道它是真正明智的部分嘲笑。但与mockito这是可能的。你可以嘲笑你ClassUnderTest并告诉给的Mockito执行真正的方法时method1被称为

ClassUnderTest mock = Mockito.mock(ClassUnderTest.class); 
when(mock.method1()).thenCallRealMethod(); 

查看收藏

http://site.mockito.org/mockito/docs/current/org/mockito/Mockito.html#partial_mocks

2.断言AssertJ为您提供了收藏很不错的断言 - 例如:

List<String> list1 = Arrays.asList("1", "2", "3"); 
List<String> list2 = Arrays.asList("1", "2", "3"); 
then(list1).containsExactlyElementsOf(list2); 

请在这里查看详情 https://joel-costigliola.github.io/assertj/assertj-core-features-highlight.html#extracted-method-result-assertion

https://github.com/joel-costigliola/assertj-examples/blob/master/assertions-examples/src/test/java/org/assertj/examples/ListSpecificAssertionsExamples.java

+0

谢谢。但问题是,你在列表中使用了字符串。如果我只有字符串,那么我可以使用assertEquals()。但问题是我有两个对象,具有相同的值,这是在两个单独的列表中。 – user5417542

+0

然后你去正确地实现equals() - 所以你的'User'类实现等于反映你的对象的身份。 –

0

你的问题的第一部分已经被马蒂亚斯回答。使用PowerMock将是一种选择。

@RunWith(PowerMockRunner.class) 
@PrepareForTest(ClassUnderTest.class) 
public class YourTest { 

    @Test 
    public void yourTest() { 
     PowerMockito.suppress(MemberMatcher.method(ClassUnderTest.class, "method2")); 
     ClassUnderTest m = mock(ClassUnderTest.class); 
     //method2 will not be called 
     m.method1(); 
    } 
} 

关于名单断言,您可以在Hamcrest使用强大的samePropertyValuesAs匹配的。

import static org.hamcrest.MatcherAssert.assertThat; 
import static org.hamcrest.Matchers.containsInAnyOrder; 
import static org.hamcrest.Matchers.samePropertyValuesAs; 

@Test 
public void yourTest() throws Exception { 

    .... 

    assertThat(list1, containsInAnyOrder(userCollectionToMatcher(list2))); 
} 

public Collection<Matcher<? super User>> userCollectionToMatcher(Collection<User> users) { 
    return users.stream().map(u -> samePropertyValuesAs(u)).collect(Collectors.toList()); 
}