如何使用 JMockit 模拟 DAO 层?
How Do I mock a DAO Layer using JMockit?
我正在尝试模拟一个看起来像这样的 DAO 层接口...
public interface DummyDAO{
public List<VO> getSearchCriteria(String Id, Integer version) throws Exception;
}
在实现部分,我 运行 一个查询,它根据该查询为我获取了一个值对象列表。我如何模拟来自数据库的 VO 列表。有没有简单的方法可以做到这一点?我正试图鼓励我的团队使用 Jmockit,但我仍然是这个模拟工具的新手。如果您需要更多信息,请告诉我。
谢谢
一种简单的方法是使用 Mockito.spy() 。间谍方法创建实例的代理,让您有机会模拟一种方法的行为。
您可以创建一个列表,当您调用您的 dao 方法时将返回该列表。
示例:
yourDao = spy(new YourDaoImplementation())
doReturn(yourExampleList).when(yourDao).getSearchCriteria(any(String.class), any(Integer.class));
如果你真的想测试你的dao,你可以使用一个轻量级的数据库如HSQLDB
这里的答案部分取决于 CUT(被测代码)如何使用 List<VO>
。例如,如果您的代码是 RESTful 服务,仅充当代理并将此 List<VO>
返回给用户,而不检查内容或任何内容,那么这就足够了:
@Tested CUT cut;
@Injectable DummyDAO dao;
@Injectable List<VO> res;
@Test
public void testSomething() throws Exception {
new Expectations() {{
dao.getSearchCriteria(anyString, anyInt); result = res;
}};
List<VO> output = cut.methodBeingTested();
// assertions go here, like that output and res are the same
// you can also put Verifications here
}
如果您希望对 VO
进行分析,那么事情会变得更加复杂,例如:
@Tested CUT cut;
@Injectable DummyDAO dao;
@Mocked VO vo;
@Test
public void testSomething() throws Exception {
final List<VO> res = new ArrayList<VO>();
Collections.addAll(res, vo, vo, vo, vo);
new Expectations() {{
dao.getSearchCriteria(anyString, anyInt); result = res;
}};
new Expectations(4) {{
vo.getFoo(); returns(5, 47, 13, -7);
}};
cut.methodBeingTested();
// assertions go here, like that you handled the negative number properly
// you can also put Verifications here
}
注意这里我没有模拟 List
—— 如果你正在做更复杂的操作,最好坚持使用真正的 List
而不必模拟它的所有操作。我模拟了一个 VO 并多次将它添加到列表中——这没关系,因为每次检查它时它的行为都会不同,因此看起来是不同的 VO
.
考试,因为它发生了 4 次,所以我搬到了另一个 Expectations
区块,因为你期望它发生 4 次。我这样做只是为了炫耀期望块,因为在这种情况下,可以通过在原始块中包含 vo.getFoobar(); times=4; returns(5, 47, 13, -7);
来轻松完成……或者,第二个块可能看起来像
new StrictExpectations(4) {{
vo.getFoo(); returns(5, 47, 13, -7);
vo.getBar(); returns("foo", "bar", "baz", "quux");
}};
在这种情况下,times
字段将不起作用,您必须将它放在一个单独的块中 - 这个块表示它希望有 getFoo()
和 getBar()
调用,交替,恰好 4 次——如果遍历列表并每次都查看两个属性,你会想要这样做。
希望我已经给了你深思;在不了解更多您的具体用例的情况下,我自己不能更具体。
我正在尝试模拟一个看起来像这样的 DAO 层接口...
public interface DummyDAO{
public List<VO> getSearchCriteria(String Id, Integer version) throws Exception;
}
在实现部分,我 运行 一个查询,它根据该查询为我获取了一个值对象列表。我如何模拟来自数据库的 VO 列表。有没有简单的方法可以做到这一点?我正试图鼓励我的团队使用 Jmockit,但我仍然是这个模拟工具的新手。如果您需要更多信息,请告诉我。
谢谢
一种简单的方法是使用 Mockito.spy() 。间谍方法创建实例的代理,让您有机会模拟一种方法的行为。
您可以创建一个列表,当您调用您的 dao 方法时将返回该列表。
示例:
yourDao = spy(new YourDaoImplementation())
doReturn(yourExampleList).when(yourDao).getSearchCriteria(any(String.class), any(Integer.class));
如果你真的想测试你的dao,你可以使用一个轻量级的数据库如HSQLDB
这里的答案部分取决于 CUT(被测代码)如何使用 List<VO>
。例如,如果您的代码是 RESTful 服务,仅充当代理并将此 List<VO>
返回给用户,而不检查内容或任何内容,那么这就足够了:
@Tested CUT cut;
@Injectable DummyDAO dao;
@Injectable List<VO> res;
@Test
public void testSomething() throws Exception {
new Expectations() {{
dao.getSearchCriteria(anyString, anyInt); result = res;
}};
List<VO> output = cut.methodBeingTested();
// assertions go here, like that output and res are the same
// you can also put Verifications here
}
如果您希望对 VO
进行分析,那么事情会变得更加复杂,例如:
@Tested CUT cut;
@Injectable DummyDAO dao;
@Mocked VO vo;
@Test
public void testSomething() throws Exception {
final List<VO> res = new ArrayList<VO>();
Collections.addAll(res, vo, vo, vo, vo);
new Expectations() {{
dao.getSearchCriteria(anyString, anyInt); result = res;
}};
new Expectations(4) {{
vo.getFoo(); returns(5, 47, 13, -7);
}};
cut.methodBeingTested();
// assertions go here, like that you handled the negative number properly
// you can also put Verifications here
}
注意这里我没有模拟 List
—— 如果你正在做更复杂的操作,最好坚持使用真正的 List
而不必模拟它的所有操作。我模拟了一个 VO 并多次将它添加到列表中——这没关系,因为每次检查它时它的行为都会不同,因此看起来是不同的 VO
.
考试,因为它发生了 4 次,所以我搬到了另一个 Expectations
区块,因为你期望它发生 4 次。我这样做只是为了炫耀期望块,因为在这种情况下,可以通过在原始块中包含 vo.getFoobar(); times=4; returns(5, 47, 13, -7);
来轻松完成……或者,第二个块可能看起来像
new StrictExpectations(4) {{
vo.getFoo(); returns(5, 47, 13, -7);
vo.getBar(); returns("foo", "bar", "baz", "quux");
}};
在这种情况下,times
字段将不起作用,您必须将它放在一个单独的块中 - 这个块表示它希望有 getFoo()
和 getBar()
调用,交替,恰好 4 次——如果遍历列表并每次都查看两个属性,你会想要这样做。
希望我已经给了你深思;在不了解更多您的具体用例的情况下,我自己不能更具体。