儿童采集的自定义模型绑定 [英] Custom model binder for child collection

查看:98
本文介绍了儿童采集的自定义模型绑定的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经搜查高和低,所以希望有人能帮助我。我有一个类:

 公共类Person
{
    公共字符串名称{;组; }
    公众的ICollection<玩具与GT; {搞定;组; }
}

我有一个控制器的方法:

 公众的ActionResult更新(人toycollector)
{
....
}

我要绑定到集合。我知道我只会得到的ID,但我会处理的,在我的控制器。我只需要能够通过ID的收藏翻转。我开始写一个模型绑定:

 公共类CustomModelBinder:DefaultModelBinder
    {
        保护覆盖无效BindProperty(ControllerContext controllerContext,ModelBindingContext的BindingContext,的PropertyDescriptor PropertyDescriptor的)
        {
            如果(propertyDescriptor.PropertyType == typeof运算(ICollection的<精品GT;))
            {
                //我该怎么做?在这里
            }
}

那么,如何打造精品,从传递到我的方法的数值集合?谢谢!

编辑:
貌似我没有这个答案张贴到我自己的问题,所以我就编辑自己的帖子。看起来像你所要做的就是分析出的数据并将其添加到像这样的模式:

 如果(propertyDescriptor.PropertyType == typeof运算(的ICollection)){            VAR incomingData = bindingContext.ValueProvider.GetValue(编辑。+ propertyDescriptor.Name +[]);
            如果(incomingData!= NULL)
            {
                ICollection的<玩具和GT;玩具=新的List<玩具和GT;();
                串[] IDS = incomingData.AttemptedValue.Split(,);
                的foreach(IDS中的字符串ID)
                {
                    INT toyId = int.Parse(ID);
                    toys.Add(新玩具(){ToyID = toyId});
                }
                VAR模型= bindingContext.Model的人;
                model.Toys =玩具;
            }
            返回;
        }


解决方案

您应该不需要自定义模型绑定这一点。

参阅这一职位由菲尔哈克为全面落实,但基本思路是,对集合中的每一个项目,你让下面的下面的命名约定表单域:

 玩具[指数]<&字段名GT;

因此​​,举例来说,如果你想绑定3玩具对象:

 <输入类型=隐藏的名字=玩具[0] .ID值=1/>
<输入类型=隐藏的名字=玩具[1] .IDVALUE =2/>
<输入类型=隐藏的名字=玩具[2] .IDVALUE =3/>

最重要的部分是,所有的索引值占和无索引被跳过。例如,如果你有一个表单值玩具[1]。字段名> 必须也有玩具[0]<字段名方式>

这一切是说,这取决于究竟你需要完成它可能更容易简单地绑定到ID的集合,而不是整个对象。你可以让你的控制器操作的ID转换为实际的模型。

如果您preFER简单,身份证,唯一的方法,所有你需要做的就是让一个字符串/ INT / GUID(无论你的id是)集合对象在请求模型,然后再创建1个或多个字段所有具有相同名称的每个ID值。默认的模型绑定会自动处理请求创建一个从值集合。

I've searched high and low so hopefully someone can help me. I have a class:

public class Person
{
    public string Name { get; set; }
    public ICollection<Toys> { get; set; }
}

I have a controller method:

public ActionResult Update(Person toycollector)
{
....
}

I want to bind to the collection. I realize I will only get the IDs but I will deal with that in my controller. I just need to be able to flip through the collection of IDs. I started writing a model binder:

public class CustomModelBinder : DefaultModelBinder
    {
        protected override void BindProperty(ControllerContext controllerContext, ModelBindingContext bindingContext, PropertyDescriptor propertyDescriptor)
        {
            if (propertyDescriptor.PropertyType == typeof(ICollection<Toys>))
            {
                //What do I do here???
            }
}

So how do I build the collection of Toys from the values passed into my method? Thanks!

EDIT: Looks like I couldn't post this answer to my own question so I'll just edit my post. looks like all you have to do is parse out the data and add it to the model like so:

if (propertyDescriptor.PropertyType == typeof(ICollection)) {

            var incomingData = bindingContext.ValueProvider.GetValue("Edit." + propertyDescriptor.Name + "[]");
            if (incomingData != null)
            {
                ICollection<Toy> toys = new List<Toy>();
                string[] ids = incomingData.AttemptedValue.Split(',');
                foreach (string id in ids)
                {
                    int toyId = int.Parse(id);
                    toys.Add(new Toy() { ToyID = toyId });
                }
                var model = bindingContext.Model as Person;
                model.Toys = toys;
            }
            return;
        }

解决方案

You shouldn't need a custom model binder for this.

Refer to this post by Phil Haack for the full implementation, but the basic idea is that for each item in the collection, you make a form field that follows the following naming convention:

Toys[index].<FieldName>

So, for example, if you wanted to bind 3 Toy objects:

<input type="hidden" name="Toys[0].Id" value="1" />
<input type="hidden" name="Toys[1].Id" value="2" />
<input type="hidden" name="Toys[2].Id" value="3" />

The important part is that all index values are accounted for and no indexes are skipped. For example, if you have a form value Toys[1].<FieldName> you must also have a Toys[0].<FieldName> value.

All this being said, depending on what exactly you need to accomplish it may be easier to simply bind to a collection of Ids rather than whole objects. You can let your controller action translate the Ids to actual models.

If you prefer the simpler, Id-only approach, all you need to do is make a string/int/guid (whatever your id is) collection object in your request model and then create 1 or more fields all having the same name for each Id value. The default model binder will automatically handle creating the collection from the values in the request.

这篇关于儿童采集的自定义模型绑定的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆