我已根据SO POST创建了包含自定义属性的客户例外
但是,当我记录异常时,它没有被序列化。
如果我放置调试器,则不调用GetObjectData
方法和SerializableExceptionWithCustomProperties(SerializationInfo info, StreamingContext context)
构造函数,并且记录器仅记录消息和堆栈跟踪,但不记录我的自定义属性
但是,我在异常中添加了ToString()
方法,并且在我记录异常时它会受到影响,现在我可以构造包含我的自定义属性的字符串并将其返回。
那么添加Serializable
属性和GetObjectData
方法以及SerializableExceptionWithCustomProperties(SerializationInfo info, StreamingContext context)
构造函数的用途是什么?
我正在使用Serilog进行记录
[Serializable]
// Important: This attribute is NOT inherited from Exception, and MUST be specified
// otherwise serialization will fail with a SerializationException stating that
// "Type X in Assembly Y is not marked as serializable."
public class SerializableExceptionWithCustomProperties : Exception
{
private readonly string resourceName;
public SerializableExceptionWithCustomProperties()
{
}
public SerializableExceptionWithCustomProperties(string message)
: base(message)
{
}
public SerializableExceptionWithCustomProperties(string message, Exception innerException)
: base(message, innerException)
{
}
public SerializableExceptionWithCustomProperties(string message, string resourceName)
: base(message)
{
this.resourceName = resourceName;
}
public SerializableExceptionWithCustomProperties(string message, string resourceName, Exception innerException)
: base(message, innerException)
{
this.resourceName = resourceName;
}
public string ResourceName
{
get { return this.resourceName; }
}
[SecurityPermissionAttribute(SecurityAction.Demand, SerializationFormatter = true)]
// Constructor should be protected for unsealed classes, private for sealed classes.
// (The Serializer invokes this constructor through reflection, so it can be private)
protected SerializableExceptionWithCustomProperties(SerializationInfo info, StreamingContext context)
: base(info, context)
{
this.resourceName = info.GetString("ResourceName");
}
[SecurityPermissionAttribute(SecurityAction.Demand, SerializationFormatter = true)]
public override void GetObjectData(SerializationInfo info, StreamingContext context)
{
// Serialize data for our base classes. base will verify info != null.
base.GetObjectData(info, context);
info.AddValue("ResourceName", this.ResourceName);
}
public override string ToString()
{
return base.ToString() + Environment.NewLine + "ResourceName: " + this.ResourceName;
}
}
答案 0 :(得分:0)
可选择性的目的是例如将对象从一个系统传输到另一个系统(例如在clirnt和服务器之间),继续使用传输的对象。 在您的情况下,您只需将异常转储到接收器,您可以通过定义te异常消息或覆盖ToString()方法来定义它如何表示为文本。