c# - 最新版本中的异常消息更改

标签 c# json.net asp.net-web-api

我刚刚将 Newtonsoft.Json 库从 4.5.1 更新到 5.0.8。我注意到其中一条异常消息发生了变化。一旦无法反序列化该值,我的 400 响应中将包含以下内容,“错误转换值...”。现在,此消息在 4.5.1 中有所不同。库的版本。问题是暴露了对象的全名,这对我来说是一种不良行为。

为了澄清:

问题如下。直到Newtonsoft.Json库的4.5.1版本,一旦抛出JsonSerializationException,响应中的消息只是说明某个对象无法序列化。从那个版本开始,响应消息中的库,是的,它包括错误消息,但也包括它未能序列化到的对象的全名。很遗憾,因为我不想将错误消息中的命名空间暴露给外界。

我刚刚查看了JSON库的源代码,发现现在StringEnumConverter中的代码是:

catch (Exception ex)
{
    throw JsonSerializationException.Create(reader, "Error converting value {0} to type '{1}'.".FormatWith(CultureInfo.InvariantCulture, MiscellaneousUtils.FormatValueForPrint(reader.Value), objectType), ex);
}

同时它抛出默认的 Enum.Parse ArgumentException 消息“必须在字符串中指定用于解析的有效信息”。之前。

现在,我更喜欢这条消息,因为它没有向用户显示我的 API 的内部命名空间。

我试图在我的 Application_Start 方法中连接事件 JsonFormatter.SerializerSettings.Error,但是我无法执行我想要执行的操作。 我有机会访问我打算处理的异常,

private static void Error(object sender, ErrorEventArgs errorEventArgs)
{
    if (errorEventArgs.ErrorContext.Error.GetType() == typeof(JsonSerializationException))
    {

但是所有的属性都是只读的,我想修改的对象被标记为内部的。重新抛出异常也不异常(exception)。

为清楚起见,请查看 Newtonsoft.Json.Net40 项目中的 StringEnumConverterJsonSerializerInternalBase 类。

您是否知道在何处 Hook 相关库以覆盖错误消息?或者关于如何解决问题的任何其他想法(停止在错误消息中显示完整的命名空间)?

我的问题是,我能否通过指定不同的消息以某种方式重新抛出异常,例如 4.5.1 中的消息?

最佳答案

一段时间后,我找到了一个可行的解决方案。我基本上创建了一个派生自 StringEnumConverter 并覆盖 ReadJson 方法的新转换器。

我的新转换器如下所示:

public class StringEnumConverterEx : StringEnumConverter
    {
        public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
        {
            // the message in the response, once an serialization exception is thrown, after the version 4.5.1 of Newtonsoft.JSON library,
            // has changed. As we do not want to expose the full namespace of our Enums, we are catching the exception and re-throwing it
            // with a different message.
            try
            {
                return base.ReadJson(reader, objectType, existingValue, serializer);
            }
            catch (JsonSerializationException)
            {
                string values = objectType.IsEnum ? String.Join(",", Enum.GetNames(objectType)) : string.Empty;

                throw new JsonSerializationException(string.Format("Error converting value {0}, possible values are: {1}",
                    objectType.Name, values));
            }
        }
    }

现在我只是在我的应用启动时添加这个转换器而不是原来的 StringEnumConverter。

GlobalConfiguration.Configuration.Formatters.JsonFormatter.SerializerSettings.Converters.Add(new StringEnumConverterEx());

这可以解决问题并覆盖异常消息。 如您所见,我还在消息中提供了该枚举的可能值。

希望这对其他人有帮助。

干杯

关于c# - 最新版本中的异常消息更改,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20906939/

相关文章:

c# - Json反序列化问题

c# - 事件处理器执行顺序

c# - HttpResponseMessage 返回什么作为 Json

c# - 将正确的 header 值发送到从 Angular $http 到 asp.net webapi 的 Preflight 请求时出错

c# - AutoMapper:如果指定类型的源对象为空,则将目标对象的所有属性设置为默认值

c# - n 单击一个按钮给出 n 个输出。需要的只是一次点击产生的一个输出

json - 使用 JSON Schema 指定值可以是字符串或 null

c# - 当我事先不知道 key 时,如何在 C# 中解析 JSON 对象?

c# - Newtonsoft JObject.Parse 抛出基本异常...如何处理

.net - 如何让 Web API OData v4 使用 DateTime