设置自定义异常的消息,而不将其传递给基础构造函数

Dir*_*oer 51 c# exception visual-studio visual-studio-2012

我想在C#中创建一个自定义Exception,但理论上我需要先做一点解析才能创建一个人类可读的ExceptionMessage.

问题是原始Message只能通过调用基础构造函数来设置Messsage,所以我不能提前做任何解析.

我尝试过像这样覆盖Message属性:

public class CustomException : Exception
{
    string _Message;

    public CustomException(dynamic json) : base("Plep")
    {
        // Some parsing to create a human readable message (simplified)
        _Message    = json.message;
    }

    public override string Message
    {
        get { return _Message; }
    }
}
Run Code Online (Sandbox Code Playgroud)

问题是Visual Studio调试器仍然显示我传递给构造函数的消息,在这种情况下是Plep.

throw new CustomException( new { message="Show this message" } )
Run Code Online (Sandbox Code Playgroud)

结果是:

Visual Studio异常对话框

如果我将基础构造函数留空,它将显示一条非常通用的消息:

App.exe中出现未处理的"App.CustomException"类型异常

看起来Exception Dialog读取了一些我也没有访问权限的字段/属性.是否有任何其他方法可以在Exception的基础构造函数外部设置人类可读的错误消息.

请注意,我正在使用Visual Studio 2012.

Seb*_*edl 93

只需将格式代码放入静态方法中?

public CustomException(dynamic json) : base(HumanReadable(json)) {}
private static string HumanReadable(dynamic json) {
    return whatever you need to;
}
Run Code Online (Sandbox Code Playgroud)

  • 完善!甚至不知道你实际上可以在基础构造函数的arguments部分中调用静态方法! (3认同)
  • 啊..必须等待19个小时才能给你奖励.非常酷,设置赏金实际上确实有效;) (2认同)

nvo*_*igt 17

考虑用于创建新例外的Microsoft准则:

  using System;
  using System.Runtime.Serialization;

  [Serializable]
  public class CustomException : Exception
  {
    //
    // For guidelines regarding the creation of new exception types, see
    //    https://msdn.microsoft.com/en-us/library/ms229064(v=vs.100).aspx
    //

    public CustomException()
    {
    }

    public CustomException(string message) : base(message)
    {
    }

    public CustomException(string message, Exception inner) : base(message, inner)
    {
    }

    protected CustomException(SerializationInfo info, StreamingContext context) : base(info, context)
    {
    }

    public static CustomException FromJson(dynamic json)
    {
      string text = ""; // parse from json here

      return new CustomException(text);
    }
  }
Run Code Online (Sandbox Code Playgroud)

请注意您可以在程序中使用的静态工厂方法(不是模式的一部分),如下所示:

throw CustomException.FromJson(variable);
Run Code Online (Sandbox Code Playgroud)

这样你就可以遵循最佳实践并在异常类中解析你的json.

  • 这可行..但在某种程度上,你仍然在努力工作.我从来没有通过调用静态方法抛出异常 - 默认的.NET异常也没有静态方法来调用它们.我宁愿不这样做,因为对于其他程序员来说它不是很容易被发现. (6认同)
  • 评论中的两个链接都被破坏了.新链接:[例外设计指南](https://msdn.microsoft.com/en-us/library/ms229014(v = vs.100).aspx) (2认同)

Fer*_*cio 9

我认为问题可能出在Visual Studio调试器上.我得到了使用调试器的相同结果,但是当我打印消息时:

class CustomException : Exception {
    public CustomException(dynamic json)
        : base("Plep") {
            _Message = json.message;
    }

    public override string Message {
        get { return _Message; }
    }

    private string _Message;
}

class Program {
    static void Main(string[] args) {
        try {
            throw new CustomException(new { message = "Show this message" });
        } catch (Exception ex) {
            Console.WriteLine(ex.Message);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

我得到了预期"Show this message".

如果将断点放在捕获异常的位置,调试器会显示正确的消息.


Sim*_*s0n 7

我喜欢在这里使用这个。这很简单,不需要静态函数:

public class MyException : Exception
{
    public MyException () : base("This is my Custom Exception Message")
    {
    }
}
Run Code Online (Sandbox Code Playgroud)


Kie*_*oot 6

这样的事情有什么问题。

    public class FolderNotEmptyException : Exception
{

    public FolderNotEmptyException(string Path) : base($"Directory is not empty. '{Path}'.")
    { }

    public FolderNotEmptyException(string Path, Exception InnerException) : base($"Directory is not empty. '{Path}'.", InnerException)
    { }

}
Run Code Online (Sandbox Code Playgroud)

我只使用一个字符串并包含参数。简单的解决方案。