繁体   English   中英

需要针对多种不同情况在ASP.NET MVC站点上进行全局定向重定向的建议

[英]Need recommendation for global, targeted redirects on ASP.NET MVC site for multiple differing conditions

我正在使用ASP.NET MVC应用程序,管理员可以在其中添加新用户并标记他们以完成其他信息,然后他们才能使用网站的其他功能。 例如,我们有一个“ ForcePasswordReset”布尔值,以及完成安全问题的要求。 我们没有为这些用户使用Active Directory。

最终,这是我想要实现的行为:

  1. 将需要更改密码的所有已登录用户定向到ChangePassword视图。 并且,如果该用户单击其他链接,则将其引导回ChangePassword视图。
  2. 对于必须更改其安全性问题的用户,情况相同。

最初,我将支票直接放入Login Controller ActionResult中。 但这仅解释了登录操作。 下面是一个简短的代码示例。

public ActionResult Login(LoginModel model, string returnUrl)
    {
        if (ModelState.IsValid)
        {    
            // ...

            // Does the user need to complete some missing information?
            if (externalUser.IsSecurityQuestionInfoComplete == false)
                return RedirectToAction("ChangeSecurityQuestions", "MyInfo");
            if (externalUser.ForcePasswordReset)
                return RedirectToAction("ChangePassword", "MyInfo");

            // Login was successful
            return RedirectToLocal(returnUrl);
        }
    }

这种方法的一个问题是,在那些目标视图中还存在其他超链接,用户可以在其中导航离开目标界面。 因此,例如,定向到ChangeSecurityQuestions视图的用户只需单击即可。

登录的用户可以随时更改这些设置。 我可以为更改密码和安全性问题创建重复的视图,这些视图仅适用于这种情况,在这种情况下,用户被迫更新这些值。 为了保持DRY并减少维护,我想在两种情况下使用相同的视图(仅想编辑该信息的用户和被迫编辑该信息的用户)。 但是,如果替代方案更糟,尝试在这方面保持DRY可能会出错。

我开始在助手类中编写一种方法来转移这些用户的权限,尝试类似的方法。

    /// <summary>
    /// Check scenarios where the ExternalUser needs to complete some missing information, and divert as necessary.
    /// </summary>
    public static void divertExternalUserAsRequired(Controller controller, ExternalUser externalUser)
    {
        if (externalUser.IsSecurityQuestionInfoComplete == false)
            return controller.RedirectToAction("ChangeSecurityQuestions", "MyInfo");

        if (externalUser.ForcePasswordReset)
            return controller.RedirectToAction("ChangePassword", "MyInfo");
    }

但是由于保护级别的原因,该RedirectToAction无法访问。 而且,似乎不建议这样做( 是否可以在自定义AuthorizeAttribute类内使用RedirectToAction()? )。 而且我不喜欢通过在整个地方粘贴此检查来增加我的控制器的想法。

UtilityHelpers.divertExternalUserAsRequired(this, externalUser);

建议使用什么方法来处理这种情况? 我认为这是在全局范围内实现的,可以在加载任何相关视图时运行检查。

谢谢你的帮助。

如果我正确理解了您的问题,那么您可以使用几种选择。

一种选择是检查Global.asax.cs类中Application_BeginRequest中的必要条件。 在每个请求的开始都会调用此方法,如果条件失败,则可以像下面这样加载其他控制器操作:

    protected void Application_BeginRequest(object sender, EventArgs e)
    {
        if (!externalUser.IsSecurityQuestionInfoComplete)
        {
            var routeData = new RouteData();
            routeData.Values["action"] = "MyInfo";
            routeData.Values["controller"] = "ChangeSecurityQuestions";

            RequestContext requestContext = new RequestContext(new HttpContextWrapper(Context), routeData);

            IController errorController = new ChangeSecurityQuestionsController();
            errorController.Execute(requestContext);

            requestContext.HttpContext.Response.End();
        }
    }

您可以使用的另一种选择是创建并注册全局动作过滤器 正如您在问题中提到的那样,您不喜欢用这些条件检查乱扔控制器的想法。 通过注册全局动作过滤器,您的控制器可以完全不知道针对它执行的动作过滤器。 您需要做的就是在Global.asax.cs注册操作过滤器,如下所示:

protected void Application_Start()
{
    ...

    GlobalFilters.Filters.Add(new SecurityQuestionCompleteFilter());

    ...
}

我希望这有帮助。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM