Java 在Jmockit mock对象中使用另一个对象作为参数

Java 在Jmockit mock对象中使用另一个对象作为参数,java,spring,unit-testing,junit,jmockit,Java,Spring,Unit Testing,Junit,Jmockit,我是JMockit的新手,已经成功地使用它运行了一个基本单元测试。然而,我在尝试模拟Spring LdapTemplate时遇到了麻烦。问题似乎出在LdapTemplate使用的LdapQuery上。我也需要嘲笑这个吗 JUnit测试 @RunWith(JMockit.class) public class MyTest { @Mocked LdapTemplate mockLdapTemplate; @Test public void retrieveAcc

我是JMockit的新手,已经成功地使用它运行了一个基本单元测试。然而,我在尝试模拟Spring LdapTemplate时遇到了麻烦。问题似乎出在LdapTemplate使用的LdapQuery上。我也需要嘲笑这个吗

JUnit测试

@RunWith(JMockit.class)
public class MyTest {

    @Mocked
    LdapTemplate mockLdapTemplate;

    @Test
    public void retrieveAccount_test() {

        Account acct = new Account();
        acct.setEmail("foobar@gmail.com");
        acct.setUserId("userA");
        final List<Account> expected = Arrays.asList(acct);

        new Expectations() {
            { 
              mockLdapTemplate.search(query().base(anyString).where(anyString)
                    .is("userA"), (AttributesMapper) any);
              result = expected;
            }
        };
        AccountService service = new AccountServiceImpl(mockLdapTemplate);
        Account account = service.retrieveAccount("userA");
        assertThat(account, is(notNullValue()));
    }
}
@RunWith(JMockit.class)
公共类MyTest{
@嘲弄
LdapTemplate mockLdapTemplate;
@试验
公共无效检索帐户测试(){
账户账户=新账户();
帐户设置电子邮件(“foobar@gmail.com");
账户setUserId(“userA”);
预期最终列表=Arrays.asList(acct);
新期望(){
{ 
mockLdapTemplate.search(query().base(anyString).where(anyString)
.是(“用户A”),(属性标记)任何);
结果=预期;
}
};
AccountService服务=新AccountServiceImpl(mockLdapTemplate);
Account=service.retrieveAccount(“userA”);
资产(账户,是(notNullValue());
}
}
会计服务

public class AccountServiceImpl implements AccountService {

private LdapTemplate ldapTemplate;

@Autowired
public AccountServiceImpl(LdapTemplate ldapTemplate) {
    this.ldapTemplate = ldapTemplate;
}

@Override
public Account retrieveAccount(String userId) {
    LdapQuery query = query().base("ou=users").where("uid").is(userId);
    List<Account> list = ldapTemplate.search(query,
            new AccountMapper());
    if (list != null && !list.isEmpty()) {
        return list.get(0);
    }

    return null;
}

public class AccountMapper implements
        AttributesMapper<Account> {

    @Override
    public Account mapFromAttributes(Attributes attrs)
            throws NamingException {
        Account account = new Account();
        account.setEmail((String) attrs.get("mail").get());
        account.setUserId((String) attrs.get("uid").get());

        return account;
    }
}
}
公共类AccountServiceImpl实现AccountService{
私有LdapTemplate LdapTemplate;
@自动连线
公共帐户ServiceImpl(LdapTemplate LdapTemplate){
this.ldapTemplate=ldapTemplate;
}
@凌驾
公共帐户检索帐户(字符串用户ID){
LdapQuery query=query().base(“ou=users”)。其中(“uid”)是(userId);
List List=ldapTemplate.search(查询,
新的AccountMapper());
if(list!=null&&!list.isEmpty()){
返回列表。获取(0);
}
返回null;
}
公共类AccountMapper实现
属性映射{
@凌驾
公共帐户mapFromAttributes(属性属性属性)
抛出NamingException{
账户=新账户();
account.setEmail((字符串)attrs.get(“mail”).get();
account.setUserId((字符串)attrs.get(“uid”).get();
返回帐户;
}
}
}
(省略Account类,因为它应该是自解释的。)

如果替换
mockLdapTemplate.search(query().base(anyString).where(anyString)
.是(“用户A”),(属性标记)任何)mockLdapTemplate.search((LdapQuery)withNotNull(),(AttributesMapper)any)
测试通过(这是我所期望的,但这或多或少告诉我问题出在LdapQuery参数上)


谢谢

你已经知道答案了:期望值应该记录为

mockLdapTemplate.search((LdapQuery)withNotNull(), (AttributesMapper) any)

因为这是从测试单元调用的唯一模拟方法。参数匹配器“any”、“withNotNull()”等只能用于对模拟方法的调用,并且测试中未模拟
LdapQuery

好的。所以我需要模拟LdapQuery?你能举个例子吗?当我传入“userA”参数时,我的测试在is()方法中。基本上没有这个,测试不会真正测试任何东西;一种可能的替代方法(取决于查询对象中合适的“getter”的可用性)是捕获传递给
search
方法的查询对象,使用
qry=withCapture()
作为参数匹配器(使用局部变量
LdapQuery qry
)。另一种选择是使用Spring的
org.springframework.ldap.test
facilities.Thank编写集成测试。我会试试第一个。