【问题标题】:FormsAuthentication and Ajax RequestsFormsAuthentication 和 Ajax 请求
【发布时间】:2015-02-25 04:38:51
【问题描述】:

当从 jQuery 发送 ajax 请求时,我无法知道用户是否经过身份验证。

HttpContext.User.Identity 不为空,当用户从浏览器发出常规请求并且设置了aspxauth cookie 时。当用户尝试从 jQuery 发出 ajax 请求时,aspxauth 根本没有设置。

我的网络配置

<authentication mode="Forms">
    <forms loginUrl="~/" />
</authentication>

设置 FormsAuthentication Cookie

var cookie = new AuthCookie
            {
                UserId = user.UserId,
                Email = user.Email,
                Name = user.Name,
                RememberMe = createPersistentCookie,
                TimeZone = user.TimeZone,
                CompanyId = user.CompanyId,
                Roles = new List<string> { user.Role ?? "user" }
            };

            string userData = JsonConvert.SerializeObject(cookie);
            var ticket = new FormsAuthenticationTicket(1, cookie.Email, DateTime.Now,
                                                       DateTime.Now.Add(FormsAuthentication.Timeout),
                                                       createPersistentCookie, userData);
            string encTicket = FormsAuthentication.Encrypt(ticket);
            var httpCookie = new HttpCookie(FormsAuthentication.FormsCookieName, encTicket) { Expires = DateTime.Now.Add(FormsAuthentication.Timeout) };

            _httpContext.Response.Cookies.Add(httpCookie);

当我通过我的兄弟发出请求时,身份验证 cookie 出现:

每当我使用 $.get() 通过 javascript 发出请求或通过 javascript 加载 javascript 脚本/任何其他请求时,我都会得到:

奇怪的是,我在另一个 ASP 应用程序上使用了WebSecurity,而且效果很好。 auth cookie 总是从客户端发送回服务器。对于这个 ASP MVC 5 应用程序,当我尝试使用 FormAuthentication 时,我无法让 AuthCookie 继续处理所有请求。

【问题讨论】:

    标签: asp.net-mvc asp.net-mvc-5 forms-authentication


    【解决方案1】:

    您仍然可以使用 [Authorize] 等来装饰您的课程/方法。如果您要检查控制器方法内部,您可以访问从 System.Web.Mvc.Controller 或 System.Web.Http.ApiController 继承的用户属性,具体取决于您的控制器风格:

    //
    // Summary:
    //     Returns the current principal associated with this request.
    //
    // Returns:
    //     The current principal associated with this request.
    public IPrincipal User { get; set; }
    

    可以这样使用:

    if (User != null && User.Identity != null && User.Identity.IsAuthenticated)
    {
        // user has access - process request
    }
    

    编辑:

    下面是一个带有 ajax[able] 方法的 [Api]Controller 示例,该方法使用控制器的 User 属性而不是 HttpContext 的:

    public class HelloController : ApiController
    {
        [HttpGet]
        public IHttpActionResult HelloWorld()
        {
            try
            {
                if (User != null && User.Identity != null && User.Identity.IsAuthenticated)
                {
                    return Ok("Hello There " + User.Identity.Name + "!");
                }
               else
                {
                    return Ok("Hello There Anonymous!");
                }
            }
            catch { throw; }
        }
    }
    

    【讨论】:

    • 对象来自 ajax 请求时未设置用户
    • 这个 User 对象不是来自 HttpContext,而是直接来自控制器。无论请求是什么“类型”,调用任何控制器方法时都会解决此问题。我假设您的 ajax 请求调用控制器方法正确吗?
    • 目前我正在使用名为CustomAuth 的Action 顶部的授权属性来检查用户是否为空等等,但是,当我执行ajax 请求时,它始终为空。 HttpContext 没有传递给我的属性吗?
    • 我真的不确定。以我的经验,HttpContext 仅适用于传统的控制器请求(ActionResult)。因此,对于我的 ajax 控制器方法,我直接依赖 User 属性,因为自定义身份验证装饰器似乎不会在 api 控制器上触发(?)。
    • 问题是,当我向服务器发出 jQuery 请求时,aspx 身份验证不会被传输过来。它是故意这样的,所以它是安全的。常规的控制器请求可以通过浏览器正常工作,但是手动 jQuery 请求只是通过准系统。其他人如何判断 jQuery 请求是否安全?
    猜你喜欢
    • 2011-11-23
    • 2014-06-28
    • 2013-01-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-05
    • 2020-06-17
    • 2014-08-24
    相关资源
    最近更新 更多