代码改变世界

[MVC] 自定义ActionSelector,根据参数选择Action

2012-12-25 11:35  Zork  阅读(2185)  评论(1编辑  收藏  举报

很多时候我们会根据UI传入的参数,呈现不同的View。也就是对于同一个Action如何根据请求数据返回不同的View。通常情况下我们会按照如下方法来写,例如:

[AcceptVerbs(HttpVerbs.Post)]
public ActionResult LoadTreeNodes(TreeViewItem treeViewItem)
{
    var nodeText = treeViewItem.Text.ToLower();
    if (nodeText == "videos")
    {
        ……
        return View("videos");
    }
    if (nodeText == "news")
    {
        ……
        return View("news");
    }return View("index");
} 

这个时候Action 里面会有很多的if else. 其实,我们忽略了MVC 提供的 ActionNameSelectorAttribute.  我们完全可以自定义ActionNameSelectorAttribute来实现上诉功能。 MVC中的ActionNameAttribute就是继承自ActionNameSelectorAttribute。达到多个Action对应同一个ActionName的目的。

自定义TreeNodeActionSelectorAttribute

[AttributeUsage(AttributeTargets.Method, AllowMultiple = false, Inherited = true)]
public class TreeNodeActionSelectorAttribute : ActionNameSelectorAttribute
{
    public string TreeNodeText { get; private set; }
    public TreeNodeActionSelectorAttribute(string nodeText)
    {
        if (String.IsNullOrEmpty(nodeText))
        {
            throw new ArgumentException("nodeText");
        }
        this.TreeNodeText = nodeText;
    }
    public override bool IsValidName(ControllerContext controllerContext, string actionName, MethodInfo methodInfo)
    {
        var text = controllerContext.RequestContext.HttpContext.Request["text"];
        return String.Equals(this.TreeNodeText, text, StringComparison.OrdinalIgnoreCase);
     }
}

改造Action

[ActionName(“LoadTreeNodes”)]
[TreeNodeActionSelector (“videos”)]
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult LoadVideoNodes(TreeViewItem treeViewItem)
{
    ……
    return View("videos");
}
[ActionName(“LoadTreeNodes”)]
[TreeNodeActionSelector (“news”)]
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult LoadNews(TreeViewItem treeViewItem)
{
    ……
    return View("news");
}
......

有些时候我们可能需要根据用户属于不同的角色,返回不同的View。这种情况也可以通过自定义ActionNameSelectorAttribute来实现。具体如何做请参考:http://www.cnblogs.com/anytao/archive/2009/04/22/1440883.html