什么是模型绑定?
首先思考这个,如果在表单中输入了值,然后调用Index方法
其实这个有值,就是因为有模型绑定,那么模型绑定是怎么实现对象的创建以及赋值的呢?
主要是实现IModelBinder这个接口,并实现BindModel()方法
在这个方法里面,通过ModelBindingContext的ValueProvider的GetValue来获取值,那么值有哪些来源呢?
->1.Request.Form
->2.RouteData.values
->3.Request.QueryString
->4.Request.Files
应用程序就在这些内置的集合中找值,下面来看一下一个简单的值提供者
public class CurrentTimeValueProvider:IValueProvider { public bool ContainsPrefix(string prefix) { return string.Compare("CurrentTime",prefix,true)==0; } public ValueProviderResult GetValue(string key) { return ContainsPrefix(key) ? new ValueProviderResult(DateTime.Now, null, System.Globalization.CultureInfo.InstalledUICulture) : null; } }
然后如果我们要使用这个值提供者,那么我们就应该让程序知道,我们有这个提供者
所有,我们需要在全局处理程序Global.asax中的Application_Start()方法中注册
为了注册我们还需要创建一个值提供者工厂
public class CurrentTimeValueProviderFactory:ValueProviderFactory { public override IValueProvider GetValueProvider(ControllerContext controllerContext) { return new CurrentTimeValueProvider(); } }
ValueProviderFactories.Factories.Add(new CurrentTimeValueProviderFactory());
然后我们在控制器中访问
通过这个我们可以知道我们写的这个值提供者,只是简单的判断是否可以处理这个currentTime前缀的数据,如果可以就返回当前时间
否则,返回空
既然我们有了值提供者,那么我们就可以通过模型绑定来获取值了,下面上一个例子
public class Person { [HiddenInput(DisplayValue=false)] public int PersonId { get; set; } public string FirstName { get; set; } public string LastName { get; set; } [DataType(DataType.Date)] public DateTime BirthDate { get; set; } public Address HomeAddress { get; set; } public bool IsApproved { get; set; } }
public class PersonModelBinder : IModelBinder { public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext) { //获取要绑定的模型对象 var model = (Person)bindingContext.Model ?? (Person)DependencyResolver.Current.GetService(typeof(Person)); var hasPrefi = bindingContext.ValueProvider.ContainsPrefix(bindingContext.ModelName); var searchPrefix = (hasPrefi) ? bindingContext.ModelName + "." : ""; model.PersonId = int.Parse(GetValue(bindingContext, searchPrefix, "PersonId")); model.FirstName = GetValue(bindingContext, searchPrefix, "FirstName"); model.LastName = GetValue(bindingContext, searchPrefix, "LastName"); model.BirthDate = DateTime.Parse(GetValue(bindingContext, searchPrefix, "BirthDate")); model.IsApproved = GetCheckedValue(bindingContext, searchPrefix, "IsApproved"); return model; } private string GetValue(ModelBindingContext context, string prefix, string ke) { var vpr = context.ValueProvider.GetValue(ke); return vpr == null ? null : vpr.AttemptedValue; } private bool GetCheckedValue(ModelBindingContext context, string prefix, string ke) { var result = false; var vpr = context.ValueProvider.GetValue(prefix + ke); if (vpr != null) { result = (bool)vpr.ConvertTo(typeof(bool)); } return result; } }
然后我们就需要我们这个模型绑定和程序关联起来了,关联的方法一共有三种
->1.
ModelBinders.Binders.Add(typeof(Person), new PersonModelBinder());
->2.和上面的值提供者一个,需要实现一个工厂接口
ModelBinderProviders.BinderProviders.Add(new CustomModelBinderProvider());
->3.直接在类上面使用
[ModelBinder(typeof(PersonModelBinder))]