0

IExceptionToErrorInfoConverter为 ASP.NET 样板实现了自定义以转换 Web API 中的自定义异常。

问题是 ABP 具有严格的接口,必须返回ErrorInfo类型:

ErrorInfo Convert(Exception exception);

问题是ErrorInfo结构不符合我的要求,所以我想拥有自己的错误 DTO。

任何人都知道如何规避 ABP 异常转换?

4

2 回答 2

2

你可以尝试一种技巧。可能是,当 Abp 创建 json 响应时,它会通过反射将所有可用属性序列化错误并将其与其他东西一起包装到MvcAjaxResponse对象中,即您可以尝试创建自己的类,派生自并在实现ErrorInfo时替换它:IExceptionToErrorInfoConverter

[Serializable]
public class MyErrorInfo : ErrorInfo
{
    public string MyProperty1 { get; set; }
    public int MyProperty2 { get; set; }
}

public class MyExceptionToErrorInfoConverter : IExceptionToErrorInfoConverter
{
    public IExceptionToErrorInfoConverter Next { set { } }        

    public ErrorInfo Convert(Exception exception)
    {
        return new MyErrorInfo{ MyProperty1 = "test", MyProperty2  = 1};
    }
}
于 2016-07-05T13:03:47.430 回答
2

感谢@slava-utesinov接受的答案(在此 QA 中),这是我的补充信息。

object实际上,在处理序列化 DTO 时,人们会怀疑在内部使用 ABP ,因此假设是可靠的。

来自 ABP 源的一些示例代码:

public static string ToJsonString(this object obj, bool camelCase = false, bool indented = false)
{ ... }

protected override JsonResult Json(object data, string contentType, Encoding contentEncoding, JsonRequestBehavior behavior)
{ ... }

因此,成功后,我通过尝试隐藏原始 ErrorInfo 成员来解决问题。现在,知道 ABP 使用 Json.NET,我发现了Conditional Property Serialization的特性。按照惯例bool ShouldSerialize[member name](),我们可以指示序列化程序忽略一个属性。

所以我最终得到了以下概念验证代码:

public class ErrorInfoEx : ErrorInfo
{
   public new string Details { get; set; }
   public bool ShouldSerializeDetails() { return false; }

   public ErrorInfoEx(int code, string message) : base(code, message) { }
   public string MyField { get; set; }
}

请注意,出于某种原因,您必须替换基类实现以忽略基类成员。

这导致了以下 JSON,如您所见,没有“详细信息”属性,但存在“myField”。

{
    "success":false,
    "result":null,
    "error":
        {
            "myField":"123",

            "code":420,
            "message":"Validation failed",
            "validationErrors":
                [{
                    "message":"'Order Number' should not be empty.",
                    "members":["OrderNumber"]
                }]
        },
        "unAuthorizedRequest":false
}
于 2016-07-06T06:03:23.247 回答