科技行者

行者学院 转型私董会 科技行者专题报道 网红大战科技行者

知识库

知识库 安全导航

至顶网软件频道Java异常框架设计

Java异常框架设计

  • 扫一扫
    分享文章到微信

  • 扫一扫
    关注官方公众号
    至顶头条

任何的异常都是Throwable类(为何不是接口??),并且在它之下包含两个字类Error / Exception,而Error仅在当在Java虚拟机中发生动态连接失败或其它的定位失败的时候,Java虚拟机抛出一个Error对象。

作者:builder.com.cn 来源:ccid 2008年2月18日

关键字:

  • 评论
  • 分享微博
  • 分享邮件

在本页阅读全文(共2页)

解决方案:J2EE异常框架

我们拿一个模拟的例子来说明异常框架的设计过程,比如我们要对外提供doBusiness()这个业务方法

public void doBusiness() throws xxxBusinessException

当客户端调用这样的方法的时候应该这样处理异常(包括处理RuntimeException , checked exception)
记住,无论如何我们都不希望或者确切的说是不应该将RuntimeException这样的异常暴露给客户的,因为他们没有解决这个问题的责任!
我们暂时将Struts中的某个Action看作时客户端,其中doExecute(....)要调用doBusiness()这个方法

public void doAction(......)
{
 try
 {

  xxx.doBusiness();
 }
 catch(Exception e)
 {
   if(e instanceof RuntimeException) 
   {
    // catch runtime exception
    // 你可以在这里将捕获到的RuntimeException
    // 将异常通知给某个负责此程序的程序员,让他知道他
    // 自己犯了多么低级的错误!


   }else
   {
    //checked exception such as xxxBusinessException
    //将这样的异常暴露给客户显示   

   }

 }
}

我们可以这样设计xxxBusinessException

public class xxxBusinessException extends ApplicationException
{
    public xxxBusinessException(String s){
        super(s);

};

import java.io.PrintStream;
import java.io.PrintWriter;
public class ApplicationException extends Exception {
       /** A wrapped Throwable */
       protected Throwable cause;
       public ApplicationException() {
           super("Error occurred in application.");
       }
       public ApplicationException(String message)  {
           super(message);
       }
       public ApplicationException(String message, Throwable cause)  {
           super(message);
           this.cause = cause;
       }
       // Created to match the JDK 1.4 Throwable method.
       public Throwable initCause(Throwable cause)  {
           this.cause = cause;
           return cause;
       }
       public String getMessage() {
           // Get this exception's message.
           String msg = super.getMessage();
           Throwable parent = this;
           Throwable child;
           // Look for nested exceptions.
           while((child = getNestedException(parent)) != null) {
               // Get the child's message.
               String msg2 = child.getMessage();
               // If we found a message for the child exception,
               // we append it.
               if (msg2 != null) {
                   if (msg != null) {
                       msg += ": " + msg2;
                   } else {
                       msg = msg2;
                   }
               }
               // Any nested ApplicationException will append its own
               // children, so we need to break out of here.
               if (child instanceof ApplicationException) {
                   break;
               }
               parent = child;
           }
           // Return the completed message.
           return msg;
       }
       public void printStackTrace() {
           // Print the stack trace for this exception.
           super.printStackTrace();
           Throwable parent = this;
           Throwable child;
           // Print the stack trace for each nested exception.
           while((child = getNestedException(parent)) != null) {
               if (child != null) {
                   System.err.print("Caused by: ");
                   child.printStackTrace();
                   if (child instanceof ApplicationException) {
                       break;
                   }
                   parent = child;
               }
           }
       }
       public void printStackTrace(PrintStream s) {
           // Print the stack trace for this exception.
           super.printStackTrace(s);
           Throwable parent = this;
           Throwable child;
           // Print the stack trace for each nested exception.
           while((child = getNestedException(parent)) != null) {
               if (child != null) {
                   s.print("Caused by: ");
                   child.printStackTrace(s);
                   if (child instanceof ApplicationException) {
                       break;
                   }
                   parent = child;
               }
           }
       }
       public void printStackTrace(PrintWriter w) {
           // Print the stack trace for this exception.
           super.printStackTrace(w);
           Throwable parent = this;
           Throwable child;
           // Print the stack trace for each nested exception.
           while((child = getNestedException(parent)) != null) {
               if (child != null) {
                   w.print("Caused by: ");
                   child.printStackTrace(w);
                   if (child instanceof ApplicationException) {
                       break;
                   }
                   parent = child;
               }
           }
       }
       public Throwable getCause()  {
           return cause;
       }
}

而"聪明"的读者肯定要问我那doBusiness()这个业务方法该如何包装异常呢?

 public void doBusiness() throw xxxBusinessException
 {
   try
   {
     execute1(); // if it throw exception1

     exexute2(); // if it throw exception 2

     .... .....

   }
   catch (exception1 e1)
   {
    throw new xxxBusinessException(e1);
   }
   catch(exception2 e2)
   {
    throw new xxxBusinessException(e2);
   }
   ........
 }

 也可以这样

 public void doBusiness() throw xxxBusinessException
 {
   try
   {
     execute1(); // if it throw exception1

     exexute2(); // if it throw exception 2

     .... .....

   }
   catch (Exception e)
   {
    // 注意很多应用在这里根本不判断异常的类型而一股脑的采用
    // throw new xxxBusinessException(e);
    // 而这样带来的问题就是xxxBusinessException"吞掉了"RuntimeException
    // 从而将checked excption 与unchecked exception混在了一起!

    // 其实xxxBusinessException属于checked excpetion ,它根本不应该也不能够理睬RuntimeException
    if(! e instanceof RuntimeException) throw new xxxBusinessException(e);
   }
 }


总结
 1。JAVA的异常分为两类: checked exception & unchecked excpetion
 2。应用开发中产生的异常都应该集成自Exception 但都属于checked excpetion类型
 3。应用中的每一层在包装并传递异常的时候要过滤掉RuntimeException!
 4。从责任这个角度看Error属于JVM需要负担的责任;RuntimeException是程序应该负担的责任;checked exception 是具体应用负担的责任
 5。无论如何我们都不希望或者确切的说是不应该将RuntimeException这样的异常暴露给客户的,因为他们没有解决这个问题的责任!

    • 评论
    • 分享微博
    • 分享邮件
    邮件订阅

    如果您非常迫切的想了解IT领域最新产品与技术信息,那么订阅至顶网技术邮件将是您的最佳途径之一。

    重磅专题
    往期文章
    最新文章