简体   繁体   English

自定义异常类以警告错误并记录日志

[英]Custom exception class to alert errors and log

I am writting an API for some data manipulation these days and I have faced a question that I cannot answer myself :D 这些天,我正在编写用于某些数据操作的API,但遇到一个我无法回答自己的问题:D

I have made an exception class that extends the .net Application Exception class because I want to add some functionality there to be executed everytime the API throws an exception. 我制作了一个扩展.net Application Exception类的异常类,因为我想在API引发异常时在其中添加一些功能。 For example I want to alert the error message and stacktrace via sms and email and I want to log the inner exception via Log4net. 例如,我想通过短信和电子邮件来警告错误消息和stacktrace,并且我想通过Log4net记录内部异常。 I don't know if this is a good aproach to use with the custom exception class or if I overused the meaning of the custom exceptions. 我不知道这是与自定义异常类一起使用的好方法,还是我过度使用了自定义异常的含义。

I have read this article about how to extend the Exception in c# so here we go with my example of code : 我已经阅读了有关如何在c#中扩展Exception的文章 ,因此在这里我们来看一下我的代码示例:

public class CustomExceptionClass : Exception
{
    /// <summary>
    /// I use custom functionality here everytime this exception occures
    /// </summary>
    /// <param name="errorMessage">error message</param>
    /// <param name="innerEx">Inner exception that cause this exception</param>
    public MyCustomException(string errorMessage, Exception innerEx) : base(errorMessage, innerEx)
    {
        //log exception
        _log.ErrorFormat(errorMessage, innerEx);
        //alert via sms and email
        AlertMailer.SendAlertMessage(errorMessage, innerEx, innerEx.Message);
    }
}

I think that doing logging and alerting by throwing a custom exception is a valid technique. 我认为通过抛出自定义异常来进行日志记录和警报是一种有效的技术。

However, you shouldn't do the logging and alerting in the exception constructor. 但是,您不应在异常构造函数中进行日志记录和警报。 Instead you should catch the custom exception in all entry-points to your API and do the logging and alerting in the catch block. 相反,您应该在API的所有入口点中捕获自定义异常,并在catch块中进行日志记录和警报。 For example: 例如:

void MyApiFunction()
{
    try
    {
        // do data manipulation
    }
    catch(MyCustomException ex)
    {
        _log.ErrorFormat(ex.ErrorMessage, ex.InnerEx);
        AlertMailer.SendAlertMessage(ex.ErrorMessage, ex.InnerEx);
    }
}

I would recomend you to use AOP instead. 我建议您改用AOP。
PostSharp exception handling PostSharp异常处理

Custom exceptions should be used to define different types of exception. 自定义异常应用于定义不同类型的异常。

  • Exceptions from the database 数据库异常
  • Exceptions from file io 文件io的异常
  • Exceptions from web services Web服务的例外

They should be very simple, and contain no other logic than assigning variables. 它们应该非常简单,并且除分配变量外不包含其他逻辑。 Why? 为什么? Because if the exception constructor throws another exception you are going to have a hard time tracing it. 因为如果异常构造函数引发另一个异常,您将很难跟踪它。

The ways i handle those exceptions are: 处理这些异常的方式是:

  1. AOP (Spring.NET) AOP(Spring.NET)
  2. Specific try/catches 具体的尝试/抓住
  3. The global exception handler 全局异常处理程序

In a program 在程序中

namespace ConsoleApplication1 {
    class Program {
        static void Main(string[] args) {
            try {
                //do something
            } catch(Exception e) {
                //log error
            }
        }
    }
}

Or in a web site 或在网站上

public class ApplicationErrorModule : IHttpModule {

    public void Init(HttpApplication context) {
        context.Error += new EventHandler(context_Error);
    }

    private void context_Error(object sender, EventArgs e) {
        //log error
    }
}

Heavy treatments like logging and sending an email don't belong in the constructor of the exception. 日志的构造和发送电子邮件等繁重的处理不属于异常的构造函数。 You should instead handle the exception using AOP as @petro suggested, or in a catch statement. 您应该改用@petro建议的AOP或在catch语句中处理异常。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM