C# 日志错误代码设计,需要输入

C# 日志错误代码设计,需要输入,c#,custom-attributes,error-code,C#,Custom Attributes,Error Code,所以,我遇到了一个小问题。我很好奇是否有人愿意在这个设计上提供一些额外的意见 我有一个ILog接口,它有两种方法用于设计中的错误代码记录部分。Flagror和GetErrorCode;Flageror在整数上设置一个位,每个位表示抛出了某个错误。GetErrorCode(它将是主方法的返回值)返回该整数 我首先推测在每个应用程序中使用enum来包含可能的错误代码列表 但问题是,我如何准确地向用户传递错误代码“XYZ”表示应用程序在执行过程中以友好的方式达到这些非正常状态 ILog接口: (写入方

所以,我遇到了一个小问题。我很好奇是否有人愿意在这个设计上提供一些额外的意见

我有一个ILog接口,它有两种方法用于设计中的错误代码记录部分。Flagror和GetErrorCode;Flageror在整数上设置一个位,每个位表示抛出了某个错误。GetErrorCode(它将是主方法的返回值)返回该整数

我首先推测在每个应用程序中使用
enum
来包含可能的错误代码列表

但问题是,我如何准确地向用户传递错误代码“XYZ”表示应用程序在执行过程中以友好的方式达到这些非正常状态

ILog接口: (写入方法有重载)

日志类:

abstract class Log : ILog
{
    public void
    FlagError (int errorCode)
    {
        if (errorCode == 0 || errorCode == int.MinValue || errorCode != (errorCode & -errorCode))
        {
            throw new IndexOutOfRangeException ();
        }

        if ((m_errorCode & errorCode) == errorCode)
             return;

        m_errorCode += errorCode;
    }

    public int
    GetErrorCode ()
    {
        return m_errorCode;
    } 


    #region Other ILog Methods    

}
我推测在每个枚举值上使用一个属性来描述该错误,然后使用一个小过程或一些东西来帮助将错误代码“解析”为人类可读的描述


但是Idk,有什么想法吗?

我可能会使用enum,将这些值和日志代码放入每个应用程序都可以调用的公共程序集中。它可能不是有史以来最优雅的解决方案,但它完成了任务,让我们继续做更重要的事情——比如不会抛出太多错误的良好核心业务逻辑:-)


另一种选择可能是将错误代码和人类可读的描述放入配置文件中。这样,您就可以灵活地改进错误消息。我从未尝试过,但现在我想起来了,我可以看到它在很多情况下都是一个真正的恩惠。

谢谢你们的评论,伙计们,我考虑了他们,并找到了一个解决方案(虽然不是最好的)可以满足我的需要

最后,我创建了一个描述属性,并将其添加到每个枚举值中,然后在枚举上创建一个“GetDescription”扩展方法。然后,每当我标记一个错误时,它的描述就会写入控制台/文件/窗口或w/e

我想我应该多暴露一些ILog的方法来找到这个解决方案

新的错误方法:

public void
FlagError (Enum  errorCode)
{
   int  errorValue = Convert.ToInt32 (errorCode);

   if (errorValue == 0 || errorValue == int.MinValue
      || errorValue != (errorValue & -errorValue))
   {
      WriteError ("ErrorCode {0}: {1}",
                  errorValue,
                  errorCode.GetDescription ());

      m_errorCode = int.MinValue;

      throw new IndexOutOfRangeException ();
   }

   if ((m_errorCode & errorValue) == errorValue)
      return;

   WriteError ("ErrorCode {0}: {1}",
               errorValue,
               errorCode.GetDescription ());

   m_errorCode += errorValue;
}
GetDescription扩展方法:

public static string 
GetDescription (this Enum  @enum)
{
   StringBuilder  builder;

   var  descriptionAttributes = @enum.GetType ()
                                     .GetCustomAttributes (
                                          typeof (DescriptionAttribute),
                                          false) as DescriptionAttribute [];

   if (descriptionAttributes == null || descriptionAttributes.Length == 0)
      return string.Empty;

   builder = new StringBuilder ();

   foreach (DescriptionAttribute  description in descriptionAttributes)
   {
      builder.Append (description.Description);
      builder.AppendLine ();
   }

   return builder.ToString ();
}
描述属性:

public sealed class DescriptionAttribute : Attribute
{
   public 
   DescriptionAttribute (string  description)
   {
      m_description = description;
   }

   public string 
   Description
   {
      get
      {
          return m_description;
      }
   }


   private readonly string m_description;
}

如果有人有任何额外的输入,我很想听听。

我见过使用开关逻辑解析描述的枚举,但我的第一个问题是为什么不为每种类型的错误使用实际的特定异常?如果你不这样做是因为你积累了一组你想要返回的错误,那么像你描述的位屏蔽错误代码对我来说似乎很有效。但是我个人会用一些字典把所有的错误都传回去。位掩码虽然有效,但绝对不容易阅读。这就是你想要做的吗?返回多个异常的问题是,一些错误可以在没有实际抛出异常的情况下被标记,我真的不想去“log.flageror(newanonexception(“This coursed”);”但这是个好主意。不,我不想做链接中的事情。另外,如果你愿意,我希望你能仔细看看我的答案。我想困扰我的是你使用了“错误”这个词。这意味着,至少对我来说,发生了某种意想不到的坏事——这意味着使用了异常。也许如果你用一个不同的术语,那么所有的enum体操都会更有意义。只是一个想法。这是真的,我应该解释一下,我只是想更一般一些。你建议用什么术语?(另外,我仍然愿意接受任何关于设计的建议。)我喜欢在配置文件或其他文件中有人类可读的描述,但这很难维护,因为我不能保证如果开发人员添加新的错误代码,他们会返回并更改配置文件。我正在寻找一种对开发人员来说很明显并且对用户来说很容易解释的方法。如果你发现你正在广泛使用这种方法,一个潜在的性能优化就是将
DescriptionAttribute
类密封起来,使用一个显式支持字符串变量,该变量为
只读
,并且具有
Description
属性,只有一个访问该显式变量的getter。
public sealed class DescriptionAttribute : Attribute
{
   public 
   DescriptionAttribute (string  description)
   {
      m_description = description;
   }

   public string 
   Description
   {
      get
      {
          return m_description;
      }
   }


   private readonly string m_description;
}