WebApi - Bind from both Uri and Body

前端 未结 4 1550
小鲜肉
小鲜肉 2020-12-13 12:51

Is it possible to bind a model from both the Uri and Body?

For instance, given the following:

routes.MapHttpRoute(
    name: \"API Default\",
    rou         


        
4条回答
  •  盖世英雄少女心
    2020-12-13 13:36

    Alright, I came up with a way to do it. Basically, I made an action filter which will run after the model has been populated from JSON. It will then look at the URL parameters, and set the appropriate properties on the model. Full source below:

    using System.ComponentModel;
    using System.Linq;
    using System.Net;
    using System.Net.Http;
    using System.Reflection;
    using System.Web.Http.Controllers;
    using System.Web.Http.Filters;
    
    
    public class UrlPopulatorFilterAttribute : ActionFilterAttribute
    {
        public override void OnActionExecuting(HttpActionContext actionContext)
        {
            var model = actionContext.ActionArguments.Values.FirstOrDefault();
            if (model == null) return;
            var modelType = model.GetType();
            var routeParams = actionContext.ControllerContext.RouteData.Values;
    
            foreach (var key in routeParams.Keys.Where(k => k != "controller"))
            {
                var prop = modelType.GetProperty(key, BindingFlags.IgnoreCase | BindingFlags.Instance | BindingFlags.Public);
                if (prop != null)
                {
                    var descriptor = TypeDescriptor.GetConverter(prop.PropertyType);
                    if (descriptor.CanConvertFrom(typeof(string)))
                    {
                        prop.SetValueFast(model, descriptor.ConvertFromString(routeParams[key] as string));
                    }
                }
            }
        }
    }
    

提交回复
热议问题