[英]Can I write any meaningful unit test in this scenario?
我有這個實體 -
public class MerchantConfig {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
private Long merchantId;
private String configKey;
private String configValue;
..
}
它目前在商家級別存儲配置(鍵和值)。
我們現在也需要在用戶級別(用戶到商家的一對多映射)存儲配置。
我們將這兩列添加到實體中 -
private Long entityId;
private String entityType;
entityId 現在將存儲merchantId/UserId,entityType 將與字符串值“merchantid”或“user_id”指示相同。
這是一個現有的服務層方法 -
public MerchantConfig enableSync(boolean isActive, Long merchantId,boolean isSync){
MerchantConfig merchantConfig= merchantConfigRespository.findByMerchantIdAndConfigKey(merchantId,Constants.MerchantConfigKeys.SYNC_ENABLED.key);
if(merchantConfig==null){
merchantConfig = new MerchantConfig();
merchantConfig.setMerchantId(merchantId);
merchantConfig.setConfigKey(Constants.MerchantConfigKeys.SYNC_ENABLED.key);
}
if(isSync)
merchantConfig.setConfigValue("1");
else
merchantConfig.setConfigValue("0");
merchantConfig.setIsActive(isActive);
return merchantConfigRespository.save(merchantConfig);
}
這是上面的 controller -
@PostMapping("/admin/enableSync")
public ResponseEntity<Object> enableSync(HttpServletRequest request, HttpServletResponse response,
@RequestParam("merchantId") Long merchantId,
@RequestParam("isValid") boolean isValid,
@RequestParam("isSync") boolean isSync) {
if (isValid && isSync)
LOGGER.info("enabling sync for merchant {}", merchantId);
else
LOGGER.info("disabling sync for merchant {}", merchantId);
MerchantConfig merchantConfig = merchantConfigService.enableSync(isValid, merchantId, isSync);
if(merchantConfig!=null)
return new ResponseEntity<>(new ResponseDTO(Constants.API_RESPONSE_SUCCESS, merchantConfig, "success"),
HttpStatus.OK);
return new ResponseEntity<>(new ResponseDTO(Constants.API_RESPONSE_FAILURE, "unable to enable sync"),
HttpStatus.OK);
}
我們決定只更改服務並向下更改,保持 controller 層不變。
用服務方法中的 findByEntityIdAndEntityTypeAndConfigKey() 替換存儲庫方法調用 findByMerchantIdAndConfigKey() 並進行此更改 -
public MerchantConfig enableSync(boolean isActive, Long merchantId,boolean isSync){
MerchantConfig merchantConfig= merchantConfigRespository.findByEntityIdAndEntityTypeAndConfigKey(merchantId,Enum.MerchantConfigType.MERCHANT_ID.v,Constants.MerchantConfigKeys.SYNC_ENABLED.key);
if(merchantConfig==null){
merchantConfig = new MerchantConfig();
merchantConfig.setEntityId(merchantId);
merchantConfig.setEntityType(Enum.MerchantConfigType.MERCHANT_ID.v);
merchantConfig.setConfigKey(Constants.MerchantConfigKeys.SYNC_ENABLED.key);
}
if(isSync)
merchantConfig.setConfigValue("1");
else
merchantConfig.setConfigValue("0");
merchantConfig.setIsActive(isActive);
return merchantConfigRespository.save(merchantConfig);
}
我在服務層放了什么有用的單元測試用例?
如果我要模擬存儲庫層響應並驗證 servive 方法是否返回與模擬響應相同的 MerchantConfig 實體,這不是矯枉過正嗎?
相反,我覺得測試 db 值會更有用,方法是在 db 中創建一些已知條目。 例如,在這種情況下,當 db 中已經有一些商家級別的配置並且要輸入用戶級別的配置時,應該覆蓋用戶級別的條目,因為配置器正在嘗試取消設置所有商家級別的配置。
測試是否在 db 中給定商家級別的配置會很有用,當調用保存配置 API 端點來保存用戶級別的配置時,商家級別的配置被標記為非活動狀態。
順便問一下,這些測試叫什么? 請給出一些解決方案,因為我已經在這場辯論中苦苦掙扎了一段時間。 每次坐下來寫傳統的單元測試用例,我都花太多時間,還是有問題,這是單元測試無法覆蓋的。 請提供一些全面的指南來編寫此類測試。
首先,感謝您的提問,這是一個很好的問題。 這讓我思考。 現在關於答案...
如果有任何科學證明是編寫測試的唯一正確方法,我不知道。 作為專業人士,您將不得不撥打電話。 如果我是你,我會考慮以下幾點:
選項 1我使用的經驗法則是,如果某些東西可以通過單元測試進行測試,那么它應該通過單元測試進行測試,除非我有充分的理由不這么認為。 這是我個人的選擇,原因如下:
選項 2現在,在我看來,使用集成測試而不是單元測試的唯一正當理由是某些東西非常難以/不可能以其他方式進行測試。 只有當我完全確定這部分邏輯永遠不會再改變時,我可能會在你的情況下選擇這個,但我認為情況並非如此。
現在我們可以提出選項 3 :它確實看起來像enableSync
對許多事情所做的(即創建/查找 object 並切換同步標志)
如果您將下面的代碼提取到一個單獨的方法中(比如說,構建merchantConfig
):
MerchantConfig merchantConfig=
if(merchantConfig==null){
merchantConfig = new MerchantConfig();
merchantConfig.setEntityId(merchantId);
merchantConfig.setEntityType(Enum.MerchantConfigType.MERCHANT_ID.v);
merchantConfig.setConfigKey(Constants.MerchantConfigKeys.SYNC_ENABLED.key);
}
這應該很容易進行單元測試,並且不需要數據庫交互或 mocking。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.