Lab: Creating a Secure Application

Lab: Creating a Secure Application

In this lab, you ll create a simple application that uses Forms authentication to identify and authorize users. The application allows new users to add their user name and password, allows existing users to sign in, and displays the user s identity once he or she has signed in. When complete, the Web application will appear as shown in Figure 8-25.

figure 8-25 the login and userinfo web forms

Figure 8-25. The LogIn and UserInfo Web forms

Estimated lesson time: 30 minutes

Exercise 1: Enable Forms Authentication

To enable Forms authentication:



  1. Create a new ASP.NET Web Forms application, and open the Web.config file generated for the project.

  2. Make the changes to the <authentication> element shown here:

    <authentication mode="Forms"> <forms loginUrl="LogIn.aspx"> <credentials passwordFormat="SHA1"> </credentials> </forms> </authentication>

  3. The preceding authentication settings enable Forms authentication, direct unauthenticated users to the LogIn.aspx Web form, and enable password encryption using the SHA1 algorithm. To require authentication using these settings, add the following <authorization> element to the Web.config file:

    <authorization> <deny users="?" /> <!-- Deny unauthorized users --> </authorization>

This authorization setting denies access to any unauthenticated users, thus forcing authentication.

When the changes to Web.config have been made, you can create the LogIn.aspx Web form that allows users to add new accounts and to log on to existing ones.

Exercise 2: Create the LogIn Web Form

In this exercise, you ll create a Web form named LogIn.aspx and a data file named Users.xml that are used to authenticate users. Because this is a simplified example, LogIn.aspx allows users to create a new account if their user name was not found.

In the real world, you might want to direct users to a separate Web form for creating new accounts or you might want an administrator to create their accounts and e-mail their passwords back to them. In either case, the basic concepts are the same.

To create the LogIn Web form and user data file:

  1. Use Visual Studio or another text editor to create a text file containing the following line:

    <users name="" password="" />

  2. The sample will use this file to as a template to store user names and passwords. Because passwords will be encrypted, the first name and passwords are blank you can delete this line later, after other user names and passwords have been added.

  3. Create the LogIn.aspx Web form. This Web form contains text boxes, validation, and other controls, as shown in the following table.

    Control type

    Property

    Value

    Label

    Text

    User name:

    TextBox

    ID

    txtUserName

    RequiredFieldValidator

    ID

    vldUserName

    ControlToValidate

    txtUserName

    ErrorMessage

    Name is required.

    Label

    Text

    Password:

    TextBox

    ID

    txtPassword

    TextMode

    Password

    RequiredFieldValidator

    ID

    vldPassword

    ControlToValidate

    txtPassword

    ErrorMessage

    Password is required.

    Button

    ID

    butSignOn

    Text

    Sign On

    Button

    ID

    butAddUser

    Text

    Add User

    Visible

    False

    Label

    ID

    lblStatus

  4. Begin writing the code for LogIn.aspx by adding the following line to beginning of the Login.aspx code module:

    Visual Basic .NET

    Imports System.Web.Security

    Visual C#

    using System.Web.Security;

  5. Add the following code to the butSignOn control s Click event procedure to check the user name and password and to prompt the user if the user name is not found. The event procedure will use two helper functions: UserExists to check whether the user name exists in Users.xml, and PasswordValid to check whether the entered password is valid.

    Visual Basic .NET

    Private Sub butSignOn_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles butSignOn.Click ' Check the user name. If UserExists(txtUserName.Text) Then ' Check the password (encrypted). If PasswordValid(txtUserName.Text, txtPassword.Text) Then ' Sign the user on. FormsAuthentication.RedirectFromLoginPage(txtUserName.Text, _ True) Else ' Display an invalid password message. lblStatus.Text = "Password does not match. Try again." End If Else ' If user name not found, offer to add it. lblStatus.Text = "User name not found. Click Add User to add it now." ' Make Add User button visible. butAddUser.Visible = True End If ' Keep track of tries. Session("Tries") = CInt(Session("Tries")) + 1 If Session("Tries") > 2 Then ' After third try, deny access. Response.Redirect("Denied.htm") End If End Sub

    Visual C#

    private void butSignOn_Click(object sender, System.EventArgs e) { // Check the user name. if (UserExists(txtUserName.Text)) // Check the password (encrypted). if (PasswordValid(txtUserName.Text, txtPassword.Text)) // Sign the user on. FormsAuthentication.RedirectFromLoginPage(txtUserName.Text, true); else // Display an invalid password message. lblStatus.Text = "Password does not match. Try again."; else { // If user name not found, offer to add it. lblStatus.Text = "User not found. Click Add User to add it now."; // Make Add User button visible. butAddUser.Visible = true; } // Keep track of tries. ViewState["Tries"] = System.Convert.ToInt32(ViewState["Tries"]) + 1; if (System.Convert.ToInt32(ViewState["Tries"]) > 3) Response.Redirect("Denied.htm"); }

  6. Add the UserExists and PasswordValid functions to load the Users.xml file into a data set and then search through the data set for a matching user name and password. If a match is found, the functions return True; otherwise, they return False as shown below:

    Visual Basic .NET

    Private Function UserExists(ByVal UserName As String) As Boolean ' Create a data set to read the XML file. Dim dsUsers As New DataSet() ' Use error handling in case is file missing. Try ' Build the Users.xml file path. Dim strXMLFile As String = Server.MapPath(".") & _  "\Users.xml" ' Read the file dsUsers.ReadXml(strXMLFile, XmlReadMode.InferSchema) ' For each row in the Users table. Dim rowUser As DataRow For Each rowUser In dsUsers.Tables("Users").Rows ' Check for name match. If rowUser("name") = UserName Then Return True Exit For End If Next Catch ' In case of error return False. Return False End Try End Function Private Function PasswordValid(ByVal UserName As String, _ ByVal Password As String) ' Create a data set to read the XML file. Dim dsUsers As New DataSet() ' Use error handling in case is file missing. Try ' Build the Users.xml file path. Dim strXMLFile As String = Server.MapPath(".") & _  "\Users.xml" ' Read the file dsUsers.ReadXml(strXMLFile, XmlReadMode.InferSchema) ' For each row in the Users table. Dim rowUser As DataRow For Each rowUser In dsUsers.Tables("Users").Rows ' Check for name match. If rowUser("name") = UserName Then If rowUser("password") = _ FormsAuthentication.HashPasswordForStoringInConfigFile_ (Password, "SHA1") Then Return True Exit For End If End If Next Catch ' In case of error return false. Return False End Try End Function

    Visual C#

    private bool UserExists(string UserName) { // Create a data set to read the XML file. DataSet dsUsers = new DataSet(); // Use error handling in case is file missing. try { // Build the Users.xml file path. string strXMLFile = Server.MapPath(".") +  "\\Users.xml"; // Read the file dsUsers.ReadXml(strXMLFile, XmlReadMode.InferSchema); // For each row in the Users table. foreach (DataRow rowUser in dsUsers.Tables["Users"].Rows) // Check for name match. if (rowUser["name"].ToString() == UserName) return true; } catch { // In case of error return False. return false; } // Otherwise, return false return false; } private bool PasswordValid(string UserName, string Password) { // Create a data set to read the XML file. DataSet dsUsers = new DataSet(); // Use error handling in case is file missing. try { // Build the Users.xml file path. string strXMLFile = Server.MapPath(".") +  "\\Users.xml"; // Read the file dsUsers.ReadXml(strXMLFile, XmlReadMode.InferSchema); // For each row in the Users table. foreach (DataRow rowUser in dsUsers.Tables["Users"].Rows) // Check for name match. if (rowUser["name"].ToString() == UserName) if (rowUser["password"].ToString() == FormsAuthentication.HashPasswordForStoringInConfigFile (Password, "SHA1")) return true; } catch { // In case of error return False. return false; } // Otherwise, return false. return false; }

  7. The PasswordValid function in the preceding code uses the HashPasswordForStoringInConfigFile method because the passwords are stored using encryption. Create an AddUser function using the same method to store the password in Users.xml, as shown in the following code:

    Visual Basic .NET

    Private Sub butAddUser_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles butAddUser.Click If AddUser(txtUserName.Text, txtPassword.Text) Then ' Display success. lblStatus.Text = "User added. Click Sign On to continue." ' Hide button. butAddUser.Visible = False Else ' Display failure. lblStatus.Text =_  "User could not be added. Choose a different name." End If End Sub Private Function AddUser(ByVal UserName As String, ByVal Password _ As String) ' If the user already exists, return False and exit. If UserExists(UserName) Then Return False Exit Function End If ' Otherwise, add user to XML file. Dim dsUsers As New DataSet() ' Use error handling in case is file missing. Try ' Build the Users.xml file path. Dim strXMLFile As String = Server.MapPath(".") & _  "\Users.xml" ' Read the file. dsUsers.ReadXml(strXMLFile, XmlReadMode.InferSchema) ' Add a new row. Dim rowUser As DataRow = dsUsers.Tables("users").NewRow() ' Set Username. rowUser("name") = UserName ' Set password (encrypted). rowUser("password") = _ FormsAuthentication.HashPasswordForStoringInConfigFile _ (Password, "SHA1") ' Add row. dsUsers.Tables("users").Rows.Add(rowUser) ' Write data set. dsUsers.WriteXml(strXMLFile) Return True Catch ' In case of error return False. Return False End Try End Function

    Visual C#

    private void butAddUser_Click(object sender, System.EventArgs e) { if (AddUser(txtUserName.Text, txtPassword.Text)) { // Display success. lblStatus.Text = "User added. Click Sign On to continue."; // Hide button. butAddUser.Visible = false; } else // Display failure. lblStatus.Text =  "User could not be added. Choose a different name."; } private bool AddUser(string UserName, string Password) { // If the user already exists, return False and exit. if (UserExists(UserName)) { return false; } // Otherwise, add user to XML file. DataSet dsUsers = new DataSet(); // Use error handling in case is file missing. try { // Build the Users.xml file path. string strXMLFile = Server.MapPath(".") +  "\\Users.xml"; // Read the file. dsUsers.ReadXml(strXMLFile, XmlReadMode.InferSchema); // Add a new row. DataRow rowUser = dsUsers.Tables["users"].NewRow(); // Set Username. rowUser["name"] = UserName; // Set password (encrypted). rowUser["password"] = FormsAuthentication.HashPasswordForStoringInConfigFile (Password, "SHA1"); // Add row. dsUsers.Tables["users"].Rows.Add(rowUser); // Write data set. dsUsers.WriteXml(strXMLFile); return true; } catch { // In case of error return false. return false; } }

Exercise 3: Display User Information

In this exercise, you ll create the UserInfo.aspx Web form to display the user s name and authentication information using the User class s Identity object. You ll also create an HTML page to display if access is denied. Because HTML pages aren t automatically included in a Web application s authentication scheme, users can access that page even if they aren t authenticated.

To display user information:

  1. Create the UserInfo.aspx Web form and make it the start page for the application. Unauthenticated users will actually be directed to the LogIn.aspx Web form first, because that s the login page specified in Web.config. After users are authenticated, they are directed to the application s start page by the RedirectFromLoginPage method.

  2. Add a table to the UserInfo.aspx page in which to display the user name and authentication information and a command button to allow the user to sign out from the application. The table includes named <span> elements as placeholders for the user data, as shown in the following HTML:

    <H2>Forms Authorization</H2> <TABLE  borderColor="black" cellSpacing="1" cellPadding="1" width="500" bgColor="aliceblue" border="1"> <TR> <TD>Authenticated</TD> <TD><SPAN  runat="server"></SPAN></TD> </TR> <TR> <TD>User name</TD> <TD><SPAN  runat="server"></SPAN></TD> </TR> <TR> <TD>Authentication type</TD> <TD><SPAN  runat="server"></SPAN></TD> </TR> <TR> <TD>Code running as user</TD> <TD><SPAN  runat="server"></SPAN></TD> </TR></TABLE> <P> <asp:Button  runat="server" Text="Sign Out"></asp:Button> </P>

  3. Add the following code to the Web form s Page_Load event procedure to display user information:

    Visual Basic .NET

    Private Sub Page_Load(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles MyBase.Load ' Display user authentication information. spnAuthenticated.InnerText = User.Identity.IsAuthenticated() spnUserName.InnerText = User.Identity.Name() spnAuthenticationType.InnerText = User.Identity.AuthenticationType() spnImpUser.InnerText = _ System.Security.Principal.WindowsIdentity.GetCurrent().Name End Sub

    Visual C#

    private void Page_Load(object sender, System.EventArgs e) { // Display user authentication information. spnAuthenticated.InnerText = User.Identity.IsAuthenticated.ToString(); spnUserName.InnerText = User.Identity.Name; spnAuthenticationType.InnerText = User.Identity.AuthenticationType; spnImpUser.InnerText = System.Security.Principal.WindowsIdentity.GetCurrent().Name; }

  4. Add the following code to the butSignOut_Click event procedure to sign the user out of the application using the SignOut method. This removes the authentication cookie that was stored on the user s computer and requires that the user sign in again to access the Web application.

    Visual Basic .NET

    Private Sub butSignOut_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles butSignOut.Click ' Remove authentication cookie. FormsAuthentication.SignOut() ' Redirect back to this page (displays log in screen). Response.Redirect("UserInfo.aspx") End Sub

    Visual C#

    private void butSignOut_Click(object sender, System.EventArgs e) { // Remove authentication cookie. FormsAuthentication.SignOut(); // Redirect back to this page (displays log in screen). Response.Redirect("UserInfo.aspx"); }

  5. Add an HTML page to the application named Denied.htm. This is the page that the LogIn Web form displays if the user doesn t enter a correct user name and password after three tries. Denied.htm includes a message to the user, as shown in the following HTML:

    <h2>Access Denied</h2> <p>You must enter a valid user name and password to use this application. </p>

Exercise 4: Advanced Topics

The preceding exercises show how to implement Forms authentication in a step-by-step fashion. To gain a thorough understanding of other types of authentication, you can experiment by changing the authentication mode in the preceding application s Web.config file.

  • To switch the application to Windows authentication, comment out the current <authentication> element in Web.config and add the element shown here:

    <authentication mode="Windows" />

  • To switch the application to Passport authentication, install the Passport SDK and modify the <authentication> element in Web.config, as shown here:

    <authentication mode="Passport" />

Finally, for extra credit, get a server certificate from a certificate authority, such as VeriSign, and implement secure communications for the application. Use HTTPS to activate secure communications, as shown in Lesson 5.



MCAD(s)MCSD Self-Paced Training Kit(c) Developing Web Applications With Microsoft Visual Basic. Net and Microsoft V[.  .. ]0-315
MCAD(s)MCSD Self-Paced Training Kit(c) Developing Web Applications With Microsoft Visual Basic. Net and Microsoft V[. .. ]0-315
ISBN: N/A
EAN: N/A
Year: 2003
Pages: 118

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net