asp.net-mvc 模型绑定不起作用
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/10743908/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Model Binding not working
提问by Mike
I have the following POCO classes:
我有以下 POCO 课程:
public class Location
{
public int LocationId { get; set; }
public string Name { get; set; }
public string Street { get; set; }
public string City { get; set; }
public string State { get; set; }
public string ZipCode { get; set; }
public string Country { get; set; }
public float? Latitude { get; set; }
public float? Longitude { get; set; }
public string PhoneNumber { get; set; }
public string EmailAddress { get; set; }
public string Website { get; set; }
public virtual ICollection<Program> Programs { get; set; }
public virtual ICollection<PlayerType> PlayerTypes { get; set; }
}
public class PlayerType
{
public int PlayerTypeId { get; set; }
public string Name { get; set; }
public int SortOrder { get; set; }
public bool IsActive { get; set; }
public virtual ICollection<Location> Locations { get; set; }
}
And a View Model Class
和一个视图模型类
public class LocationViewModel
{
public Location Location { get; set; }
public IList<PlayerType> SelectPlayerTypes { get; set; }
public LocationViewModel()
{
Location = new Location();
}
}
Within my Create Form, I have defined the model as
在我的创建表单中,我将模型定义为
@model Locator.Models.LocationViewModel
And have fields like the following:
并具有如下字段:
div class="editor-label">
@Html.LabelFor(model => model.Location.Name)
</div>
<div class="editor-field">
@Html.EditorFor(model => model.Location.Name)
@Html.ValidationMessageFor(model => model.Location.Name)
</div>
In my controller to handle the POST I have
在我的控制器中处理 POST 我有
[HttpPost]
public ActionResult Create(LocationViewModel location)
{
if (ModelState.IsValid) {
locationRepository.InsertOrUpdate(location.Location);
locationRepository.Save();
return RedirectToAction("Index");
}
location.SelectPlayerTypes = golferTypeRepository.All.Where(p => p.IsActive).ToList();
return View(location);
}
The problem is that I have a Location object but none of the properties are to set to the values entered in the form.
问题是我有一个 Location 对象,但没有一个属性要设置为表单中输入的值。
Am I doing something wrong here?
我在这里做错了吗?
Thanks
谢谢
回答by Darin Dimitrov
Here's the problem:
这是问题所在:
[HttpPost]
public ActionResult Create(LocationViewModel location)
Do you see it? It's the name of your action argument: location.
你看到了吗?这是您的操作参数的名称:location.
Look at your view model now, it has a property named Location:
现在看看你的视图模型,它有一个名为 的属性Location:
public Location Location { get; set; }
This confuses the model binder. It no longer knows whether you need to bind the LocationViewModelor its property.
这会混淆模型绑定器。它不再知道您是否需要绑定 theLocationViewModel或它的属性。
So simply rename to avoid the conflict:
因此,只需重命名即可避免冲突:
[HttpPost]
public ActionResult Create(LocationViewModel model)
回答by Grzegorz
Just to contribute another possible reason: I've spent couple of hours looking for an error in my code and the reason for the binder not working in my case was using a model with public fields rather than public properties:
只是为了贡献另一个可能的原因:我花了几个小时来寻找我的代码中的错误,并且绑定器在我的情况下不起作用的原因是使用具有公共字段而不是公共属性的模型:
public int CustomerName;
and it should be:
它应该是:
public int CustomerName { get; set; }
Been working on ASP.NET MVC for 3 years now and I never came across this before. Hope it saves somebody some frustration ;)
已经在 ASP.NET MVC 上工作 3 年了,我以前从未遇到过这种情况。希望它可以为某人节省一些挫败感;)
回答by ilans
Also late to join the party, but after 3 years of asp.net mvc, I've came across that disabled inputs are not posted, so the model binder cannot bind them of course. See here:
加入聚会也很晚,但是在使用 3 年的 asp.net mvc 之后,我发现未发布禁用的输入,因此模型绑定器当然无法绑定它们。见这里:
"Disabled elements in a form will not be submitted".
“表单中的禁用元素将不会被提交”。
Better use readonly="readonly"over disabled. See here.
更好地使用而readonly="readonly"不是残疾人。见这里。
回答by Fjarskiptagervitungl
Just to reiterate what Tod was saying, the model binder needs a 'name' attribute on the HTML element to map the properties. I was doing a quick test form by hand and only used the 'id' attribute to identify my elements.
只是重申 Tod 所说的话,模型绑定器需要 HTML 元素上的“名称”属性来映射属性。我正在手工制作一个快速测试表单,并且只使用 'id' 属性来标识我的元素。
Everything fell into place when I added the 'name' attribute.
当我添加 'name' 属性时,一切都已就位。
<input type="text" id="Address" name="Address" />
回答by Anderson Fortaleza
Let me add here yeat another reason why the model binder would not work properly.
让我在这里补充一下模型绑定器无法正常工作的另一个原因。
I had a model with the property ContactPhone, somewhere along the way I decided to change the name of this property to Phone, then all of a sudden model binding for this property stopped working when I was trying to create a new instance.
我有一个带有属性的模型,在ContactPhone此过程中我决定将这个属性的名称更改为Phone,然后当我尝试创建一个新实例时,这个属性的模型绑定突然停止工作。
The problem was on the Createaction in my controller. I have used the default Visual Studio scaffolding and it has created the method signature as this:
问题出Create在我的控制器中的操作上。我使用了默认的 Visual Studio 脚手架,它创建了方法签名,如下所示:
public ActionResult Create([Bind(Include = "Id,ContactPhone, ...")] Customer customer)
{ ... }
Pay attention to the Bindattribute, the scaffolder created the fields using the original name ContactPhoneand as this is a string, it was not refactored. As the new field Phonewas not being included, it's value was ignored by the model binder.
注意Bind属性,脚手架使用原始名称创建字段ContactPhone,由于这是一个字符串,它没有被重构。由于Phone未包含新字段,因此模型绑定器忽略了它的值。
I hope this saves someone's time.
我希望这可以节省某人的时间。
Good luck!
祝你好运!
回答by mahlatse
For anyone else still experiencing an issues with this, if you name your parameter in your post method to be the same as one of your properties, the default modelbinder will also fail.
对于仍然遇到此问题的其他任何人,如果您将 post 方法中的参数命名为与您的属性之一相同,则默认模型绑定器也将失败。
回答by Kabali
Mine was a bit unique case, but hope it helps someone in similar context. I had my View Model implementing IValidatableObject, and the Validate method from this interface was returning a null if success. It had to return an empty IEnumerable. Hence the binding was actually happening but crashing.
我的情况有点独特,但希望它可以帮助处于类似情况的人。我让我的视图模型实现了 IValidatableObject,如果成功,来自这个接口的 Validate 方法返回一个 null。它必须返回一个空的 IEnumerable。因此绑定实际上正在发生但崩溃了。
Basically when you get this issue, use Fiddler to look at posted data, make sure the posted variables match the properties(not fields!) on your view models, and put a break point on the View Model constructor to ensure the Routing Engine hits the correct POST method. Good luck!
基本上当你遇到这个问题时,使用 Fiddler 查看发布的数据,确保发布的变量与视图模型上的属性(不是字段!)匹配,并在视图模型构造函数上放置一个断点以确保路由引擎命中正确的 POST 方法。祝你好运!
回答by Tod
And another reason: Normally I use the built in editors or displays for and would have never encountered this issue. However in this case I required a semi-custom control. Basically a drop down with lots of data attributes on the options.
另一个原因:通常我使用内置的编辑器或显示器,并且从未遇到过这个问题。但是在这种情况下,我需要一个半自定义控件。基本上是一个下拉菜单,在选项上有很多数据属性。
What I was doing, for my select tag was:
我在做什么,我的选择标签是:
<select name="@Html.IdFor(x => x.SubModel.ID)" id="@Html.IdFor(x => x.SubModel)" class="form-control select-control">
Now everything was posting back and to the untrained eye it looked like everything should work and bind. However the IdFor helper renders sub models with an underscore. The model binder doesn't interpret underscores as a class hierarchy indicator. What should be separating them is a dot. Which comes from NameFor:
现在一切都在回传,在未经训练的眼睛看来,一切都应该可以正常工作并绑定。然而,IdFor 助手使用下划线呈现子模型。模型绑定器不会将下划线解释为类层次结构指示符。应该将它们分开的是一个点。来自 NameFor:
<select name="@Html.NameFor(x => x.SubModel.ID)" id="@Html.IdFor(x => x.SubModel)" class="form-control select-control">
NameFor fixed all my issues.
NameFor 解决了我所有的问题。
回答by Passenger
I know it's too late to comment on this.What I did is added parameter less constructor in the ViewModel and everything worked awesome.
我知道现在对此发表评论为时已晚。我所做的是在 ViewModel 中添加了无参数构造函数,一切都很棒。
回答by ntombela
This saved my day. Iad the following:
这挽救了我的一天。输入以下内容:
public ActionResult Edit(int masterId, ConclusionView conclusion)
ConclusionViewhas a property named Conclusionso I nearly lost my mind.
ConclusionView有一个名为的财产,Conclusion所以我几乎失去了理智。

