Recent Changes
Wednesday, June 23
-
SSE698Project3
edited
... Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
... project has growth gr…
(view changes)...Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
...project hasgrowthgrown substanially since
{image31.jpg}
Even the looks of many of the screens changed. Things as simple as the login screen now have customized look.
{image35.jpg}
...of thatsaidsaid, I picked...paper. Theareaareas covered include Styles, Masterpages, UserControls,Cookies,Cookies and AJAX.
Styles
In project 2 I did not do much with styles. As the project progress styles have started to have a larger part of the project. Currently, there is now several places styles are intergrated into the project. The first is the manual upload page, which was talked about in project 2. The new places include the masterpages. Since the styles are so intergrated with the masterpages I will cover them there.
Masterpages
...have only been working with
What is a masterpage? My definition of a masterpage is a template which defines the content areas and layout of the pages it is applied. In this project, thus far, I have created two masterpages. The first masterpage is for administrator and faculty pages. This masterpage will setup the feel and layout of the administrator and faculty pages. It contains the header, the footer, side menu, and main content area.
Once the four content areas are defined, the next step is to layout each of the areas with styles sheet. In this project the administator sheets will be called adminStyles.css.
...text-align: center;
padding: 5px;
}As you can
As...the styles sheet control the
The next setp is the asp portion of the masterpage:
<%@ Master Language="C#" AutoEventWireup="true" CodeFile="AdminMasterPage.master.cs" Inherits="AdminMasterPage" %>
...protected void Page_Load(object sender, EventArgs e)
{
Next, in the page load since thisThis is going...be asecureroll specfic page, so in the pageandload I do...the user to be able to use the backbutton, espceially after loggout we willbutton. To stop the page fromcaching. This will causecaching thepage to reload on the back button. When the page reloads iscode below was added. If the user's session cookie...of dateisthe page willpushsend the user
Response.Expires = 0;
Response.Cache.SetNoStore();
Response.AppendHeader("Pragma", "no-cache");
...the userhavehas the correct
if(Request.Cookies["PermLevel"] != null)
{
I had the System.Diagnostics referenced and using the writing to the immediate window to verify the proper permission level was being pulled from the cookie.
Debug.Write(Server.HtmlEncode(Request.Cookies["PermLevel"].Value));
...if statement.IIt probably needs to bechangechanged to remove
if (Server.HtmlEncode(Request.Cookies["PermLevel"].Value).ToString() != "3")
{
...}
}
...I wantedto dateto display the date oneverevery page, I
DateDisplay.Text = DateTime.Now.ToString("dddd, MMMM dd");
Now to building the side menus. In the administrator page even though I have two different users with permissions to view the page I needed different side menus based on permissions (ex. a faculty member should not be able to create a user, but an administrator should.)
...Now the masterpage is complete it is time to visit the actual asp. The original goal was to place a form on each page. The problem with this is there would have been so many pages it might have been more difficult to manage them. So after a little research the user of usercontrols came into play.
Usercontrols
...of thepage wherepages were very similar
To start 10 usercontrols were created. We will look at the editStudent.
<%@ Control Language="C#" AutoEventWireup="true" CodeFile="editStudent.ascx.cs" Inherits="controls_editStudent" %>
...}
}
...look ateditUser.aspxeditUser.aspx. The first
<%@ Page Title="" Language="C#" MasterPageFile="~/resources/masterpages/AdminMasterPage.master" AutoEventWireup="true" CodeFile="edituser.aspx.cs" Inherits="admin_editstudent" %>
On the editUser we are going to register 3 user controls. The correct one will show based on the users selection.
...<p> </p>
<p> </p>
...all theuserusers with the
Here is the DropDownList 1
<asp:DropDownList ID="DropDownUserType" runat="server" Width="170px"
5:48 pm -
SSE698Project3
edited
SSE
SSE 698: Web
Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
(view changes)SSE
SSE 698: Web
Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
5:18 pm -
SSE698Project3
edited
SSE SSE 698: Web
Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
(view changes)SSE 698: Web
SSE
Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
5:17 pm
Tuesday, June 22
-
7:54 pm
-
SSE698Project3
edited
... Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
... project 2. As As yo…
(view changes)...Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
...project 2.AsAs you can
{image31.jpg}
...screens changed.ThingsThings as simple
{image35.jpg}
...UserControls, Cookies,
Styles
...with styles.AsAs the project...the project.Currently,Currently, there is nowseveralseveral places styles...the project.TheThe first is...project 2.TheThe new places...the masterpages.SinceSince the styles...them there.
Masterpages
...to me.II happened to...something else.ThoughThough I have...this project.
What
What is a masterpage?MyMy definition of...is applied.InIn this project,...two masterpages.TheThe first masterpage...faculty pages.ThisThis masterpage will...faculty pages.ItIt contains the...styles sheet.InIn this project
body {
font-family: Verdana;
...}
#leftContent {
width: 85px;
padding: 10px;
font-size: 90%;
...padding: 5px;
}
...the masterpage.TheThe masterpage layout...by www.asp.net.
The next setp is the asp portion of the masterpage:
<%@ Master Language="C#" AutoEventWireup="true" CodeFile="AdminMasterPage.master.cs" Inherits="AdminMasterPage" %>
...<asp:Label ID="DateDisplay" runat="server"></asp:Label>
</p>
<h3>Task</h3>
<asp:Repeater ID="side_menu" runat="server">
<ItemTemplate>
<li>
...a database.ThisThis will make...menu items.InIn the long...menu items.ThisThis means we...the link.TheThe asp repeater...id= "HyperLink2"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
NavigateUrl= '<%#"~/admin/" + DataBinder.Eval(Container.DataItem, "url") + "?TaskID=" + DataBinder.Eval(Container.DataItem,"menu_category_ID")%>'>
<%#DataBinder.Eval(Container.DataItem, "menu_name")%>
...</ItemTemplate>
</asp:Repeater>
...secondary menu.ItIt has two...the database.InIn the database
<h3>Misc.</h3>
<li>
...id= "HyperLink1"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
NavigateUrl="~/admin/ebbmain.aspx">
Home
...<ItemTemplate>
<li>
...id= "HyperLink2"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
NavigateUrl='<%#"~/admin/" + DataBinder.Eval(Container.DataItem, "url") + "?TaskID=" + DataBinder.Eval(Container.DataItem,"menu_category_ID")%>'>
<%#DataBinder.Eval(Container.DataItem, "menu_name")%>
...</li>
<li>
...id= "HyperLink3"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
NavigateUrl="~/logout.aspx">
Logout
...</asp:Repeater>
</div>
...footer content.
<div id="footerContent">
<img src="~/resources/images/footer.gif" alt="Powered by ASP.NET!" />
...</body>
</html>
...the masterpage.ThereThere are several here.
using System;
using System.Collections.Generic;
...public partial class AdminMasterPage : System.Web.UI.MasterPage
{
...data connectors.ContinuedContinued from project
dataControl myDataControl;
protected void Page_Load(object sender, EventArgs e)
{
...from caching.ThisThis will cause...back button.WhenWhen the page...login page.TheThe session cookie
Response.Expires = 0;
Response.Cache.SetNoStore();
Response.AppendHeader("Pragma", "no-cache");
...the page.TheThe permission level...the cookie.EachEach time the...page load.IfIf the permission...login page.
if(Request.Cookies["PermLevel"] != null)
{
I had the System.Diagnostics referenced and using the writing to the immediate window to verify the proper permission level was being pulled from the cookie.
Debug.Write(Server.HtmlEncode(Request.Cookies["PermLevel"].Value));
...if statement.II probably needs...nested if.II could use...> 1.However,However, I am
if (Server.HtmlEncode(Request.Cookies["PermLevel"].Value).ToString() != "3")
{
...Since I wanted to date to display on ever page, I can easily place it in the masterpage.
DateDisplay.Text = DateTime.Now.ToString("dddd, MMMM dd");
...side menus.InIn the administrator
DATA
myDataControl = new dataControl();
Open a data connection
myDataControl.Open_Data_Con();
...SQL query.IfIf it is
if (Server.HtmlEncode(Request.Cookies["PermLevel"].Value).ToString() == "3")
{
...Now we have completed the current masterpage.
{image32.jpg}
...student masterpage.TheThe student masterpage...actual asp.TheThe original goal...each page.TheThe problem with...manage them.SoSo after a
Usercontrols
...the user.InsteadInstead of hiding...may display.ThenThen I would...the page.ThisThis did several...to create.ItIt made editing\modifing...much easier.ItIt provides for...were created.WeWe will look
<%@ Control Language="C#" AutoEventWireup="true" CodeFile="editStudent.ascx.cs" Inherits="controls_editStudent" %>
The user control simple contains a base form:
...
<asp:Label ID="Label6" runat="server" Text="Verify Password"></asp:Label>
...runat="server" TabIndex="5"
TextMode="Password"></asp:TextBox>
<br />
<br />
<br />
...Changes" Height="40px"
Width="94px" onclick="Button1_Click" TabIndex="6" />
{image34.jpg}
...on_click event.ThereThere still needs...the database.TheThe validation also
using System;
using System.Collections.Generic;
...protected void Button1_Click(object sender, EventArgs e)
{
...data class.
myDataControl = new dataControl();
myDataControl.Open_Data_Con();
...myDataControl.WriteData("UPDATE students SET first_name = '" + firstname.Text + "', last_name = '" + lastname.Text + "', email = '" + email.Text + "' Where user_id = " + userid.Text);
myDataControl.WriteData("UPDATE users SET username = '" + username.Text + "', password = '" + password.Text + "' Where user_id = " + userid.Text);
myDataControl.Close_Connection();
}
}
...the usercontrol.WeWe will look at editUser.aspxTheThe first thing
<%@ Page Title="" Language="C#" MasterPageFile="~/resources/masterpages/AdminMasterPage.master" AutoEventWireup="true" CodeFile="edituser.aspx.cs" Inherits="admin_editstudent" %>
...user controls.TheThe correct one
<%@ Register TagPrefix="EBBControl" Tagname="editStudent" Src="~/controls/editStudent.ascx" %>
<%@ Register TagPrefix="EBBControl" Tagname="editFaculty" Src="~/controls/editFaculty.ascx" %>
...<p> </p>
<p> </p>
...two DropDownList.TheThe first one...user type.AfterAfter selecting the...selected type.NextNext the user
Here is the DropDownList 1
...runat="server" Width="170px"
onselectedindexchanged="DropDownUserType_SelectedIndexChanged" AutoPostBack="true" >
</asp:DropDownList>
...{image36.jpg}
Here is the DropDownList 2
...runat="server" Width="170px"
onselectedindexchanged="DropDownUsers_SelectedIndexChanged" AutoPostBack="true" >
</asp:DropDownList>
...<br />
{image37.jpg}
...user controls.NoticeNotice they are...= false.
<EBBControl:editStudent ID="editStudent" Runat="server" Visible="false" > </EBBControl:editStudent>
<EBBControl:editFaculty ID="editFaculty" Runat="server" Visible="false" > </EBBControl:editFaculty>
...password.Attributes["value"] = (string)myReader["password"];
verifypassword.Attributes["value"] = (string)myReader["password"];
}
myDataControl.Close_Connection();
}
}
Cookies
...the cookie.ThisThis code resides...the EBBLogon.aspx.cs.OnceOnce a user...project 2.However,However, the change...the cookie.
FormsAuthenticationTicket ticket = new FormsAuthenticationTicket(1, username, DateTime.Now
, DateTime.Now.AddMinutes(30), isPersistent, userData, FormsAuthentication.FormsCookiePath);
...Response.Cookies["PermLevel"].Value = permLevel.ToString();
Response.Cookies.Add(new HttpCookie(FormsAuthentication.FormsCookieName, encTicket));
...correct page.AsAs noted above
switch (permLevel)
{
...}
Exceptions to forms authentication:
...forms authentication.ByBy defaults forms...before access.InIn this project...not needed.Additionally,Additionally, there have...and styles.ThisThis brought a...upload page.ThisThis page the...not needed.ToTo make an
<location path="EBBAUpload.aspx">
<system.web>
<authorization>
...all users.
<allow users="*"/>
</authorization>
</system.web>
</location>
...next item.AuthenticationAuthentication rules are...in order.SoSo the deny...the exceptions.
<location path="EBBMUpload.aspx">
<system.web>
...</location>
AJAX
...collapsable panels.II wanted to...user profile.AfterAfter researching this...most functional.TheThe user will...the panel.
Using
Using AJAX within...nor seen.ThisThis is an...at http://www.asp.net/ajaxlibrary/act_CollapsiblePanel.ashx.II used the...this project.
All
All of the...the asp.ThisThis is after...the project.TheThe tool kit...folder Bin.InIn this project...asp code.TheThe code is...collapsible panel.InIn this case...the editUser.aspx.TheThe edit user...total panels.AA collapsible panel...two panels.TheThe first panel...collapsible panel.TheThe second panel
<%@ Page
Language="C#"
...</asp:Content>
<asp:Content ID="Content2" ContentPlaceHolderID="MainContent" Runat="Server">
...the ajax.TheThe first line
<ajaxToolkit:ToolkitScriptManager runat="Server" ID="ScriptManager1" />
In the title panel is called panel2 here.
...CssClass="collapsePanelHeader" Height="30px">
<div style="padding:5px; cursor: pointer; vertical-align: middle;">
Give the title panel a caption.
...</div>
</asp:Panel>
...content panel.ItIt will contain
<asp:Panel ID="Panel1" runat="server" CssClass="collapsePanel" Height="0">
<br />
...<p> </p>
<p> </p>
...runat="server" Width="170px"
onselectedindexchanged="DropDownUserType_SelectedIndexChanged" AutoPostBack="true" >
</asp:DropDownList>
<p>
...runat="server" Width="170px"
onselectedindexchanged="DropDownUsers_SelectedIndexChanged" AutoPostBack="true" >
</asp:DropDownList>
...TargetControlID="Panel1"
ExpandControlID="Panel2"
CollapseControlID="Panel2"
Collapsed="True"
TextLabelID="Label1"
ImageControlID="Image1"
ExpandedText="(Hide Details...)"
CollapsedText="(Show Details...)"
7:53 pm -
SSE698Project3
edited
... Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
This project has growth subs…
(view changes)...Project 3 (Summer 2010) - Course Syllabus
by Chris A. Bombardo
This project has growth substanially since project 2. As you can see from the screen shot a lot of pages have been added.
{image31.jpg}
Even the looks of many of the screens changed. Things as simple as the login screen now have customized look.
{image35.jpg}
With all of that said I picked several areas to concentrate on for the paper. The area include Styles, Masterpages, UserControls, Cookies,
Styles
In project 2 I did not do much with styles. As the project progress styles have started to have a larger part of the project. Currently, there is now several places styles are intergrated into the project. The first is the manual upload page, which was talked about in project 2. The new places include the masterpages. Since the styles are so intergrated with the masterpages I will cover them there.
Masterpages
Masterpages was something completely new to me. I happened to come across them while researching something else. Though I have only working with them for a week or so, masterpages is the best thing I have learned working on this project.
What is a masterpage? My definition of a masterpage is a template which defines the content areas and layout of the pages it is applied. In this project, thus far, I have created two masterpages. The first masterpage is for administrator and faculty pages. This masterpage will setup the feel and layout of the administrator and faculty pages. It contains the header, the footer, side menu, and main content area.
Once the four content areas are defined, the next step is to layout each of the areas with styles sheet. In this project the administator sheets will be called adminStyles.css.
body {
font-family: Verdana;
font-size: medium;
margin: 0px;
}
h1, h2 {
margin: 0px;
}
#topContent {
text-align: right;
background-color: #00008B;
color: White;
font-size: x-large;
text-decoration: none;
font-weight: bold;
padding: 10px;
height: 50px;
}
#topContent a {
text-decoration: none;
color: White;
}
#leftContent {
width: 85px;
padding: 10px;
font-size: 90%;
text-align: left;
position: absolute;
top: 60px;
margin-top: 10px;
left: 0px;
}
#leftContent h3 {
text-transform: uppercase;
letter-spacing: 2px;
text-align: center;
border-top: dotted 1px #660;
border-bottom: dotted 1px #660;
}
#mainContent {
text-align: left;
margin-left: 120px;
padding: 10px;
}
#footerContent {
text-align: center;
padding: 5px;
}
As you can see in the styles control the font, margins, alignment, padding, borders, location and so forth of each section in the masterpage. The masterpage layout used in this project is based on the tutorial provied by www.asp.net.
The next setp is the asp portion of the masterpage:
<%@ Master Language="C#" AutoEventWireup="true" CodeFile="AdminMasterPage.master.cs" Inherits="AdminMasterPage" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
<title>Electronic Bluebook Exam System Administrator</title>
<asp:ContentPlaceHolder id="head" runat="server">
</asp:ContentPlaceHolder>
We need to apply the styles to the page:
<link href="~/resources/styles/adminStyles.css" rel="stylesheet" type="text/css" />
</head>
<body>
Next we will layout the form on the masterpage:
<form id="form1" runat="server">
Top Content:
<div id="topContent">
<a href="/admin/ebbmain.aspx">Electronic Bluebook<br />
<font size="1" face="Verdana">by CompuTest, LLC</font></a>
</div>
Main Content:
<div id="mainContent">
<asp:ContentPlaceHolder id="MainContent" runat="server">
</asp:ContentPlaceHolder>
</div>
Left Menu:
<div id="leftContent">
<p style="text-align: center;">
<asp:Label ID="DateDisplay" runat="server"></asp:Label>
</p>
<h3>Task</h3>
<asp:Repeater ID="side_menu" runat="server">
<ItemTemplate>
<li>
In this project the menu items are going to be stored in a database. This will make it easier to add and remove menu items. In the long run it will also make it possible for the user to customize the menu items. This means we need to create a asp.Repeater, create a hyperlink, and bind the data to the link. The asp repeater will do this for each of the items returned in the SQLDataReader, which will be touched on later.
<asp:HyperLink id= "HyperLink2"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
NavigateUrl= '<%#"~/admin/" + DataBinder.Eval(Container.DataItem, "url") + "?TaskID=" + DataBinder.Eval(Container.DataItem,"menu_category_ID")%>'>
<%#DataBinder.Eval(Container.DataItem, "menu_name")%>
</asp:HyperLink>
</li>
</ItemTemplate>
</asp:Repeater>
Next we put in secondary menu. It has two static links to home and logout, plus an additional data repeater to pull links from the database. In the database the links are given and menu_id to identify which menu each links should be placed.
<h3>Misc.</h3>
<li>
<asp:HyperLink id= "HyperLink1"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
NavigateUrl="~/admin/ebbmain.aspx">
Home
</asp:HyperLink>
</li>
<asp:Repeater ID="side_menu2" runat="server">
<ItemTemplate>
<li>
<asp:HyperLink id= "HyperLink2"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
NavigateUrl='<%#"~/admin/" + DataBinder.Eval(Container.DataItem, "url") + "?TaskID=" + DataBinder.Eval(Container.DataItem,"menu_category_ID")%>'>
<%#DataBinder.Eval(Container.DataItem, "menu_name")%>
</asp:HyperLink>
</li>
<li>
<asp:HyperLink id= "HyperLink3"
runat="server"
Font-Size="Smaller"
ForeColor="#0000CC"
Font-Names="verdana"
NavigateUrl="~/logout.aspx">
Logout
</asp:HyperLink>
</li>
</ItemTemplate>
</asp:Repeater>
</div>
Finally, we come to the footer content.
<div id="footerContent">
<img src="~/resources/images/footer.gif" alt="Powered by ASP.NET!" />
</div>
</form>
</body>
</html>
Once the asp is complete the final stop is to complete any C# code behind the masterpage. There are several here.
using System;
using System.Collections.Generic;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Diagnostics;
public partial class AdminMasterPage : System.Web.UI.MasterPage
{
First we need to create a data connectors. Continued from project two we can tie into the dataControl class.
dataControl myDataControl;
protected void Page_Load(object sender, EventArgs e)
{
Next, in the page load since this is going to be a secure page and I do not want the user to use the back button, espceially after loggout we will stop the page from caching. This will cause the page to reload on the back button. When the page reloads is the session cookie (covered later) is out of date is will push the user back to the login page. The session cookie may be out-dated if the user logged out or if the session was left open too long without activity.
Response.Expires = 0;
Response.Cache.SetNoStore();
Response.AppendHeader("Pragma", "no-cache");
Next, on the page load we are going to verify the user have the correct permission level to view the page. The permission level is pulled from the database when the user logs in and then stored encrypted in the cookie. Each time the user visits a protected page it is first check with forms authentication then check the permission level on the page load. If the permission level is null or underrated currently the user is pushed back to the login page.
if(Request.Cookies["PermLevel"] != null)
{
I had the System.Diagnostics referenced and using the writing to the immediate window to verify the proper permission level was being pulled from the cookie.
Debug.Write(Server.HtmlEncode(Request.Cookies["PermLevel"].Value));
Currenty I am checking 2 permission levels at this page with a nested if statement. I probably needs to be change to remove the nested if. I could use a > 1. However, I am still developing the different permission level possibilites.
if (Server.HtmlEncode(Request.Cookies["PermLevel"].Value).ToString() != "3")
{
if (Server.HtmlEncode(Request.Cookies["PermLevel"].Value).ToString() != "2")
{
Response.Redirect("~/EBBLogon.aspx", true);
}
}
}
Since I wanted to date to display on ever page, I can easily place it in the masterpage.
DateDisplay.Text = DateTime.Now.ToString("dddd, MMMM dd");
Now to building the side menus. In the administrator page even though I have two different users with permissions to view the page I needed different side menus based on permissions (ex. a faculty member should not be able to create a user, but an administrator should.)
DATA
myDataControl = new dataControl();
Open a data connection
myDataControl.Open_Data_Con();
If the permission level is set to administrator run the selected SQL query. If it is anything other than three we have a different SQL statement.
if (Server.HtmlEncode(Request.Cookies["PermLevel"].Value).ToString() == "3")
{
side_menu.DataSource = myDataControl.ReadDataSet("Select menu_category_id, menu_name, url from side_menu where (permissionLevel = 1) OR permissionLevel = 2");
}
else
{
side_menu.DataSource = myDataControl.ReadDataSet("Select menu_category_id, menu_name, url from side_menu where permissionLevel = 2");
}
Bind the data to the datarepeater (side_menu).
side_menu.DataBind();
myDataControl.Close_Connection();
Get the second side menu and bind the data.
myDataControl.Open_Data_Con();
side_menu2.DataSource = myDataControl.ReadDataSet("Select menu_category_id, menu_name, url from side_menu where permissionLevel = 3");
side_menu2.DataBind();
myDataControl.Close_Connection();
}
}
Now we have completed the current masterpage.
{image32.jpg}
Similar to the administrator masterpage I created a student masterpage. The student masterpage is nearly identical to the administrator at the time, with the exception of different menu identifies.
Now the masterpage is complete it is time to visit the actual asp. The original goal was to place a form on each page. The problem with this is there would have been so many pages it might have been more difficult to manage them. So after a little research the user of usercontrols came into play.
Usercontrols
Many of the page where very similar with only slight changes in the input form displayed to the user. Instead of hiding and showing individual components I created a usercontrol for each of the forms a page may display. Then I would display the proper usercontrol in the main contain of the page. This did several things, first is limited the number of pages I needed to create. It made editing\modifing the project much easier. It provides for a more organized and readable project.
To start 10 usercontrols were created. We will look at the editStudent.
<%@ Control Language="C#" AutoEventWireup="true" CodeFile="editStudent.ascx.cs" Inherits="controls_editStudent" %>
The user control simple contains a base form:
Edit Student:
<asp:TextBox ID="userid" runat="server" Visible="False" Width="25px"></asp:TextBox>
<br />
<br />
<asp:Label ID="Label1" runat="server" Text="First Name:"></asp:Label>
<asp:TextBox ID="firstname" runat="server"></asp:TextBox>
<asp:Label ID="Label2" runat="server" Text="Last Name:"></asp:Label>
<asp:TextBox ID="lastname" runat="server" TabIndex="1"></asp:TextBox>
<br />
<br />
<br />
<asp:Label ID="Label3" runat="server" Text="Email:"></asp:Label>
<asp:TextBox ID="email" runat="server" TabIndex="2"></asp:TextBox>
<asp:Label ID="Label4" runat="server" Text="Username:"></asp:Label>
<asp:TextBox ID="username" runat="server" TabIndex="3"></asp:TextBox>
<br />
<br />
<asp:Label ID="Label5" runat="server" Text="Password"></asp:Label>
<asp:TextBox ID="password" runat="server" TabIndex="4" TextMode="Password"></asp:TextBox>
<asp:Label ID="Label6" runat="server" Text="Verify Password"></asp:Label>
<asp:TextBox ID="verifypassword" runat="server" TabIndex="5"
TextMode="Password"></asp:TextBox>
<br />
<br />
<br />
<asp:Button ID="Button1" runat="server" Text="Save Changes" Height="40px"
Width="94px" onclick="Button1_Click" TabIndex="6" />
{image34.jpg}
The C# sharp code behind the user control writes the data to the database on the on_click event. There still needs to be a text validation written to verify no junk data is trying to be wrote to the database. The validation also needs to make sure someone is not trying to SQL inject, even within the administrator login.
using System;
using System.Collections.Generic;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Data.SqlClient;
public partial class controls_editStudent : System.Web.UI.UserControl
{
dataControl myDataControl;
protected void Page_Load(object sender, EventArgs e)
{
}
protected void Button1_Click(object sender, EventArgs e)
{
Grab the data class.
myDataControl = new dataControl();
myDataControl.Open_Data_Con();
Write the data to the database.
myDataControl.WriteData("UPDATE students SET first_name = '" + firstname.Text + "', last_name = '" + lastname.Text + "', email = '" + email.Text + "' Where user_id = " + userid.Text);
myDataControl.WriteData("UPDATE users SET username = '" + username.Text + "', password = '" + password.Text + "' Where user_id = " + userid.Text);
myDataControl.Close_Connection();
}
}
Now to use the usercontrol. We will look at editUser.aspx The first thing is to register the userControl.
<%@ Page Title="" Language="C#" MasterPageFile="~/resources/masterpages/AdminMasterPage.master" AutoEventWireup="true" CodeFile="edituser.aspx.cs" Inherits="admin_editstudent" %>
On the editUser we are going to register 3 user controls. The correct one will show based on the users selection.
<%@ Register TagPrefix="EBBControl" Tagname="editStudent" Src="~/controls/editStudent.ascx" %>
<%@ Register TagPrefix="EBBControl" Tagname="editFaculty" Src="~/controls/editFaculty.ascx" %>
<%@ Register TagPrefix="EBBControl" Tagname="editAdministrator" Src="~/controls/editAdministrator.ascx" %>
Next, to load the header of the masterpage.
<asp:Content ID="Content1" ContentPlaceHolderID="head" Runat="Server">
</asp:Content>
After the header is the MainContent, which will contain our data.
<asp:Content ID="Content2" ContentPlaceHolderID="MainContent" Runat="Server">
<h2>Edit User:</h2>
<p> </p>
<p> </p>
We will add two DropDownList. The first one the user will select the user type. After selecting the user type the code will load the second DropDownList with all the user with the selected type. Next the user will be selected and the user control will be displayed.
Here is the DropDownList 1
<asp:DropDownList ID="DropDownUserType" runat="server" Width="170px"
onselectedindexchanged="DropDownUserType_SelectedIndexChanged" AutoPostBack="true" >
</asp:DropDownList>
<p>
{image36.jpg}
Here is the DropDownList 2
<asp:DropDownList ID="DropDownUsers" runat="server" Width="170px"
onselectedindexchanged="DropDownUsers_SelectedIndexChanged" AutoPostBack="true" >
</asp:DropDownList>
</p>
<br />
<br />
<br />
{image37.jpg}
Loading of the user controls. Notice they are all marked as visiable = false.
<EBBControl:editStudent ID="editStudent" Runat="server" Visible="false" > </EBBControl:editStudent>
<EBBControl:editFaculty ID="editFaculty" Runat="server" Visible="false" > </EBBControl:editFaculty>
<EBBControl:editAdministrator ID="editAdministrator" Runat="server" Visible="false" > </EBBControl:editAdministrator>
</asp:Content>
{image33.jpg}
Now the C# code in the editUser.aspx
using System;
using System.Collections.Generic;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Data.SqlClient;
public partial class admin_editstudent : System.Web.UI.Page
{
dataControl myDataControl;
int userType = 0;
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
First, we will load all of our user types into the first dropdownlist on page load.
myDataControl = new dataControl();
SqlDataReader myReader;
myDataControl.Open_Data_Con();
myReader = myDataControl.ReadDataSet("Select * from user_types ORDER BY userType");
this.DropDownUserType.DataSource = myReader;
this.DropDownUserType.DataTextField = "userName";
this.DropDownUserType.DataValueField = "userType";
this.DropDownUserType.DataBind();
this.DropDownUserType.SelectedValue = "0";
}
}
When the user makes a change in dropdownlist1 dropdownlist2 is updated with all the users based dropdownlist1 user type selected.
protected void DropDownUserType_SelectedIndexChanged(object sender, EventArgs e)
{
myDataControl = new dataControl();
SqlDataReader myReader;
myDataControl.Open_Data_Con();
myReader = myDataControl.ReadDataSet("Select * from users where accountType = " + Convert.ToInt32(this.DropDownUserType.SelectedValue));
this.DropDownUsers.DataSource = myReader;
this.DropDownUsers.DataTextField = "username";
this.DropDownUsers.DataValueField = "user_id";
this.DropDownUsers.DataBind();
this.DropDownUsers.Items.Insert(0, new ListItem(String.Empty, String.Empty));
this.DropDownUsers.SelectedIndex = 0;
}
Next, when the user selects a user the proper user control is displayed and the data is populated.
protected void DropDownUsers_SelectedIndexChanged(object sender, EventArgs e)
{
userType = Convert.ToInt32(this.DropDownUserType.SelectedValue);
switch (userType)
{
case 1: //Student
ShoweditStudent();
HideeditFaculty();
HideeditAdministrator();
populateEditForm(editStudent);
break;
case 2: //Faculty
HideeditStudent();
ShoweditFaculty();
HideeditAdministrator();
populateEditForm(editFaculty);
break;
case 3: //Administrator
HideeditStudent();
HideeditFaculty();
ShoweditAdministrator();
populateEditForm(editAdministrator);
break;
default: //None
HideeditStudent();
HideeditFaculty();
HideeditAdministrator();
break;
}
}
Showing the usercontrols.
void ShoweditStudent()
{
if (editStudent.Visible == false)
editStudent.Visible = true;
}
void ShoweditFaculty()
{
if (editFaculty.Visible == false)
editFaculty.Visible = true;
}
void ShoweditAdministrator()
{
if (editAdministrator.Visible == false)
editAdministrator.Visible = true;
}
Hiding the non-used usercontrols.
void HideeditStudent()
{
if (editStudent.Visible == true)
editStudent.Visible = false;
}
void HideeditFaculty()
{
if (editFaculty.Visible == true)
editFaculty.Visible = false;
}
void HideeditAdministrator()
{
if (editAdministrator.Visible == true)
editAdministrator.Visible = false;
}
Populate the usercontrols form fields.
void populateEditForm(UserControl userControl)
{
myDataControl = new dataControl();
SqlDataReader myReader = null;
myDataControl.Open_Data_Con();
if (userType == 1)
myReader = myDataControl.ReadDataSet("SELECT students.first_name, students.last_name, students.email, users.username, users.password, users.lastlogin FROM students INNER JOIN users ON students.user_id = users.user_id WHERE(users.user_id = " + Convert.ToInt32(this.DropDownUsers.SelectedValue) + ")" );
if (userType == 2)
myReader = myDataControl.ReadDataSet("SELECT faculty.first_name, faculty.last_name, faculty.email, users.username, users.password, users.lastlogin FROM faculty INNER JOIN users ON faculty.user_id = users.user_id WHERE(users.user_id = " + Convert.ToInt32(this.DropDownUsers.SelectedValue) + ")" );
if (userType == 3)
myReader = myDataControl.ReadDataSet("SELECT administrator.first_name, administrator.last_name, administrator.email, users.username, users.password, users.lastlogin FROM administrator INNER JOIN users ON administrator.user_id = users.user_id WHERE(users.user_id = " + Convert.ToInt32(this.DropDownUsers.SelectedValue) + ")");
TextBox firstname = (TextBox)userControl.FindControl("firstname");
TextBox lastname = (TextBox)userControl.FindControl("lastname");
TextBox email = (TextBox)userControl.FindControl("email");
TextBox username = (TextBox)userControl.FindControl("username");
TextBox password = (TextBox)userControl.FindControl("password");
TextBox verifypassword = (TextBox)userControl.FindControl("verifypassword");
TextBox userid = (TextBox)userControl.FindControl("userid");
userid.Text = this.DropDownUsers.SelectedValue.ToString();
while (myReader.Read())
{
firstname.Text = (string)myReader["first_name"];
lastname.Text = (string)myReader["last_name"];
email.Text = (string)myReader["email"];
username.Text = (string)myReader["username"];
password.Attributes["value"] = (string)myReader["password"];
verifypassword.Attributes["value"] = (string)myReader["password"];
}
myDataControl.Close_Connection();
}
}
Cookies
Since cookies have been talked about several times above, I wanted to briefly touch on the writing of the cookie. This code resides on the EBBLogon.aspx.cs. Once a user is authenticated the a cookie is created, as covered in project 2. However, the change here is the permission level is stored in the cookie.
FormsAuthenticationTicket ticket = new FormsAuthenticationTicket(1, username, DateTime.Now
, DateTime.Now.AddMinutes(30), isPersistent, userData, FormsAuthentication.FormsCookiePath);
// Encrypt the ticket.
string encTicket = FormsAuthentication.Encrypt(ticket);
First, we need to get the permission level from the database, which we can grab from the accountType table based on the username – note: it may be more stable to pull the data with the user_id key.
int permLevel = 0;
SqlDataReader myDataSet;
mydataControl.Open_Data_Con();
myDataSet = mydataControl.ReadDataSet("Select accountType from users where username='" + username + "'");
while (myDataSet.Read())
{
permLevel = Convert.ToInt32(myDataSet[0]);
}
Once the data is a in a variable we can write it to the cookie.
// Create the cookie.
Response.Cookies["PermLevel"].Value = permLevel.ToString();
Response.Cookies.Add(new HttpCookie(FormsAuthentication.FormsCookieName, encTicket));
Next, to send the user to the correct page. As noted above the page the user goes to will re-evaulate the permission level to verify the user has permission to load the page.
switch (permLevel)
{
case 1: //Student
Response.Redirect("student//ebbmain.aspx");
break;
case 2: //Faculty
Response.Redirect("admin//ebbmain.aspx");
break;
case 3: //Admin
Response.Redirect("admin//ebbmain.aspx");
break;
default: //Unknown
break;
}
Exceptions to forms authentication:
One of the changes additions to project two I wanted to point out was the addition of exceptions to the forms authentication. By defaults forms authentication requires every page to be authenticated before access. In this project there was several pages authentication was not needed. Additionally, there have been issues reported with forms authentication and styles. This brought a need to have exception to the forms authentication.
The first exception was the automatic upload page. This page the EBB application talks to and at this time authentication is not needed. To make an exception we will use the location tag in the web.Config file. The path can be the relative path the a file or folder.
<location path="EBBAUpload.aspx">
<system.web>
<authorization>
We will allow all users.
<allow users="*"/>
</authorization>
</system.web>
</location>
Then we will move on to the next item. Authentication rules are read in order. So the deny must be place prior to the the exceptions.
<location path="EBBMUpload.aspx">
<system.web>
<authorization>
<allow users="*"/>
</authorization>
</system.web>
</location>
<location path="resources/images">
<system.web>
<authorization>
<allow users="*"/>
</authorization>
</system.web>
</location>
<location path="resources/styles">
<system.web>
<authorization>
<allow users="*"/>
</authorization>
</system.web>
</location>
Masterpages are suppose to have an automatic exception, however, I figured if I placed it in the exceptions I would be able to keep track of all the exceptions.
<location path="resources/masterpages">
<system.web>
<authorization>
<allow users="*"/>
</authorization>
</system.web>
</location>
AJAX
The final portion of the program I am working on for the class is creating collapsable panels. I wanted to be able organize the main content of the page displayed to the user in several categories such as user profile, course tied to the user profile, and exams tied to the coures and user profile. After researching this for a while collapsalbe panels seemed to be the best looking and most functional. The user will be able to expand one the panel for the select users and see the information within the panel.
Using AJAX within asp was something I have never done nor seen. This is an ok example and and some information at http://www.asp.net/ajaxlibrary/act_CollapsiblePanel.ashx. I used the example to get a start, it is not completed yet, to adding collapsible panels to this project.
All of the code is controlled in the asp. This is after you add the Ajax Control Toolkit to the project. The tool kit must be added to the asp special folder Bin. In this project I added the .Net 3.5 version because it is what the project is based on.
Now to the asp code. The code is to be added to the aspx page needed to show the collapsible panel. In this case it is the editUser.aspx. The edit user will have three collapsible panels, which means 6 total panels. A collapsible panel is a combiniation of two panels. The first panel is the title panel, it contains the title and action buttom for the collapsible panel. The second panel is the actual panel which expands or collapsise based on the clicking of the action button.
<%@ Page
Language="C#"
MasterPageFile=" ~/resources/masterpages/AdminMasterPage.master "
AutoEventWireup="true"
Inherits="CommonPage"
Title="Electron Bluebook Exam System" %>
<%@ Register TagPrefix="EBBControl" Tagname="editStudent" Src="~/controls/editStudent.ascx" %>
<%@ Register TagPrefix="EBBControl" Tagname="editFaculty" Src="~/controls/editFaculty.ascx" %>
<%@ Register TagPrefix="EBBControl" Tagname="editAdministrator" Src="~/controls/editAdministrator.ascx" %>
Notice we are registering the Ajax control tool kit now.
<%@ Register
Assembly="AjaxControlToolkit"
Namespace="AjaxControlToolkit"
TagPrefix="ajaxToolkit" %>
<asp:Content ID="Content1" ContentPlaceHolderID="head" Runat="Server">
</asp:Content>
<asp:Content ID="Content2" ContentPlaceHolderID="MainContent" Runat="Server">
In side of the mainContent we start the ajax. The first line is setup the script.
<ajaxToolkit:ToolkitScriptManager runat="Server" ID="ScriptManager1" />
In the title panel is called panel2 here.
<asp:Panel ID="Panel2" runat="server" CssClass="collapsePanelHeader" Height="30px">
<div style="padding:5px; cursor: pointer; vertical-align: middle;">
Give the title panel a caption.
[[code format="asp"]]
<div style="float: left;">User Profile div>
<div style="float: left; margin-left: 20px;">
<asp:Label ID="Label1" runat="server">( Edit User Profile...)</asp:Label>
</div>
<div style="float: right; vertical-align: middle;">
The image controls the click.
<asp:ImageButton ID="Image1" runat="server" ImageUrl="~/images/expand_blue.jpg" AlternateText="(Edit User Profile...)"/>
</div>
</div>
</asp:Panel>
Panel1 is now our content panel. It will contain the usercontrols (forms) for editing the users in this case.
<asp:Panel ID="Panel1" runat="server" CssClass="collapsePanel" Height="0">
<br />
<p>
<h2>Edit User:</h2>
<p> </p>
<p> </p>
<asp:DropDownList ID="DropDownUserType" runat="server" Width="170px"
onselectedindexchanged="DropDownUserType_SelectedIndexChanged" AutoPostBack="true" >
</asp:DropDownList>
<p>
<asp:DropDownList ID="DropDownUsers" runat="server" Width="170px"
onselectedindexchanged="DropDownUsers_SelectedIndexChanged" AutoPostBack="true" >
</asp:DropDownList>
</p>
<br />
<br />
<br />
<EBBControl:editStudent ID="editStudent" Runat="server" Visible="false" > </EBBControl:editStudent>
<EBBControl:editFaculty ID="editFaculty" Runat="server" Visible="false" > </EBBControl:editFaculty>
<EBBControl:editAdministrator ID="editAdministrator" Runat="server" Visible="false" > </EBBControl:editAdministrator>
</p>
</asp:Panel>
</div>
Finally, we close the panel and set the options for expanding followed by collapising.
<ajaxToolkit:CollapsiblePanelExtender ID="userProfile_exp" runat="Server"
TargetControlID="Panel1"
ExpandControlID="Panel2"
CollapseControlID="Panel2"
Collapsed="True"
TextLabelID="Label1"
ImageControlID="Image1"
ExpandedText="(Hide Details...)"
CollapsedText="(Show Details...)"
ExpandedImage="~/images/collapse_blue.jpg"
CollapsedImage="~/images/expand_blue.jpg"
SuppressPostBack="true"
SkinID="CollapsiblePanelDemo" />
</asp:Content>
The program is not completed, but I have learned a great deal working through the program as a project.
7:51 pm -
image34.jpg
uploaded
7:30 pm -
image35.jpg
uploaded
7:30 pm -
image31.jpg
uploaded
7:25 pm -
image32.jpg
uploaded
7:25 pm