在Java单元测试中,如何mock未注入但在待测class内部创建的变量?
In Java unit testing, how to mock the variables that are not injected but created inside the to-be-tested class?
例如要测试的class是
public class toBeTested {
private Object variable;
public toBeTested(){
variable = someFactory(); // What if this someFactory() sends internet request?
// Can I mock "variable" without calling
// someFactory() in testing?
}
public void doSomething(){
...
Object returnedValue = variable.someMethod(); // In testing, can I mock the behavior of
// this someMethod() method when
// "variable" is a private instance
// variable that is not injected?
Object localVariable = new SomeClass(); // Can I mock this "localVariable" in
// testing?
...
}
}
我的问题如上评论所述。
简而言之,如何模拟未注入但在待测内部创建的变量class?
提前致谢!
你的问题更多是关于设计的,你的class的设计是错误的,不可测试,写单元测试不容易(有时根本不可能)一种方法和 class 以前开发的。实际上 TDD(测试驱动开发)的一大好处是它可以帮助开发人员以可测试的方式开发他们的组件。
如果先编写测试,您的 class 就不会以这种方式开发。事实上,当你为你的组件编写测试时,你应该做的一件不可避免的事情就是重构。因此,在这里要将您的组件重构为可测试组件,您应该将工厂作为参数传递给 class 的构造函数。
而 localVariable 呢:
这真的取决于你的情况和你对你的单位的期望(这里你的单位是 doSomething
方法)。如果它是一个变量,你从你的方法中提取出来作为它的任务的一部分来创建,并且它应该在每次调用中根据方法中的一些逻辑来创建,那么让它在那里是没有问题的,但是如果它提供了一些其他的逻辑来你的方法,可以作为参数传递给你的 class 你可以把它作为参数传递给你的 class 的 cunstructor。
还有一点,重构的时候要小心,会有很多其他组件使用你的组件,你应该逐步重构,你不应该改变你的方法的逻辑。
添加另一个观点:如果遇到您必须测试给定 class 并且不允许更改您需要测试的 class 的情况,您可以选择使用像 PowerMock (https://github.com/powermock/powermock) 这样的框架来提供增强的模拟功能。
但请注意,不建议仅将 PowerMock 用于证明难以测试代码的合理性。 Tashkhisi 的回答是迄今为止更好的通用方法。
例如要测试的class是
public class toBeTested {
private Object variable;
public toBeTested(){
variable = someFactory(); // What if this someFactory() sends internet request?
// Can I mock "variable" without calling
// someFactory() in testing?
}
public void doSomething(){
...
Object returnedValue = variable.someMethod(); // In testing, can I mock the behavior of
// this someMethod() method when
// "variable" is a private instance
// variable that is not injected?
Object localVariable = new SomeClass(); // Can I mock this "localVariable" in
// testing?
...
}
}
我的问题如上评论所述。
简而言之,如何模拟未注入但在待测内部创建的变量class?
提前致谢!
你的问题更多是关于设计的,你的class的设计是错误的,不可测试,写单元测试不容易(有时根本不可能)一种方法和 class 以前开发的。实际上 TDD(测试驱动开发)的一大好处是它可以帮助开发人员以可测试的方式开发他们的组件。
如果先编写测试,您的 class 就不会以这种方式开发。事实上,当你为你的组件编写测试时,你应该做的一件不可避免的事情就是重构。因此,在这里要将您的组件重构为可测试组件,您应该将工厂作为参数传递给 class 的构造函数。
而 localVariable 呢:
这真的取决于你的情况和你对你的单位的期望(这里你的单位是 doSomething
方法)。如果它是一个变量,你从你的方法中提取出来作为它的任务的一部分来创建,并且它应该在每次调用中根据方法中的一些逻辑来创建,那么让它在那里是没有问题的,但是如果它提供了一些其他的逻辑来你的方法,可以作为参数传递给你的 class 你可以把它作为参数传递给你的 class 的 cunstructor。
还有一点,重构的时候要小心,会有很多其他组件使用你的组件,你应该逐步重构,你不应该改变你的方法的逻辑。
添加另一个观点:如果遇到您必须测试给定 class 并且不允许更改您需要测试的 class 的情况,您可以选择使用像 PowerMock (https://github.com/powermock/powermock) 这样的框架来提供增强的模拟功能。
但请注意,不建议仅将 PowerMock 用于证明难以测试代码的合理性。 Tashkhisi 的回答是迄今为止更好的通用方法。