背景
在我的Oracle数据库中,我有大量可能导致异常的数据库调用。我目前有所有这些的异常处理程序,它们调用错误包。简而言之,最终会针对预期错误引发raise_application_error
,或者针对意外错误引发raise
,并将其发送回调用Java Groovy / Grails应用程序层。
因此,例如,如果用户输入id并单击搜索,我将从数据库运行select查询。如果该ID不存在,我会遇到NO_DATA_FOUND
异常,该异常执行带有自定义错误消息的raise_application_error
(即“无法找到输入的ID”。)
然而,应用程序开发团队表示他们正在努力解决这个问题。他们正在尝试在Groovy中执行单元测试,理想情况下需要返回一个变量。我当前返回的SQL异常导致所有测试失败,因为它是一个例外。他们的代码如下:
void nameOfProcedure() {
String result = storedProcedure.callDBProcedure(ConnectionType.MSSQL, val1, val2)
log.info "SQL Procedure query result value: "+ result
assertEquals("1", result)
}
他们可以在测试上面添加这样的东西:
@Test (expected = SQLException.class)
但这意味着所有返回的SQLExceptions都会通过,无论它们是否是针对当前问题的正确例外。
问题:
这个问题的最佳解决方案是什么?我被迫从我的异常块中返回变量,而不是raise_application_errors - 但是我非常不愿意这样做,因为我一直被告知这只是一种可怕的做法。或者,他们可以在结束时做出改变,但显然不愿意。
下一步是什么?我应该编码将“预期”错误作为变量返回,而不是异常吗?例如,如果有人输入了未找到的ID:
BEGIN
SELECT id
FROM table
WHERE id = entered_id
EXCEPTION
WHEN NO DATA FOUND THEN
RETURN 'ID cannot be found';
END
或者,他们是否应该遵循指南like this,该指南建议使用Hamcrest匹配器创建自己的自定义异常属性,他们可以在JUnit测试中检查它们。这里的最佳做法是什么?
答案 0 :(得分:0)
你是对的,这是一种可怕的做法。只是'wagging the dog';他们懒得工作,并希望你破坏应用程序设计以取悦他们。
通常,返回异常的单元测试应如下所示:
try {
String result = callDBProcedure();
fail("Result instead of exception");}
catch (OracleSQLException e) {
assertEquals(e.errorCode, RAISE_APPLICATION_ERROR_CODE);}
catch (Throwable t) {
fail("Unexpected error");
}
他们可以按照自己的意愿升级。例如,他们可以开发程序'调用SP并将异常转换为他们想要的任何东西'并在测试中使用它。但它们不应影响测试之外的应用程序设计。从不。