在 JUnit 的 for 循环中模拟 if 条件
Mocking an if condition within a for loop in JUnit
我正在尝试使用 Mockito 和 JUnit 模拟一个方法。出于某种原因,尽管测试满足 if 语句,但它一直说永远不会调用嵌入式方法。
这是我正在测试的方法:
public List<LifeProduct> prune(List<LifeProduct> products) {
for (LifeProduct product : products) {
int id = product.getProductAnalyticsIdentifier();
boolean deleteAnnuity = id > 10014;
boolean deleteLifeInsurance = product.getLifeInsurance()
.getHighLevelLifeInsuranceGroupName()
.equals("string");
if (deleteAnnuity) {
annuityService.deleteAnnuityById(id);
}
if (deleteLifeInsurance) {
lifeInsuranceService.deleteLifeInsuranceById(id);
}
}
return products;
}
这是我对迭代器设置的测试:
@Before
public void setUp() throws Exception {
MockitoAnnotations.initMocks(this);
when(mockList.iterator()).thenReturn(mockIterator);
when(mockIterator.hasNext()).thenReturn(true, false);
when(mockIterator.next()).thenReturn(mockProduct);
}
@Test
public final void testPrune() throws Exception {
for (LifeProduct mockProduct : mockList) {
mockProduct.setProductAnalyticsIdentifier(99999999);
doNothing().when(annuityService).deleteAnnuityById(anyInt());
List<LifeProduct> response = lifeProductDelegate.prune(mockList);
assertNotNull(response);
verify(annuityService).deleteAnnuityById(anyInt());
}
}
您的测试有两个问题:
您正在使用 mockList
,因此使用 mockIterator.hasNext()
的两个值之一
你说调用mockIterator.hasNext()
时应该先returntrue
再false
。这里的问题是您的测试方法遍历 mockList
,因此需要调用 mockIterator.hasNext()
,然后使用第一个 true
值。被测试的方法 #prune()
然后也尝试迭代列表,但只会得到第二个,即 false
值,从而跳过循环。您的测试方法中不需要循环,因此您可以而且应该将其删除。
您设置错误mockProduct
第二期mockProduct.setProductAnalyticsIdentifier(99999999)
。 mockProduct
是一个模拟,因此当未通过 when(mockProduct...)...
配置时,这些方法不会执行任何操作。所以值 99999999 没有存储在任何地方并且 #getProductAnalyticsIdentifier()
在测试中 returns 0,默认值。你真正想要做的是配置 getter 方法,例如:
when(mockProduct.getProductAnalyticsIdentifier()).thenReturn(999999);
现在 mockProduct
将 return 当 #prune()
请求 id 并稍后将其与 10014 进行比较时的值。
我正在尝试使用 Mockito 和 JUnit 模拟一个方法。出于某种原因,尽管测试满足 if 语句,但它一直说永远不会调用嵌入式方法。
这是我正在测试的方法:
public List<LifeProduct> prune(List<LifeProduct> products) {
for (LifeProduct product : products) {
int id = product.getProductAnalyticsIdentifier();
boolean deleteAnnuity = id > 10014;
boolean deleteLifeInsurance = product.getLifeInsurance()
.getHighLevelLifeInsuranceGroupName()
.equals("string");
if (deleteAnnuity) {
annuityService.deleteAnnuityById(id);
}
if (deleteLifeInsurance) {
lifeInsuranceService.deleteLifeInsuranceById(id);
}
}
return products;
}
这是我对迭代器设置的测试:
@Before
public void setUp() throws Exception {
MockitoAnnotations.initMocks(this);
when(mockList.iterator()).thenReturn(mockIterator);
when(mockIterator.hasNext()).thenReturn(true, false);
when(mockIterator.next()).thenReturn(mockProduct);
}
@Test
public final void testPrune() throws Exception {
for (LifeProduct mockProduct : mockList) {
mockProduct.setProductAnalyticsIdentifier(99999999);
doNothing().when(annuityService).deleteAnnuityById(anyInt());
List<LifeProduct> response = lifeProductDelegate.prune(mockList);
assertNotNull(response);
verify(annuityService).deleteAnnuityById(anyInt());
}
}
您的测试有两个问题:
您正在使用 mockList
,因此使用 mockIterator.hasNext()
的两个值之一
你说调用mockIterator.hasNext()
时应该先returntrue
再false
。这里的问题是您的测试方法遍历 mockList
,因此需要调用 mockIterator.hasNext()
,然后使用第一个 true
值。被测试的方法 #prune()
然后也尝试迭代列表,但只会得到第二个,即 false
值,从而跳过循环。您的测试方法中不需要循环,因此您可以而且应该将其删除。
您设置错误mockProduct
第二期mockProduct.setProductAnalyticsIdentifier(99999999)
。 mockProduct
是一个模拟,因此当未通过 when(mockProduct...)...
配置时,这些方法不会执行任何操作。所以值 99999999 没有存储在任何地方并且 #getProductAnalyticsIdentifier()
在测试中 returns 0,默认值。你真正想要做的是配置 getter 方法,例如:
when(mockProduct.getProductAnalyticsIdentifier()).thenReturn(999999);
现在 mockProduct
将 return 当 #prune()
请求 id 并稍后将其与 10014 进行比较时的值。