前进中的蜗牛

番茄大叔

水滴穿石,非一日之功;没有量变,何来质变。

.Net之美读书笔记14

Asp.net 的验证和授权

Asp.net为用户提供了一套验证机制,用户只需要遵守就可以。用户需要明白验证流程就可以了

  1. 用户输入用户名和密码是否有效检验
  2. 为有效用户创建cookie HttpCookie authCookie = FormsAuthentication.GetAuthCookie(userName, true)
  3. 利用创建的cookie 得到票据ticket FormsAuthenticationTicket ticket = FormsAuthentication.Decrypt(authCookie.Value);
  4. 将票据ticket转换为cookie并输出authCookie.Value = FormsAuthentication.Encrypt(newTicket);HttpContext.Current.Response.Cookies.Add(authCookie);
  5. 如果按照前四步,则asp.net内部处理了登陆状态;可以调用Request.IsAuthenticated是否认证,获取用户信息FormsIdentity identity = User.Identity as FormsIdentity;string userName = User.Identity.Name;

基本验证

  1. 新建一空的webForm站点
  2. web.config
<authentication mode="Forms">
    <forms timeout="600" slidingExpiration="true" loginUrl="~/SignIn.aspx" />
</authentication>
  1. Login.aspx
<form id="form1" runat="server">
    <asp:LoginView ID="LoginView1" runat="server">
        <LoggedInTemplate>
            <asp:LoginName ID="LoginName1" runat="server" />
            ,你已经登录了^_^
            <br />
            <br />

            你可以选择
            <asp:LoginStatus ID="LoginStatus1" runat="server" LogoutPageUrl="~/Logout.aspx" LogoutAction="Redirect" />
        </LoggedInTemplate>
        <AnonymousTemplate>
            用户名:<asp:TextBox ID="txtUserName" runat="server" Width="128px"></asp:TextBox>
            <br />
            密 码:<asp:TextBox ID="txtPassword" runat="server"></asp:TextBox>
            <br />
            <asp:Button ID="btnLogin" runat="server" Text="登 录" OnClick="btnLogin_Click" Width="100px" />
            <br />
            <br />
            <asp:Label ID="lbMessage" runat="server" ForeColor="Red" Text=""></asp:Label>
        </AnonymousTemplate>
    </asp:LoginView>
</form>

code:

	public partial class Login : System.Web.UI.Page
	{
		private enum LoginResult
		{
			Success,
			UserNotExist,
			PasswordWrong
		}
		// 用户登录
		private LoginResult CheckUser(string userName, string password)
		{

			string validPassword = "123";   // 包含正确的密码
			string validUserName = "sa";
			// 判断用户名是否正确
			if (validUserName.Equals(userName))
			{
				// 判断密码是否正确
				if (password.Equals(validPassword))
					return LoginResult.Success;
				else
					return LoginResult.PasswordWrong;
			}
			// 用户名不存在
			return LoginResult.UserNotExist;
		}

		protected void btnLogin_Click(object sender, EventArgs e)
		{

			TextBox txtUserName = LoginView1.FindControl("txtUserName") as TextBox;
			TextBox txtPassword = LoginView1.FindControl("txtPassword") as TextBox;
			Label lbMessage = LoginView1.FindControl("lbMessage") as Label;

			string userName = txtUserName.Text;
			string password = txtPassword.Text;

			LoginResult result = CheckUser(userName, password);

			string userData = "登录时间" + DateTime.Now.ToString();

			if (result == LoginResult.Success)
			{
				SetUserDataAndRedirect(userName, userData);
			}
			else if (result == LoginResult.UserNotExist)
			{
				lbMessage.Text = "用户名不存在!";
			}
			else
			{
				lbMessage.Text = "密码有误!";
			}
		}

		// 添加自定义的值,然后导航到来到此页面之前的位置
		private void SetUserDataAndRedirect(string userName, string userData)
		{
			// 获得Cookie
			HttpCookie authCookie = FormsAuthentication.GetAuthCookie(userName, true);

			// 得到ticket凭据
			FormsAuthenticationTicket ticket = FormsAuthentication.Decrypt(authCookie.Value);

			// 根据之前的ticket凭据创建新ticket凭据,然后加入自定义信息
			FormsAuthenticationTicket newTicket = new FormsAuthenticationTicket(
				ticket.Version, ticket.Name, ticket.IssueDate,
				ticket.Expiration, ticket.IsPersistent, userData);

			// 将新的Ticke转变为Cookie值,然后添加到Cookies集合中
			authCookie.Value = FormsAuthentication.Encrypt(newTicket);
			HttpContext.Current.Response.Cookies.Add(authCookie);

			// 获得 来到登录页之前的页面,即url中return参数的值
			string url = FormsAuthentication.GetRedirectUrl(userName, true);

			Response.Redirect(url);
		}
	}
  1. Default.aspx
	<form id="form1" runat="server">
		<asp:LoginView ID="LoginView1" runat="server">
			<AnonymousTemplate>
				欢迎访问, 游客 !      
			</AnonymousTemplate>
			<LoggedInTemplate>
				你好,
			<asp:LoginName ID="LoginName1" runat="server" />
				!
			<br />
				<strong>UserData值:</strong>
				<asp:Literal ID="lbUserData" runat="server" />
			</LoggedInTemplate>
		</asp:LoginView>
		<br />
		<asp:LoginStatus ID="LoginStatus1" runat="server" LogoutPageUrl="~/Logout.aspx" LogoutAction="Redirect" />
		<asp:Label ID="userName" runat="server"></asp:Label>
	</form>

code

		protected void Page_Load(object sender, EventArgs e)
		{
			if (!IsPostBack)
			{
				if (Request.IsAuthenticated)
				{
					FormsIdentity identity = User.Identity as FormsIdentity;
					string userName = User.Identity.Name;
					string userData = identity.Ticket.UserData;
					Literal lbUserData = LoginView1.FindControl("lbUserData") as Literal;
					lbUserData.Text = userData;
				}
			}
		}

自定义IIdentity和IPrincipal接口,获取更多的用户信息

  1. 添加App_code文件夹,其下添加文件CustomIdentity.cs、CustomPrincipal.cs
	public class CustomPrincipal: IPrincipal
	{
		private CustomIdentity identity;

		public CustomPrincipal(CustomIdentity identity)
		{
			this.identity = identity;
		}
		public IIdentity Identity
		{
			get
			{
				return identity;
			}
		}
		public bool IsInRole(string role)
		{
			return false;
		}
	}
public class CustomIdentity: IIdentity
	{
		private FormsAuthenticationTicket ticket;
		private HttpContext context = HttpContext.Current;

		public CustomIdentity(FormsAuthenticationTicket ticket)
		{
			this.ticket = ticket;
		}
		public string AuthenticationType
		{
			get { return "Custom"; }
		}
		public bool IsAuthenticated
		{
			get { return true; }
		}
		public string Name
		{
			get
			{
				return ticket.Name;
			}
		}

		public FormsAuthenticationTicket Ticket
		{
			get { return ticket; }
		}

		// 这里可以是任意来自数据库的值,由Name属性取得
		// 需要注意此时已通过身份验证
		public string Email
		{
			get
			{
				HttpCookie cookie = context.Request.Cookies["Email"];

				if (cookie == null || String.IsNullOrEmpty(cookie.Value))
				{
					string email = "m3321414@163.com";   // 实际应根据name属性从数据库中获得
					cookie = new HttpCookie("UserType", email);
					context.Response.Cookies.Add(cookie);
				}

				return cookie.Value;
			}
		}
		//添加的属性
		public string DeptName
		{
			get
			{
				HttpCookie cookie = context.Request.Cookies["DeptName"];

				if (cookie == null || String.IsNullOrEmpty(cookie.Value))
				{
					string DeptName = "开发部门";   // 实际应根据name属性从数据库中获得
					cookie = new HttpCookie("UserType", DeptName);
					context.Response.Cookies.Add(cookie);
				}

				return cookie.Value;
			}
		}

	}
  1. Global.asax文件下添加认证模块
		protected void Application_OnPostAuthenticateRequest(object sender, EventArgs e)
		{
			IPrincipal user = HttpContext.Current.User;
			if (user.Identity.IsAuthenticated
				&& user.Identity.AuthenticationType == "Forms")
			{

				FormsIdentity formIdentity = user.Identity as FormsIdentity;
				WebAppEmpty.App_Code.CustomIdentity identity = new CustomIdentity(formIdentity.Ticket);

				CustomPrincipal principal = new CustomPrincipal(identity);
				HttpContext.Current.User = principal;

				Thread.CurrentPrincipal = principal;
			}
		}
  1. 页面获取数据
    CustomIdentity identity = User.Identity as CustomIdentity;
        if (identity != null)
        {
            // 获得UserData中的值
            string userData = identity.Ticket.UserData;
            Literal lbUserData = LoginView1.FindControl("lbUserData") as Literal;
            lbUserData.Text = userData;
            lbEmail.Text = identity.Email;
            lbDeptName.Text = identity.DeptName;
        }

通过用户ID获取用户信息

添加一个根据用户ID,获取用户信息的方法。每次获取调用。

posted @ 2017-12-26 18:06  LoveTomato  阅读(219)  评论(0编辑  收藏  举报