我有一个REST API,它接受由动态GUID字段组成的JSON模型.

我try 了多个模型,在所有模型中,我都遇到了错误.

这是JSON:

{
   "meta_data": {
       "name": "myname"
   },
   "1122413f-2887-4789-a112-31d003f2703a": {
       "ipadd": "1.1.1.1",
       "host": "host"
   },
   "4432313f-2887-4789-a222-31d41231233a": {
       "ipadd": "1.2.1.1",
       "host": "h3st"
   }
}

这就是模型:

public class RootObject
{
    [JsonProperty("meta_data")]
    public Metadata Metadata { get; set; }

    public Dictionary<Guid, DeviceInfo> Devices { get; set; }
}

public class DeviceInfo
{
    public string IpAdd { get; set; }
    public string Host { get; set; }
}

和控制器:

[FromBody] RootObject jsonObj

jsonObj只包含Metadata,动态字段始终为空.

我能做些什么来克服这一点?

当我在Devices以下发送时,它会接受:

"Devices": { 
     "123...."
}

但这不是我需要的.

推荐答案

如果您使用的是.NET Core 3及更高版本,则可以从System.Text.Json.Serialization开始使用JsonExtensionDataAttribute.

您应该添加一个新属性来接收额外的JSON元素,即Dictionary<string, JsonElement>.

词典的TKey值必须是字符串,并且TValue必须是JsonElement或Object.

并通过一些数据转换将其分配给Devices属性.

using System.Text.Json.Serialization;
using System.Linq;

public class RootObject
{
    [JsonPropertyName("meta_data")]
    public Metadata Metadata { get; set; }

    [JsonExtensionData]
    public Dictionary<string, JsonElement> Extension { get; set; }
    
    [JsonIgnore]
    public Dictionary<Guid, DeviceInfo> Devices 
    { 
        get
        {
            if (Extension == null)
                return null;

            return Extension.ToDictionary(x => Guid.Parse(x.Key), v => JsonSerializer.Deserialize<DeviceInfo>(JsonSerializer.Serialize(v.Value)));
        }
    }
}

public class DeviceInfo
{
    [JsonPropertyName("ipadd")]
    public string IpAdd { get; set; }
    
    [JsonPropertyName("host")]
    public string Host { get; set; }
}

enter image description here


如果您使用Newtonsoft.Json作为API/MVC应用程序中的默认序列化库/工具:

services.AddControllers()
    .AddNewtonsoftJson();

您需要使用从Newtonsoft.Json开始的属性/反序列化方法.

using Newtonsoft.Json;
using Newtonsoft.Json.Linq;

public class RootObject
{
    [JsonProperty("meta_data")]
    public Metadata Metadata { get; set; }

    [JsonExtensionData]
    public Dictionary<string, JToken> Extension { get; set; }

    [JsonIgnore]
    public Dictionary<Guid, DeviceInfo> Devices
    {
        get
        {
            if (Extension == null)
                return null;

            return Extension.ToDictionary(x => Guid.Parse(x.Key), 
                v => JObject.FromObject(v.Value)
                    .ToObject<DeviceInfo>());
        }
    }
}

public class DeviceInfo
{
    [JsonProperty("ipadd")]
    public string IpAdd { get; set; }

    public string Host { get; set; }
}

enter image description here

Csharp相关问答推荐

需要更改哪些内容才能修复被覆盖的财产中的无效警告CS 8765?

一小时后,自定义缓存停止在App Insight中保存

如何使用ConcurentDictionary属性上的属性将自定义System.Text.Json JsonConverter应用于该属性的值?

Polly v8—使用PredicateBuilder重试特定的状态代码

将现有字段映射到EFCore中的复杂类型

C#阻塞调用或await calling inside calling方法

当用户右键单击文本框并单击粘贴时触发什么事件?

取决于您的数据量的多个嵌套循环

显示文档的ECDsa签名PDF在Adobe Reader中签名后已被更改或损坏

使用带有参数和曲面的注入失败(&Q;)

如何在C#中转换泛型包装类内部的派生类

为什么@rendermode Interactive Auto不能在.NET 8.0 Blazor中运行?

在Windows Plesk上发布ASP.NET Core 7 Web API-错误:无法加载文件或程序集';Microsoft.Data.SqlClient';

具有类型识别的泛型方法

我什么时候应该在Dapper中使用Connection.OpenAsync?

发布.NET 8 Blazor WebAssembly独立应用程序以进行静态站点部署

为什么Swashbakle/Swagger在参数中包含变量名?

删除MudRadio时,MudRadioGroup未 Select 正确的MudRadio

使用postman 测试配置了身份的.NET 6应用程序

为什么Visual Studio 2022建议IDE0251将我的方法设置为只读?