我试图通过带有Powermock(1.7.0RC2),Mockito2(2.4.0)和TestNG(6.8.21)的Groovy类中的new运算符来模拟实例创建。但通常的方法是行不通的。这是我的课程和考试。
public class A {
public String send() {
B b = new B();
return b.send();
}
}
public class B {
public String send() {
return "SendFromOriginB";
}
}
@PrepareForTest([A.class])
class TestConstructor extends PowerMockTestCase {
@Mock
private B bMock
@Test
void test() {
A a = new A()
given(bMock.send()).willReturn("Send from B mock")
PowerMockito.whenNew(B.class).withNoArguments().thenReturn(bMock)
assertEquals(a.send(), "Send from B mock")
}
}
问题是A类是 Groovy类。似乎 Powermock.whenNew 并不知道新B()正在调用。
因此, var b 包含B类的常用实例,而不是 mock ,并且测试失败。但是,如果A类是 Java类,则测试按预期工作, var b 包含我的模拟。 Groovy通过自己的方式创建实例,我无法正确地模拟它们。
有没有人知道如何在Groovy类中模拟实例创建?
答案 0 :(得分:0)
你明白Groovy不是Java吗?是什么让您认为适用于Java语言的构造适用于其他语言?
从这个意义上讲:您的第一步应该是使用javap来检查由Groovy为A类创建的类文件。看看那里有什么
除此之外:用工厂替换<html>
<head>
<script src="\node_modules\jquery\dist\jquery.js"></script>
<script src="node_modules\adal-angular\lib\adal.js"></script>
</head>
<body>
<button id="login"> login</button>
<button id="clickMe">click me</button>
<script>
$(function () {
var endpoints = {
"https://graph.microsoft.com": "https://graph.microsoft.com"
};
window.config = {
tenant: 'xxxx.onmicrosoft.com',
clientId: 'xxxxxxxxxxxxxxxxx',
endpoints: endpoints
};
window.authContext = new AuthenticationContext(config);
$("#login").click(function () {
window.authContext.login();
});
$("#clickMe").click(function () {
var user = window.authContext.getCachedUser();
console.log(user);
window.authContext.acquireToken('https://graph.microsoft.com', function (error, token) {
console.log(error);
console.log(token);
$.ajax({
url: 'https://graph.microsoft.com/v1.0/me/',
headers:{'authorization':'Bearer '+ token},
type:'GET',
dataType:'json'
}).done(function(res) {
console.log(res['userPrincipalName']);
});
});
}
);
function init(){
if(window.location.hash!="")
window.authContext.handleWindowCallback(window.location.hash);
}
init();
});
</script>
</body>
</html>
并允许注入该工厂允许您轻松测试,您甚至不需要PowerMock
答案 1 :(得分:0)
我有两个建议!
@CompileStatic // <- you can use on class level
public class A {
// Or you can use on method level
// depending on groovy version
@CompileStatic
public String send() {
//
}
}
此注释将删除打破PowerMock.whenNew()方法的元编程协议。
我的第二个建议是使用Spock Framework!这个框架基于BDD,当你使用groovy时,你的测试代码非常干净和可读! Spock也可以mock constructor。
spock中的测试代码可能是这样的:
def "Given an class A, when B constructor returns a mock, a must use the mock"() {
given:
String sendFromBMock = "Send from B mock"
and:
bMock.send() >> sendFromBMock
when:
new B() >> bMock
then:
a.send() == sendFromBMock
}