从Oracle策略返回有意义的错误
我有一个Oracle策略,有一次我想停止处理并返回一个有意义的错误给Hibernate,由Oracle JDBC支持 在我的策略中,当看到某个错误时,我会执行以下操作:从Oracle策略返回有意义的错误,oracle,Oracle,我有一个Oracle策略,有一次我想停止处理并返回一个有意义的错误给Hibernate,由Oracle JDBC支持 在我的策略中,当看到某个错误时,我会执行以下操作: RAISE_APPLICATION_ERROR( -20001, 'Unauthorized' ); 注意,消息可以是任何内容,这只是一个示例 这很好,策略停止执行,SQL调用也停止,并返回调用函数(即Hibernate) 在JDBC驱动程序中,虽然我的代码和错误已从异常信息中删除: ]]ServletException的根本
RAISE_APPLICATION_ERROR( -20001, 'Unauthorized' );
注意,消息可以是任何内容,这只是一个示例
这很好,策略停止执行,SQL调用也停止,并返回调用函数(即Hibernate)
在JDBC驱动程序中,虽然我的代码和错误已从异常信息中删除:
]]ServletException的根本原因。
org.hibernate.exception.genericjdbception:无法提取
结果集在
org.hibernate.exception.internal.StandardSQLExceptionConverter.convert(StandardSQLExceptionConverter.java:54)
在
org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:126)
在
org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:112)
在
org.hibernate.engine.jdbc.internal.ResultSetReturnImpl.extract(ResultSetReturnImpl.java:91)
位于org.hibernate.loader.loader.getResultSet(loader.java:2066)
截断的。有关由以下原因导致的完整堆栈跟踪,请参阅日志文件:
java.sql.SQLException:ORA-28112:无法执行策略函数
位于的oracle.jdbc.driver.t4cttiore.processError(t4cttiore.java:450)
位于的oracle.jdbc.driver.t4cttiore.processError(t4cttiore.java:399)
位于的oracle.jdbc.driver.T4C8Oall.processError(T4C8Oall.java:1059)
oracle.jdbc.driver.T4CTTIfun.receive(T4CTTIfun.java:522)位于
oracle.jdbc.driver.T4CTTIfun.doRPC(T4CTTIfun.java:257)被截断。看见
完整堆栈跟踪的日志文件
深入研究JDBC驱动程序my-20001错误和“Unauthorized”一词已不复存在。有没有办法向调用程序返回有意义的错误?或者,似乎是“策略封送器”的程序是否会将所有异常重新包装到另一个错误中
这是向调用程序返回正确故障的最佳方法还是有更好的方法
我不想返回任何结果,因为这意味着一切正常,我想返回一个正确的错误
更新:
使用@a1ex07中的异常捕捉器,我看到错误真的消失了,并且在它的位置上存在一个“流程策略”错误。确切的堆栈跟踪如下所示:
public List<Tag> findBy(Long termId, String tagName) {
try {
Criteria criteria = sessionFactory.getCurrentSession().createCriteria(Tag.class)
.createAlias("tagTerms", "tagTerms");
if (tagName != null) {
criteria.add(Restrictions.eq("tagName", tagName));
}
//termId not used yet
criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY)
return criteria.list();
} catch (RuntimeException re) {
//SQL error is from the oracle policy and not anything else.
log.error("get failed ", re);
throw re;
}
}
位于的oracle.jdbc.driver.t4cttiore.processError(t4cttiore.java:450)
位于的oracle.jdbc.driver.t4cttiore.processError(t4cttiore.java:399)
位于的oracle.jdbc.driver.T4C8Oall.processError(T4C8Oall.java:1059)
oracle.jdbc.driver.T4CTTIfun.receive(T4CTTIfun.java:522)位于
oracle.jdbc.driver.T4CTTIfun.doRPC(T4CTTIfun.java:257)位于
位于的oracle.jdbc.driver.T4C8Oall.doOALL(T4C8Oall.java:587)
oracle.jdbc.driver.T4CPreparedStatement.doOall8(T4CPreparedStatement.java:225)
在
oracle.jdbc.driver.T4CPreparedStatement.doOall8(T4CPreparedStatement.java:53)
在
oracle.jdbc.driver.T4CPreparedStatement.executeforderdescripe(T4CPreparedStatement.java:774)
在
oracle.jdbc.driver.OracleStatement.executeMaybeDescribe(OracleStatement.java:925)
在
oracle.jdbc.driver.OracleStatement.doExecuteWithTimeout(OracleStatement.java:1111)
在
oracle.jdbc.driver.OraclePreparedStatement.executeInternal(OraclePreparedStatement.java:4798)
在
oracle.jdbc.driver.OraclePreparedStatement.executeQuery(OraclePreparedStatement.java:4845)
在
OraclePreparedStatementWrapper.executeQuery(OraclePreparedStatementWrapper.java:1501)
在
weblogic.jdbc.wrapper.PreparedStatement.executeQuery(PreparedStatement.java:144)
在
org.hibernate.engine.jdbc.internal.ResultSetReturnImpl.extract(ResultSetReturnImpl.java:82)
在这一点上:
oracle.jdbc.driver.t4cttiore.processError(t4cttiore.java:450)
仍然没有我的-20001或文本的迹象。看起来驱动程序完全删除了我的异常,并用它自己的平淡异常替换它
更新:
调用Hibernate的代码如下所示:
public List<Tag> findBy(Long termId, String tagName) {
try {
Criteria criteria = sessionFactory.getCurrentSession().createCriteria(Tag.class)
.createAlias("tagTerms", "tagTerms");
if (tagName != null) {
criteria.add(Restrictions.eq("tagName", tagName));
}
//termId not used yet
criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY)
return criteria.list();
} catch (RuntimeException re) {
//SQL error is from the oracle policy and not anything else.
log.error("get failed ", re);
throw re;
}
}
public List findBy(长期ID,字符串标记名){
试一试{
Criteria=sessionFactory.getCurrentSession().createCriteria(Tag.class)
.createAlias(“标记语”、“标记语”);
if(标记名!=null){
criteria.add(Restrictions.eq(“标记名”,tagName));
}
//termId尚未使用
criteria.setResultTransformer(criteria.DISTINCT\u ROOT\u实体)
返回条件。list();
}捕获(运行时异常re){
//SQL错误来自oracle策略,而不是其他任何原因。
log.error(“获取失败”,re);
投掷re;
}
}
标记是标准的Hibernate实体
我目前已恢复使用空结果集,至少不会导致常规SQL错误。我觉得这是不可能的,因为错误不会被传输回调用过程
希望社区能提供帮助。我认为问题不在于Oracle,而在于如何从Hibernate引发的异常中检索错误代码
exception.getCause()
或exception.getCause().getCause()
应包含来自RAISE\u APPLICATION\u error
的错误代码。例如,您的异常处理程序(Java示例)可能如下所示
public void handleSQLException(Exception e) throws ECustomException
{
SQLException se = null;
if (null != e.getCause() )
{
if (e.getCause() instanceof SQLException )
{
se = (SQLException)e.getCause();
}
if (null != e.getCause().getCause() && e.getCause().getCause() instanceof SQLException )
{
se = (SQLException)e.getCause().getCause();
}
}
if (null != se)
{
int eCode = se.getErrorCode();
if (eCode >0)
{
eCode = -eCode;
}
switch (eCode)
{
case -20001 :
throw new EInvalidPolicy(se);
--handling other defined other error codes
default :
throw new RuntimeException(e);
}
}
else
{
throw new RuntimeException(e);
}
}
在我看来,问题不在于Oracle,而在于如何从Hibernate引发的异常中检索错误代码
exception.getCause()
或exception.getCause().getCause()
应包含来自RAISE\u APPLICATION\u error
的错误代码。例如,您的异常处理程序(Java示例)可能如下所示
public void handleSQLException(Exception e) throws ECustomException
{
SQLException se = null;
if (null != e.getCause() )
{
if (e.getCause() instanceof SQLException )
{
se = (SQLException)e.getCause();
}
if (null != e.getCause().getCause() && e.getCause().getCause() instanceof SQLException )
{
se = (SQLException)e.getCause().getCause();
}
}
if (null != se)
{
int eCode = se.getErrorCode();
if (eCode >0)
{
eCode = -eCode;
}
switch (eCode)
{
case -20001 :
throw new EInvalidPolicy(se);
--handling other defined other error codes
default :
throw new RuntimeException(e);
}
}
else
{
throw new RuntimeException(e);
}
}
请参阅我的进一步解释,虽然您的代码帮助我检查,但似乎错误已经消失。我将查看是否有任何其他方法可以从策略中返回此错误以外的内容,但是这种方法似乎根本没有机会。您可以添加调用Oracle sta的代码吗