zoukankan      html  css  js  c++  java
  • Web Service 异常处理

    [转]:http://blog.csdn.net/21aspnet/archive/2007/03/24/1539795.aspx

    在.Net中实现Web服务时,在Web服务接口中产生的任何用户异常(非SoapException之外的异常)都被包装为SoapException 传递给客户端,这使得难以采用通常的方式处理Web Service的异常。本文讲述如何通过SoapExceptionHelper实现一致的异常处理。

    Web Service的异常处理问题
    在.Net中实现Web服务时,Web服务接口中产生的任何用户异常(非SoapException之外的异常)都被包装为SoapException传递给客户端 ,用户错误信息放置在SoapException的Message属性中。

    下面的例子演示了一个SoapException封装的用户异常信息。WebMethod接口TestException代码抛出一个InvalidOperationException:

    [WebMethod]
    public void TestException() {
    throw new InvalidOperationException("Invalid Operation.");
    }

    WebMethod的客户端将捕获一个SoapException异常,Message消息如下:



    其中Message消息包含一段“...-->[ 1 ]:[ 2 ] at ....”的信息,[1]为用户异常类,[2]为用户异常消息。而一个原始的SoapException(用new SoapException(...)的方式创建并抛出的异常)则没有这些信息,下面是一个原始的SoapException消息:



    遗憾的是,目前的SoapException并没有提供更多直接的手段直接获取原来的异常信息,唯一包含的用户异常信息在Message字符串中,对于使用 Web Service作为分布式机制的应用系统来说是非常不方便的,调用者无法捕获原来的异常,难以获取用户友好的异常信息。同时,因为Web Service接口代理不再抛出原来的异常,应用的开发者需要考虑两套完全不同的异常处理机制,带来了程序结构的复杂性。

    创建SoapException辅助类:SoapExceptionHelper
    SoapExceptionHelper辅助类包含下列主要接口:

    IsUserException:是否是一个UserException
    UserException:返回原始的UserException
    Message:原始异常的错误消息。
    获得原始的用户异常类和异常消息
    通过正则表达式类我们可以获得原始的用户异常类和异常消息:

    /// <summary>
    /// 读取UserException信息。
    /// </summary>
    private void ReadUserExceptionInfo() {
    //match user exception class
    System.Text.RegularExpressions.MatchCollection mc =
    Regex.Matches(soapException.Message, "---> ([^:]+):");
    if (mc.Count >= 1) {
    userExceptionClass = mc[0].Groups[1].Value;
    //match user exception message
    mc = Regex.Matches(soapException.Message, "---> [^:]+:(.*)\n");
    if (mc.Count > 0) UserExceptionMessage = mc[0].Groups[1].Value;
    }
    }

    创建用户异常实例
    UserException接口利用反射机制创建一个原来的Exception类实例:

    ... ...
    Assembly callingAssemply = Assembly.GetCallingAssembly();
    Type exceptionType = GetExceptionType(callingAssemply); //获得用户异常类型定义
    Exception e = null;
    try {
    try {
    e = Activator.CreateInstance(exceptionType, new object[]{UserExceptionMessage}, null) as Exception;
    }
    catch {}
    //if no exists constructor with message parameter, use no parameters constructor.
    if (e == null) e = Activator.CreateInstance(exceptionType) as Exception;
    }catch(Exception ex) {
    throw new SoapExceptionHelperException(userExceptionClass, ex);
    }

    return e;

    创建用户异常的问题
    因为用户异常可能定义在不同的集成块中,SoapExceptionHelper可能无法知道它的位置,无法正确的获取异常类型,如一个与 SoapExceptionHelper所在集成块和调用集成块(CallingAssembly)不再同一个引用范围内的异常类。 SoapExceptionHelper如果无法创建原始异常的实例,就创建一个System.Exception对象实例。

    为了创建真正的原始异常类,调用者可以在外部获得实际的异常类型,并传递给SoapExceptionHelper,因为调用者可以明确的引用异常定义 所在的集成块。示例如下:

    // 项目引用中引入异常定义所在的集成块
    ...
    SoapExceptionHelper helper = new SoapExceptionHelper(se);
    Type type = Type.GetType(helper.UserExceptionClass, "<异常类所在的集成块>");
    Exception e = helper.GetUserException(type);

    如果外部没有传递异常类型定义,SoapExceptionHelper尝试以以下顺序获取异常类型定义:

    Executing Assembly
    Calling Assembly
    Referenced Assemblies (of Calling Assembly)
    System.Exception
    使用SoapExceptionHelper
    返回用户友好的消息
    使用SoapExceptionHelper显示示例1中的错误消息:

    try {
    ... ... // call web method
    } catch (SoapException se){
    MessageBox.Show(new SoapExceptionHelper(se).Message) ; //show "Invalid Operation." string
    }
     

    屏蔽SoapException
    Web Service客户端代理类可以在捕获SoapException后重新抛出原来的异常,使用这种机制,可以有效的屏蔽Web Service异常处理的差异,使应用程序采用一致的本地方式处理异常。下面的代码修改Visual Studio生成的Web Service Client Proxy Class(Reference.cs文件)实现了这种机制(加粗的部分为新增的代码):

    [System.Web.Services.Protocols.SoapDocumentMethodAttribute("http://tempuri.org/TestException", RequestNamespace="http://tempuri.org/", ResponseNamespace="http://tempuri.org/", Use=System.Web.Services.Description.SoapBindingUse.Literal, ParameterStyle=System.Web.Services.Protocols.SoapParameterStyle.Wrapped)]
    public void TestException() {
    try{
    this.Invoke("TestException", new object[0]);
    }catch(SoapException se){
    SoapExceptionHelper helper = new SoapExceptionHelper(se);
    if (helper.IsUserException) throw helper.UserException; //rethrow user exception
    else throw;
    }

  • 相关阅读:
    Largest Rectangle in Histogram
    Valid Sudoku
    Set Matrix Zeroes
    Unique Paths
    Binary Tree Level Order Traversal II
    Binary Tree Level Order Traversal
    Path Sum II
    Path Sum
    Validate Binary Search Tree
    新手程序员 e
  • 原文地址:https://www.cnblogs.com/sainaxingxing/p/1281432.html
Copyright © 2011-2022 走看看