如何将绑定表单urlencoded数据建模到.net类

问题描述 投票:1回答:1

我们有第三方供应商以下列格式向我们发布数据。不幸的是,这是他们提供的唯一格式。 Json会很好,但我们没有选择。它正在击中一个.net核心webapi控制器方法。

contact%5Bid%5D=2&contact%5Bemail%[email protected]&contact%5Bfirst_name%5D=john&contact%5Blast_name%5D=smith

控制器方法如下所示。

public IActionResult Endpoint([FromForm] customClass)
{
    //do something with customClass
    return Ok();
}

这堂课就像是

using System;
using System.Runtime.Serialization;

namespace Domain.Models.Custom
{
    [DataContract]
    public class CustomClass
    {
        [DataMember(Name = "contact[id]")]
        public int Id { get; set; }

        [DataMember(Name = "contact[first_name]")]
        public string FirstName { get; set; }

        [DataMember(Name = "contact[last_name]")]
        public string LastName { get; set; }

        [DataMember(Name = "contact[phone]")]
        public string PhoneNumber { get; set; }

        [DataMember(Name = "contact[email]")]
        public string EmailAddress { get; set; }
    }
}

从我读过的所有内容来看,听起来像使用DataContract和DataMember属性来修饰类对我来说应该是模型绑定。但是当我在Endpoint方法中查看customClass的实例时,所有属性都为null。

model-binding asp.net-core-webapi
1个回答
0
投票

使用FromForm绑定时,默认情况下不支持DataContract / DataMember属性。它们只有你期望的FromBody支持,因为使用的序列化程序(通常是JSON.NET)支持这些属性 - 但是这种支持独立于MVC绑定。

有一种方法可以在启动期间扩展MVC的表单绑定:

services.AddMvc(options => options.ModelMetadataDetailsProviders.Add(new DataMemberBindingMetadataProvider()));

简单实现IBindingMetadataProvider以查找DataMemberAttribute / Name:

public class DataMemberBindingMetadataProvider : IBindingMetadataProvider
{
    public void CreateBindingMetadata(BindingMetadataProviderContext context)
    {
        var dataMember = context.Attributes.OfType<DataMemberAttribute>().FirstOrDefault();
        if (dataMember != null)
        {
            context.BindingMetadata.BinderModelName = dataMember.Name;
        }
    }
}

或者,您可以尝试添加DataAnnotationsMetadataProvider而不是您自己的元数据提供程序,但我发现它的构造函数依赖项使这个问题。

© www.soinside.com 2019 - 2024. All rights reserved.