J
Jeff B
I am having a very perplexing problem with setting the user's roles. I have
tried to figure this out for 2 days now.
When the user logs in to the site, I retrieve the roles from the database
and create a semicolon delimited string listing the roles returned and store
them in the forms authentication cookie. Then in the global.asax
Application_AuthenticateRequest, I retrieve the FormsAuthenticationTicket
from the forms authentication cookie, create a new FormsIdentity object,
then create a new GenericPrincipal object passing in the FormsIdentity
object and roles, and set the User to the new principal object.
Now, when I check to see if HttpContext.Current.User.IsInRole("TestRole1"),
I get different results from two different machines.
On my development machine, this works great.
(As you can see from the code below) It returns:
User is in TestRole1: True
TestRole1;TestRole2;TestRole3
On my production machine, this doesn't work.
(As you can see from the code below) It returns:
User is in TestRole1: False
TestRole1;TestRole2;TestRole3
The user is Authenticated and the roles are being set in
FormsAuthenticationTicket correctly. As far as I can tell, the two machines
are set up the same:
Development machine:
WinXP SP2, .NET Framework v1.1, IIS 5.1
Production machine:
Win2000 SP4, .NET Framework v1.1, IIS 5.0 (I think?)
I am desperately needing some insight into the problem. Does anyone have any
idea as to what might be causing this? Is it a setting I forgot? I have list
some code that I am using below, to see if that helps.
========================================
In my Login.aspx page, I have this code:
' Get ";" delimited string of the user's roles from the database
Dim roles As String = myFunctionToGetRoles(userID)
' Create the authentication ticket
Dim authTicket As FormsAuthenticationTicket = New
FormsAuthenticationTicket(1, userName, DateTime.Now,
DateTime.Now.AddMinutes(30), False, roles)
' Now encrypt the ticket
Dim encryptedTicket As String = FormsAuthentication.Encrypt(authTicket)
' Create a cookie and add the encrypted ticket to the cookie as data
Dim authCookie As HttpCookie = New
HttpCookie(FormsAuthentication.FormsCookieName, encryptedTicket)
' Add the cookie to the outgoing cookies collection
Response.Cookies.Add(authCookie)
' Redirect to the Authenticated page to avoid the misleading Security Alert
message box from popping up
Response.Redirect("Authenticated.aspx?ReturnUrl=" &
Request.QueryString.Item("ReturnUrl"), True)
In my Global.asax, I have this code:
Sub Application_AuthenticateRequest(ByVal sender As Object, ByVal e As
EventArgs)
' Fires upon attempting to authenticate the user
' Extract the forms authentication cookie
Dim authCookie As HttpCookie =
Context.Request.Cookies(FormsAuthentication.FormsCookieName)
If authCookie Is Nothing Then
' There is no authentication cookie
Exit Sub
End If
Dim authTicket As FormsAuthenticationTicket
Try
authTicket = FormsAuthentication.Decrypt(authCookie.Value)
Catch ex As Exception
' Log exception details omitted for simplicity
Exit Sub
End Try
If authTicket Is Nothing Then
' Cookie failed to decrypt
Exit Sub
End If
' When the ticked was created, the UserData property was
' assigned a semicolon delimited string of role names.
Dim roles As String() = authTicket.UserData.Split(";"c)
' Create an Identity object
Dim id As FormsIdentity = New FormsIdentity(authTicket)
' This principal will flow throughout the request
Dim principal As GenericPrincipal = New GenericPrincipal(id, roles)
' Attach the new principal object to the current HttpContext object
Context.User = principal
End Sub
And on my Default.aspx page, I test the roles with this code:
' Test the User's Roles
Dim curUser As System.Security.Principal.IPrincipal =
HttpContext.Current.User
If curUser.Identity.IsAuthenticated Then
If thisUser.IsInRole("TestRole1") Then
lblMessage.Text = "User is in TestRole1: True"
Else
lblMessage.Text = "User is in TestRole1: False"
End If
Dim id As FormsIdentity = CType(HttpContext.Current.User.Identity,
FormsIdentity)
Dim ticket As FormsAuthenticationTicket = id.Ticket
' Get the stored user-data, in this case, our roles
' stored in the User.Identity, and display them
lblMessage.Text += "<br>" + ticket.UserData
End If
Thanks to everyone in advance,
Jeff
tried to figure this out for 2 days now.
When the user logs in to the site, I retrieve the roles from the database
and create a semicolon delimited string listing the roles returned and store
them in the forms authentication cookie. Then in the global.asax
Application_AuthenticateRequest, I retrieve the FormsAuthenticationTicket
from the forms authentication cookie, create a new FormsIdentity object,
then create a new GenericPrincipal object passing in the FormsIdentity
object and roles, and set the User to the new principal object.
Now, when I check to see if HttpContext.Current.User.IsInRole("TestRole1"),
I get different results from two different machines.
On my development machine, this works great.
(As you can see from the code below) It returns:
User is in TestRole1: True
TestRole1;TestRole2;TestRole3
On my production machine, this doesn't work.
(As you can see from the code below) It returns:
User is in TestRole1: False
TestRole1;TestRole2;TestRole3
The user is Authenticated and the roles are being set in
FormsAuthenticationTicket correctly. As far as I can tell, the two machines
are set up the same:
Development machine:
WinXP SP2, .NET Framework v1.1, IIS 5.1
Production machine:
Win2000 SP4, .NET Framework v1.1, IIS 5.0 (I think?)
I am desperately needing some insight into the problem. Does anyone have any
idea as to what might be causing this? Is it a setting I forgot? I have list
some code that I am using below, to see if that helps.
========================================
In my Login.aspx page, I have this code:
' Get ";" delimited string of the user's roles from the database
Dim roles As String = myFunctionToGetRoles(userID)
' Create the authentication ticket
Dim authTicket As FormsAuthenticationTicket = New
FormsAuthenticationTicket(1, userName, DateTime.Now,
DateTime.Now.AddMinutes(30), False, roles)
' Now encrypt the ticket
Dim encryptedTicket As String = FormsAuthentication.Encrypt(authTicket)
' Create a cookie and add the encrypted ticket to the cookie as data
Dim authCookie As HttpCookie = New
HttpCookie(FormsAuthentication.FormsCookieName, encryptedTicket)
' Add the cookie to the outgoing cookies collection
Response.Cookies.Add(authCookie)
' Redirect to the Authenticated page to avoid the misleading Security Alert
message box from popping up
Response.Redirect("Authenticated.aspx?ReturnUrl=" &
Request.QueryString.Item("ReturnUrl"), True)
In my Global.asax, I have this code:
Sub Application_AuthenticateRequest(ByVal sender As Object, ByVal e As
EventArgs)
' Fires upon attempting to authenticate the user
' Extract the forms authentication cookie
Dim authCookie As HttpCookie =
Context.Request.Cookies(FormsAuthentication.FormsCookieName)
If authCookie Is Nothing Then
' There is no authentication cookie
Exit Sub
End If
Dim authTicket As FormsAuthenticationTicket
Try
authTicket = FormsAuthentication.Decrypt(authCookie.Value)
Catch ex As Exception
' Log exception details omitted for simplicity
Exit Sub
End Try
If authTicket Is Nothing Then
' Cookie failed to decrypt
Exit Sub
End If
' When the ticked was created, the UserData property was
' assigned a semicolon delimited string of role names.
Dim roles As String() = authTicket.UserData.Split(";"c)
' Create an Identity object
Dim id As FormsIdentity = New FormsIdentity(authTicket)
' This principal will flow throughout the request
Dim principal As GenericPrincipal = New GenericPrincipal(id, roles)
' Attach the new principal object to the current HttpContext object
Context.User = principal
End Sub
And on my Default.aspx page, I test the roles with this code:
' Test the User's Roles
Dim curUser As System.Security.Principal.IPrincipal =
HttpContext.Current.User
If curUser.Identity.IsAuthenticated Then
If thisUser.IsInRole("TestRole1") Then
lblMessage.Text = "User is in TestRole1: True"
Else
lblMessage.Text = "User is in TestRole1: False"
End If
Dim id As FormsIdentity = CType(HttpContext.Current.User.Identity,
FormsIdentity)
Dim ticket As FormsAuthenticationTicket = id.Ticket
' Get the stored user-data, in this case, our roles
' stored in the User.Identity, and display them
lblMessage.Text += "<br>" + ticket.UserData
End If
Thanks to everyone in advance,
Jeff