2011-05-06 287 views
0

我的MVC 3 web应用程序有不同的部分,需要检查用户是用户还是管理员,他们都可以访问相同的页面,除有些页面有控制器(按钮和文本框),只有管理员才能看到。我这样做,检查通过将用户的访问级别到我的视图模型,并做了检查:自定义属性重定向导致“子动作不允许执行重定向动作”错误

@if (Model.UserAccess != "Viewer") 
{ 
    [do something] 
} 

我查一下我的动作是什么访问登录的用户拥有。如果会话超时,我将它们重定向到登录页面。

我的行动是从一个项目页面视图调用,加载为局部:

@{Html.RenderAction("CategoryList", "Home", new { categoryId = Model.CategoryId });} 

我的控制器:

public PartialViewResult CategoryList(int categoryid = 0) 
{ 
    var useraccess = GetUseraccess(); 

    [blablabla stuff done here] 

    var model = new CategoryViewModel() 
    { 
     CategoryList = categorylist 
     UserAccess = useraccess 
    }; 

    return PartialView(model); 
} 

public string GetUseraccess() 
{ 
    var useraccess = "viewer"; //default 

    var check = SessionCheck(); 
    if (check == "expired") 
    { 
     ModelState.AddModelError("", "Session expired. Please login again."); 

     Response.Redirect("/Account/LogOn"); 
    } 
    else if (check == "admin") 
    { 
     useraccess = "admin"; 
    } 

    return useraccess; 
} 

public string SessionCheck() 
{ 
    if (Session["UserAccess"] == null) 
    { 
     return "expired"; 
    } 
    else if ((string)Session["UserAccess"] == "admin") 
    { 
     return "admin"; 
    } 
    else // viewer 
    { 
     return "viewer"; 
    } 
} 

现在工作正常。不过,我一直在试图实现一个自定义属性控制器被解雇之前,将检查会话的有效期:

public class CheckUserAccessSessionAttribute : ActionFilterAttribute 
{ 
    public override void OnActionExecuting(ActionExecutingContext filterContext) 
    { 
     var useraccess = filterContext.HttpContext.Session["UserAccess"]; 
     if ((string)useraccess == null) 
     { 
      filterContext.Result = new RedirectToRouteResult(new RouteValueDictionary(new { controller = "Account", action = "LogOn" })); 
     } 
    } 
} 

[CheckUserAccessSession] 
public PartialViewResult CategoryList(int categoryid = 0) 
{ 
    [same stuff as above here] 
} 

我得到的错误

Exception Details: System.InvalidOperationException: Child actions are not allowed to perform redirect actions.

我明白了为什么错误发生。但我还没有找到如何去解决它。同样,我想发送一些来自另一个自定义属性的数据给我的操作,但由于RedirectToRouteResult,这也不起作用。

回答

2

您的问题在这里,您是否正在返回该操作方法上的PartialViewResult,并且根据定义,该操作方法的输出将只是IIS提供的完整请求的一部分。您应该对操作方法进行权限检查,该方法可用于包含部分视图的完整视图。

从技术上讲,当您在初始实现中调用Response.Redirect时,您已经远离了ASP.NET MVC设计约定;即使它有效,但它的设计很糟糕。

+0

我想过,但主要很少重新加载。然而,里面的部分经常使用。所以我这样做,以便如果用户超时并返回,则必须对部分进行检查,因为主视图不会再被触发?我还能怎么做?我希望将Response.Redirect更改为RedirectToRouteResult,但这与儿童操作无法重定向的问题相同。 – LanFeusT 2011-05-06 01:00:41

+0

局域网,在这种情况下,我会做的是返回一个不同的局部视图,指示用户登录(您可以在返回时按名称指定视图);无需重新设计您的应用程序,这是您可以尝试的一件简单的事情。 – Aaronontheweb 2011-05-06 01:11:10

+0

你的第二个答案是我支持的那个:D – Aaronontheweb 2011-05-06 01:11:29

0

使用这段代码。它会工作。

protected override void HandleUnauthorizedRequest(AuthorizationContext filterContext) 
     { 
      PartialViewResult result = new PartialViewResult(); 
      result.ViewName = "noaccess"; 


      filterContext.Result = result; 
     } 
相关问题