将Dictionary <string,object>传递给MVC Controller

G-M*_*Man 15 javascript c# json asp.net-mvc-4

我试图使用AJAX将javascript对象(键值对)传递给MVC Controller操作.

控制器操作具有接收对象的Dictionary参数.

[HttpPost]
public ActionResult SearchProject(IDictionary<string, object> filter ...
Run Code Online (Sandbox Code Playgroud)

当有问题的对象为(意味着它在javascript中的值为{})时,我在调试器中看到以下内容.

在此输入图像描述

为什么控制器和操作名称会自动添加到Dictionary参数中?

使用fiddler我能够看到传递给我的控制器的内容,我没有看到传递这两个值.

如果javascript对象不为空,那么一切正常

我很难过..

Ser*_*nov 5

它附加两个值,因为默认情况下MVC注册了ValueProviderFactory:

public sealed class RouteDataValueProviderFactory : ValueProviderFactory
Run Code Online (Sandbox Code Playgroud)

返回IValueProvider的实现 - RouteDataValueProvider:

public sealed class RouteDataValueProvider : DictionaryValueProvider<object>
{
    // RouteData should use the invariant culture since it's part of the URL, and the URL should be
    // interpreted in a uniform fashion regardless of the origin of a particular request.
    public RouteDataValueProvider(ControllerContext controllerContext)
        : base(controllerContext.RouteData.Values, CultureInfo.InvariantCulture)
    {
    }
}
Run Code Online (Sandbox Code Playgroud)

基本上它只是将Dictionary绑定到当前路由的路由值.

例如,如果您将此类数据添加到以下路线RouteConfig:

routes.MapRoute(
    name: "Default",
    url: "{controller}/{action}",
    defaults: new { controller = "Home", action = "Index", SomeSpecificRouteData = 42 }
);
Run Code Online (Sandbox Code Playgroud)

那么你的字典将有3个值- controller,actionSomeSPecificRouteData.

另一个示例是您可以定义此类操作:

public ActionResult Index(string action, string controller, int SomeSpecificRouteData)
Run Code Online (Sandbox Code Playgroud)

并将RouteDataValueProvider路由中的数据作为参数传递给这些方法.以这种方式,MVC将路径中的参数绑定到动作的实际参数.

如果要删除此类行为,只需迭代ValueProviderFactories.FactoriesRouteDataValueProviderFactory从中删除即可.但是,您的路线可能会出现参数绑定问题.

  • 这并没有真正回答......在我的场景中,它是一个`IDictionary <string,IEnumerable <... >>`,我检查该值的空集.另一种方法是在检测到它时将其清空:`if(filter.ContainsKey("controller"))filter = new IDictionary <...>()`. (2认同)