I’m having problems with the AntiForgeryToken in ASP.Net MVC. If I do an iisreset on my web server and a user continues with their session they get bounced to a login page.
For now I've gone with a solution that scrubs the cookie if the exception is thrown. If the exception is thrown again I'll just let it happen as it was.
I won't mark this as 'the' answer for now in the hope that someone has a better answer.
public static class MyAntiForgeryExtensions
{
// Methods
public static string MyAntiForgeryToken(this HtmlHelper helper)
{
return MyAntiForgeryToken(helper, null);
}
public static string MyAntiForgeryToken(this HtmlHelper helper, string salt)
{
string fragment;
string path = helper.ViewContext.HttpContext.Request.ApplicationPath;
try
{
fragment = helper.AntiForgeryToken(salt, null, path);
}
catch (HttpAntiForgeryException)
{
// okay, scrub the cookie and have another go.
string cookieName = GetAntiForgeryTokenName(path);
helper.ViewContext.HttpContext.Request.Cookies.Remove(cookieName);
fragment = helper.AntiForgeryToken(salt, null, path);
}
return fragment;
}
#region AntiForgeryData code that shouldn't be sealed
// Copied from AntiForgeryData since they aren't accessible.
internal static string GetAntiForgeryTokenName(string appPath) {
if (String.IsNullOrEmpty(appPath)) {
return "__RequestVerificationToken";
}
else {
return "__RequestVerificationToken_" + Base64EncodeForCookieName(appPath);
}
}
private static string Base64EncodeForCookieName(string s) {
byte[] rawBytes = Encoding.UTF8.GetBytes(s);
string base64String = Convert.ToBase64String(rawBytes);
// replace base64-specific characters with characters that are safe for a cookie name
return base64String.Replace('+', '.').Replace('/', '-').Replace('=', '_');
}
#endregion
}