开发者

ASP.NET MVC: Specify value provider on a per-action or per-route basis?

I'm trying to set up an action in A开发者_如何学编程SP.NET MVC 3 to handle the payload of a mercurial webhook request - in this case, generated by Kiln.

The payload is JSON, but unfortunately it is sent as a URL encoded form value with the content type application/x-www-form-urlencoded, because apparently using application/json and sending it unencoded with no parameter name would make it too easy and um... standard.

This means that I can't just use the new JsonValueProviderFactory because it only picks up requests using the standard application/json content type. And of course I can't just kludge the factory to also pick up application/x-www-form-urlencoded requests too, because I need those requests to use the form data value provider everywhere else in my app that's actually receiving form data and not JSON.

So, is there a way I can specify that a ValueProvider or ValueProviderFactory should only be used for a specific action or route?


If you create a specific controller to handle these webhook requests, you can assign your unique ValueProvider when you instantiate your controller.

public class KilnController : Controller
{

    public KilnController()
    {
        this.ValueProvider = MyCustomValueProvider;
    }

    ...
}

This should fulfill your need for a custom ValueProvider for these requests.


Turns out that IValueProvider was not the particular bit of extensibility I was looking for - I just needed to use a quick IModelBinder implementation I found courtesy of James Hughes. It needed a little tweaking to cover pulling something out of the form:

public class JsonFormModelBinder : IModelBinder
{
    #region [ ModelBinder Members ]

    Object IModelBinder.BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
    {
        HttpRequestBase request = controllerContext.HttpContext.Request;
        var jsonStringData = request.Form[bindingContext.ModelName];
        if (jsonStringData != null) return JsonConvert.DeserializeObject(jsonStringData, bindingContext.ModelType);
        else return null;
    }

    #endregion
}

And the usage:

    [HttpPost]        
    public ActionResult WebHook([ModelBinder(typeof(JsonFormModelBinder))] WebHookMessage payload)
    {
        return Content("OK");
    }
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜