问题
I have made a website with a page that includes a razor form. The user can login on this form and then redirects to a different page. The logging in (and logging out) works with formsauthentication succesfully. However, I can't seem to use HttpContext.Current.User.Identity.Name to retrieve the stored username (in the formsauthentication cookie). It returns an empty string "".
I am using MVC 5 and ASP 4.5 with no standard membership or role providers.
Login:
[HttpPost]
public ActionResult Login(User user)
{
if (ModelState.IsValid)
{
bool authenticated = userscontroller.isAuthorized(user.Email, user.Password);
if (authenticated)
{
if (userscontroller.isAuthenticated())
{
userscontroller.deAuthenticateUser();
}
userscontroller.authenticateUser(user);
return Redirect(Url.Action("Index", "Home"));
}
}
}
Authenticating the user:
public void authenticateUser(User user)
{
FormsAuthentication.SetAuthCookie(user.Username, false);
}
Then getting the name of the user:
public User userFromCookie()
{
if (isAuthenticated())
{
return getUserByUsername(HttpContext.Current.User.Identity.Name);
}
else { return null; }
}
isauthenticated()
public bool isAuthenticated()
{
if (System.Web.HttpContext.Current.User.Identity.IsAuthenticated)
{
return true;
}
else
{
return false;
}
}
Webconfig:
<authentication mode="Forms">
<forms loginUrl="~/Account/Login" timeout="2880" />
</authentication>
<authorization > <deny users="?"/> </authorization>
So the identity.name returns "".
Help is appreciated!
回答1:
Possible reasons it does not work.
- You are just calling it wrong. Try
this.User.Identity.Name
- The cookie is not being persisted in the Response object so the user is actually not authenticated in the next request.
- You do not have your web.config configured to make use of forms authentication with cookies.
Here is a fully working example I created for you. This whole thing works, the only dependency is on a Newtonsoft library but you could remove that and put anything you want in the user data.
Here is the user controller
using System;
using System.Web;
using System.Web.Mvc;
using System.Web.Security;
namespace TestAuth.Controllers
{
public class UserModel
{
public string UserName { get; set; }
public string Password { get; set; }
public bool RememberMe { get; set; }
}
public class UserInfo
{
public string UserName { get; set; }
}
public class UserController : Controller
{
[AllowAnonymous]
public ActionResult Login()
{
var model = new UserModel() {Password = "password",UserName = "ItsMe", RememberMe = true};
var serializedUser = Newtonsoft.Json.JsonConvert.SerializeObject(model);
var ticket = new FormsAuthenticationTicket(1, model.UserName, DateTime.Now, DateTime.Now.AddHours(3), model.RememberMe, serializedUser);
var encryptedTicket = FormsAuthentication.Encrypt(ticket);
var isSsl = Request.IsSecureConnection; // if we are running in SSL mode then make the cookie secure only
var cookie = new HttpCookie(FormsAuthentication.FormsCookieName, encryptedTicket)
{
HttpOnly = true, // always set this to true!
Secure = isSsl,
};
if (model.RememberMe) // if the user needs to persist the cookie. Otherwise it is a session cookie
cookie.Expires = DateTime.Today.AddMonths(3); // currently hard coded to 3 months in the future
Response.Cookies.Set(cookie);
return View(); // return something
}
[Authorize]
public ActionResult ShowUserName()
{
return View(new UserInfo() {UserName = this.User.Identity.Name});
}
}
}
Here are the views. View Login.cshtml
Logged in
<br/>
@Html.ActionLink("Show the user their name", "ShowUserName", "User")
View ShowUserName.cshtml
@model TestAuth.Controllers.UserInfo
<h2>title</h2>
user name = @Model.UserName
web.config section Note that the key was generated from some web site that came up in a google search. You should probably look into getting your own and with the correct encryption types as the site I used was somewhat dated.
<system.web>
<authentication mode="Forms">
<forms name="myAuthCookie" ticketCompatibilityMode="Framework40" cookieless="UseCookies" requireSSL="false" timeout="180" protection="Encryption" />
</authentication>
<machineKey
validationKey="DA87693F33607268657E61BCF16D2EAFE339ECE0F6C9B94DFA0FE5BBCA0035EB320F81662A32D98F0A0D2A5DCBE3E678EDF216FBD45CB8BD6F13489D1548214C"
decryptionKey="26F44FEF28C3466FAB261CEF4844535678578C6658F85C6ADAE17A99B0947468"
validation="SHA1" decryption="AES"/>
<compilation debug="true" targetFramework="4.6"/>
<httpRuntime targetFramework="4.6"/>
</system.web>
来源:https://stackoverflow.com/questions/32564984/using-formsauthentication-for-login-and-use-httpcontext-current-user-identity