当前位置: 首页 > 知识库问答 >
问题:

模拟一个抽象类并向类注入Mockito注释?

白云
2023-03-14

可以模拟抽象类,也可以使用Mockito注释将模拟类注入抽象类。我现在有以下情况:

@Mock private MockClassA mockClassA;
@Mock private MockClassB mockClassB;

@Mock(answer = Answers.CALLS_REAL_METHODS) private AbstractClassUnderTest abstractClassUnderTest;

@Before
public void init() {
    MockitoAnnotations.initMocks(this);
    Whitebox.setInternalState(abstractClassUnderTest, mockClassA);
    Whitebox.setInternalState(abstractClassUnderTest, mockClassB);
}

我想在AbstractClassUnderTest上使用类似@InjectMocks的东西,但它不能与@Mock结合使用。Powermock的Whitebox的当前情况是有效的,但我很好奇是否可以通过注释来解决它。我找不到任何解决方案或示例

(我知道对测试抽象类的反对意见,我个人更愿意测试一个具体的实现,只使用@InjectMocks。)

共有2个答案

壤驷宏才
2023-03-14

在初始化之前,我发现了一些模拟字段的技巧。

@InjectMocks
private AbstractClass abstractClass;
@Mock 
private MockClass mockClass;

@Before
public void init() {
    abstractClass= mock(AbstractClass.class, Answers.CALLS_REAL_METHODS);
    MockitoAnnotations.initMocks(this);
}

也许它会帮助某人。

马弘和
2023-03-14

我不知道有什么方法可以做到这一点,原因很明确:@InjectMocks是为未被模拟的测试系统设计的,@Mock是为被模拟的协作者html" target="_blank">设计的,Mockito不是为任何类设计的,在同一个测试中填充这两个角色。

请记住,@Mock(CALLS_REAL_METHODS)声明本身就是危险的:您正在测试AbstractClassUnderTest,但没有运行任何构造函数或初始化任何字段。我不认为你可以期望这种设计的测试是现实的或健壮的,无论注释能为你做什么或不能为你做什么。(就我个人而言,我以前支持将抽象类作为“工具箱中的工具”进行真正的部分模拟,但现在我开始认为它们离现实太远了,没有用处。)

如果我处在你的位置,我会创建一个小的覆盖实现进行测试:

@RunWith(JUnit4.class) public class AbstractClassTest {
  /** Minimial AbstractClass implementation for testing. */
  public static class SimpleConcreteClass extends AbstractClass {
    public SimpleConcreteClass() { super("foo", "bar", 42); }
    @Override public void abstractMethod1() {}
    @Override public String abstractMethod2(int parameter) { return ""; }
  }

  @InjectMocks SimpleConcreteClass classUnderTest;
  @Mock mockClassA;
  @Mock mockClassB;
}

现在,您有了一个简单且可预测的AbstractClass实现,如果您只想测试AbstractClass是否具有与以前相同的扩展API,那么即使没有模拟框架,也可以使用它。(这是一个经常被忽略的抽象类测试。)您甚至可以提取它,因为它可能对其他测试有用:如果您想要覆盖单个测试类的抽象行为,您可以只使用单个方法覆盖创建一个匿名内部类,或者您可以设置classUnderTest=spy(classUnderTest) 设置Mockito代理和所需的行为。

(请记住,@InjectMocks和@Spy不能可靠地一起使用,如本GitHub问题以及它链接到的Google Code和邮件列表线程中所述。)

 类似资料:
  • 所以我有一个简单的java类: ClassA包含: B类: 我的测试设置如下所示: 问题是ClassB不是为ClassA注入的。 然后通过classA调用returnObject(ClassB),它返回NullPointerException(ClassB不是模拟/注入的)。 如果通过IWantToTestThisClass调用returObject(class B),则可以。 这是同时为两个类注

  • 我正在尝试为以下类创建单元测试: 我当前的测试类是: 我可以模拟类的私有字段,但似乎找不到模拟静态方法的方法。这是可能的还是我只是在浪费时间? 我使用Mockito1.10.19和JUnit4进行测试。 我是一个新的对象嘲弄单元测试,所以如果我有什么大错特错,请告诉我! 多谢了。

  • 问题内容: 我有以下代码: 我想使用Mockito创建一个测试。我编写了如下测试: 我在网上收到NullPointerException: ,它表示“策略”列表已初始化,但为空。Mohito有什么办法可以像Spring一样浪费时间?是否将所有实现接口“策略”的实例自动添加到列表中? 顺便说一句,我在Wrapper类中没有任何二传手,如果可能的话,我想以这种方式离开。 问题答案: Mockito不知

  • 问题内容: 我想将Mockito模拟对象注入到Spring(3+)bean中,以进行JUnit的单元测试。我的bean依赖项当前是通过在私有成员字段上使用注释来注入的。 我考虑过使用,但是我希望注入的bean实例实际上是一个代理,因此没有声明目标类的私有成员字段。我不希望为依赖项创建一个公共的setter,因为我将纯粹出于测试目的而修改接口。 我遵循了Spring社区提供的一些建议,但是未创建该模

  • 我有一个带有的测试类,它用于初始化Mockito: 现在我有一个@autowired field来获得方面的建议,但不能注入模拟。

  • 现在只有一个嘲笑工作正常。另一个返回空指针异常。@Autowired和@Mock都为BCryptPasswordEncoder密码编码器提供空点;