微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

检查 JSON 中的重复属性

如何解决检查 JSON 中的重复属性

我们正在开发一个基于 .Net 核心的 web api 应用程序,为此我们需要验证传入的请求正文,它是 JSON 格式的基于 c# 的类型。 此时我们正在评估 njsonSchema 库以查看它是否引发重复属性错误。 但看起来它不支持这种验证。我们还检查了 JSONNewtonSoft 架构验证器,但它似乎也不支持重复属性验证。

以下是我们使用的使用 njsonSchema 的最小化代码 -

using NewtonSoft.Json;
public class MyRequest
    {
        [Jsonrequired]
        [JsonProperty("name")]
        public string Name { get; set; }
}

当我们像这样传递一个 JSON 对象时 -

{"name":"abc","name":"xyz"}

我们需要我们的 JSON 验证器为 duplicate property 抛出错误 我们的示例测试看起来像这样 -

[Test]
        public async System.Threading.Tasks.Task SchemaValidation_WithDuplicateProperty_Async()
        {
            var jsonString = await File.ReadAllTextAsync("Data//JsonWithDuplicateProperty.json");
            var schema = JsonSchema.FromType<MyRequest>();
            var errors = schema.Validate(jsonString);
            Assert.That(errors.Count(),Is.EqualTo(1));
        }

所以我的问题 - 过去有人这样做过吗?或者是否有任何 .net core 库为重复属性提供 JSON 验证和/或可以使用 njsonSchemaNewtonSoft 来完成。

解决方法

正如@zaggler 指出的那样,使用 Newtonsoft,您可以使用 DuplicatePropertyNameHandling 枚举。不幸的是,您不能直接在对 DeserializeObject 的调用中使用它(在 JsonSerializerSettings 中);它必须在 JToken Reader 中使用。有关更多详细信息,请参阅此讨论主题:

https://github.com/JamesNK/Newtonsoft.Json/issues/931

这是一种以 DeserializeObject 式的方式包装操作的方法:

using System;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using System.IO;
                    
public class Program
{
    public static void Main()
    {
        var json = @"{""name"":""abc"",""name"":""xyz""}";

        var objA = DeserializeObject<MyRequest>(json,new JsonSerializerSettings(),DuplicatePropertyNameHandling.Ignore);
        Console.WriteLine(".Ignore: " + objA.Name);
        
        var objB = DeserializeObject<MyRequest>(json,DuplicatePropertyNameHandling.Replace);
        Console.WriteLine(".Replace: " + objB.Name);
        
        var objC = DeserializeObject<MyRequest>(json,DuplicatePropertyNameHandling.Error);
        Console.WriteLine(".Error: " + objC.Name); // throws error before getting here
}
    public static T DeserializeObject<T>(string json,JsonSerializerSettings settings,DuplicatePropertyNameHandling duplicateHandling)
    {
        JsonSerializer jsonSerializer = JsonSerializer.CreateDefault(settings);
        using (var stringReader = new StringReader(json))
        using (var jsonTextReader = new JsonTextReader(stringReader))
        {
            jsonTextReader.DateParseHandling = DateParseHandling.None;
            JsonLoadSettings loadSettings = new JsonLoadSettings { 
                DuplicatePropertyNameHandling = duplicateHandling
            };
            var jtoken = JToken.ReadFrom(jsonTextReader,loadSettings);
            return jtoken.ToObject<T>(jsonSerializer);
        }
    }
}
public class MyRequest
    {
        [JsonRequired]
        [JsonProperty("name")]
        public string Name { get; set; }
}

输出:

.忽略:abc

.替换:xyz

运行时异常(第 31 行):带有 当前 JSON 对象中已存在名称“name”。小路 'name',第 1 行,位置 21。

见:

https://dotnetfiddle.net/EfpzZu

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。