我有一个MVC应用程序,其中我有一个用户类和用户也可以模拟其他用户(管理员用户)。

所以,我有低于认证该代码请求和实例化我的版本用户类。

然后,它试图获得从会话对象模拟的用户,但会话不可用在在Global.asax此方法。

希望这是很有意义的。

我还能怎么做呢?

我的问题,我的猜测是,你可以访问Session对象为每个请求哪一点在Global.asax方法呢?

protected void Application_OnAuthenticateRequest(object sender, EventArgs e)
{
    IMylesterService service = ObjectFactory.GetInstance<IMylesterService>();

    if (Context.User != null)
    {
        if (Context.User.Identity.IsAuthenticated)
        {
            User user = service.GetUser(Context.User.Identity.Name);
            if (user == null)
                throw new ApplicationException("Context.user.Identity.name is not a recognized user");

            User impersonatedUser = (User)this.Session["ImpersonatedUser"];
            if (impersonatedUser == null)
                user.ImpersonatedUser = user;
            else
                user.ImpersonatedUser = impersonatedUser;

            System.Threading.Thread.CurrentPrincipal = Context.User = user;
            return;
        }
    }
    User guest = service.GetGuestUser();
    guest.ImpersonatedUser = guest;

    System.Threading.Thread.CurrentPrincipal = Context.User = guest;
}

没有正确的解决方案

其他提示

尝试创建授权滤波器:

public class CustomAuthorizationFilter : AuthorizeAttribute
{
    protected override bool AuthorizeCore(System.Web.HttpContextBase httpContext)
    {
        // perform your authorization here
        // full access to HttpContext and session
    }
}

您可以那么该属性适用于您的控制器。理想情况下,你就会有一个基本的控制器,所有其他控制器继承,你可以在该控制器上类级别应用的属性。然后,所有的请求将被授权并应用模拟,你在上面编码。

会话不会AuthenticateRequest期间可用:你将需要做的是标签所需的资料到Identity.userData;所以,如果你在哪里使用表单身份验证执行以下示例:

void Application_AuthenticateRequest(object sender, EventArgs e)
{
   if (Context.User != null)
   {
     if (Context.User.Identity.IsAuthenticated)
     {
       // retrieve the value 
       var id = (FormsIdentity)Context.User.Identity;
       var myvalue = id.Ticket.UserData; // "Here you are"
     }
   }
}

有关使用形式的符号,你需要编写自定义的cookie: MVC - >类FormsAuthenticationService:IFormsAuthenticationService

public static void SetAuthenticationCookie(HttpContextBase context, FormsAuthenticationTicket ticket)
{
    var cookie = new HttpCookie(FormsAuthentication.FormsCookieName)
       {
          Value = FormsAuthentication.Encrypt(ticket),
          Secure = FormsAuthentication.RequireSSL,
          Domain = FormsAuthentication.CookieDomain,
          HttpOnly = true,
          Expires = DateTime.Now.AddMinutes(15)
       };

    if (!context.Request.IsSecureConnection && FormsAuthentication.RequireSSL)
    {
        throw new HttpException("Ticket requires SSL.");
    }
    context.Response.Cookies.Add(cookie);
}
public static FormsAuthenticationTicket CreateTicket(HttpContextBase context, string emailAddress, string userData, bool persist)
{
    return new FormsAuthenticationTicket(1, emailAddress, DateTime.Now, DateTime.Now.AddMinutes(15), persist, userData, FormsAuthentication.FormsCookiePath);
}

最后,在签到你现在通过调用CreateTicket创建所需的车票(...),然后你会写出来的SetAuthenticationCookie(...)。

public void SignIn(string userName, string password)
{
    if(CheckUserValid(userName,password, out string email))
    {
        var ticket = CreateTicket(email, "Here you are", true);
        SetAuthenticationCookie(HttpContext.Current.Base(), ticket);
    }
}

我从来没有使用过,但假设的AcquireRequestState期间会话状态被分配:

public void Init(HttpApplication context)
{
    context.AcquireRequestState += new EventHandler(context_AcquireRequestState);
}

我有同样的需要,以在Global.asax中访问会话的问题,最后通过移动我的代码进入AcquireRequestState处理程序,认证通过后,这恰好解决了这个问题。

    protected void Application_AcquireRequestState(Object sender, EventArgs e)
    {
        if (Request.IsAuthenticated && Context.Session != null)
        {
            // access Context.Session
        }
    }

此火灾了很多,当前上下文不总是具有一个有效的会话对象,因此检查。

修改:必须添加在检查IsAuthenticated太 - 登出时得到了一个空的错误。现在巨大的。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top