zoukankan      html  css  js  c++  java
  • 使用HttpMoudle和IPrincipal实现自定义身份及权限认证

    HttpContext.Current.User用户对象表示用户的安全上下文,代码当前即以该用户的名义运行,包括用户的标识(IIdentity)和它们所属的任何角色。所有用户对象都需要实现 IPrincipal 接口。(MSDN) 

    创建一个User类实现IIdentity接口 重写相应的方法

     public class User : IIdentity
        {
            
    private int _id;
            
    private string _userName;
            
    private string _password;
            
    private bool _isAuthenticated;
            
    #region properties
            
    public virtual int Id
            {
                
    get { return this._id; }
                
    set { this._id = value; }
            }
            
    public virtual string UserName
            {
                
    get { return this._userName; }
                
    set { this._userName = value; }
            }
            
    public virtual string Password
            {
                
    get { return this._password; }
                
    set { this._password = value; }
            }
            //是否通过认证
            public virtual bool IsAuthenticated
            {
                
    get { return this._isAuthenticated; }
                
    set { this._isAuthenticated = value; }
            }
            
    //重写为用户ID
            public virtual string Name
            {
                
    get
                {
                    
    if (this._isAuthenticated)
                        
    return this._id.ToString();
                    
    else
                        
    return "";
                }
            }
            
    public virtual string AuthenticationType
            {
                
    get { return "CuyahogaAuthentication"; }
            }
            
    public User()
            {
                
    this._id = -1;
                
    this._isAuthenticated = false;
            }
        }


    创建一个CuyahogaPrincipal类实现IPrincipal接口

    public class CuyahogaPrincipal : IPrincipal
        {
            
    private User _user;
            
    // 返回一个现实IIdentity接口的user对象
            public IIdentity Identity
            {
                
    get { return this._user; }
            }

            
    // 当前用户是否属于指定角色 在以后的权限认证中可以使用 也可以使用User类中的相关方法来代替
            public bool IsInRole(string role)
            {
                
    foreach (Role roleObject in this._user.Roles)
                {
                    
    if (roleObject.Name.Equals(role))
                        
    return true;
                }
                
    return false;
            }

            
    ///初始化 若user通过授权则创建
            public CuyahogaPrincipal(User user)
            {
                
    if (user != null && user.IsAuthenticated)
                {
                    
    this._user = user;
                }
                
    else
                {
                    
    throw new SecurityException("Cannot create a principal without u valid user");
                }
            }
        }


    创建一个实现IHttpModule的AuthenticationModule类

     public class AuthenticationModule : IHttpModule
        {
            
    private const int AUTHENTICATION_TIMEOUT = 20;

            
    public AuthenticationModule()
            {
            }

            
    public void Init(HttpApplication context)
            {
                context.AuthenticateRequest 
    += new EventHandler(Context_AuthenticateRequest);
            }

            
    public void Dispose()
            {
                
    // Nothing here    
            }

            
    //登录时 验证用户时使用
            public bool AuthenticateUser(string username, string password, bool persistLogin)
            {
                //数据访问类
                CoreRepository cr = (CoreRepository)HttpContext.Current.Items["CoreRepository"];
                
    string hashedPassword = Encryption.StringToMD5Hash(password);
                
    try
                {
                    //通过用户名密码得到用户对象
                    User user = cr.GetUserByUsernameAndPassword(username, hashedPassword);
                    
    if (user != null)
                    {
                        user.IsAuthenticated 
    = true;
                        
    //string currentIp = HttpContext.Current.Request.UserHostAddress;
                        
    //user.LastLogin = DateTime.Now;
                        
    //user.LastIp = currentIp;
                        
    // Save login date and IP 记录相关信息
                        cr.UpdateObject(user);更新用户授权通过信息
                        
    // Create the authentication ticket
                        HttpContext.Current.User = new CuyahogaPrincipal(user);  //通过授权 
                        FormsAuthentication.SetAuthCookie(user.Name, persistLogin);
                        
    return true;
                    }
                    
    else
                    {
                        
    //log.Warn(String.Format("Invalid username-password combination: {0}:{1}.", username, password));
                        return false;
                    }
                }
                
    catch (Exception ex)
                {
                    
    throw new Exception(String.Format("Unable to log in user '{0}': " + ex.Message, username), ex);
                }
            }

            
    /// <summary>
            
    /// Log out the current user.注销用户
            
    /// </summary>
            public void Logout()
            {
                
    if (HttpContext.Current.User != null && HttpContext.Current.User.Identity.IsAuthenticated)
                {
                    FormsAuthentication.SignOut();
                }
            }

            
    private void Context_AuthenticateRequest(object sender, EventArgs e)
            {
                HttpApplication app 
    = (HttpApplication)sender;
                
    if (app.Context.User != null && app.Context.User.Identity.IsAuthenticated)//若用户已经通过认证
                {
                    CoreRepository cr 
    = (CoreRepository)HttpContext.Current.Items["CoreRepository"];
                    
    int userId = Int32.Parse(app.Context.User.Identity.Name);
                    User cuyahogaUser 
    = (User)cr.GetObjectById(typeof(User), userId);//得到对应的cuyahogaUser对象
                    cuyahogaUser.IsAuthenticated = true;
                    app.Context.User 
    = new CuyahogaPrincipal(cuyahogaUser);//将通过标准窗体认证的user替换成CuyahogaUser, cuyahogaUser包含更多的信息
                }
            }
        }


    登录时

     protected void btnLogin_Click(object sender, System.EventArgs e)
            {
                AuthenticationModule am 
    = (AuthenticationModule)Context.ApplicationInstance.Modules["AuthenticationModule"];
                
    if (this.txtUsername.Text.Trim().Length > 0 && this.txtPassword.Text.Trim().Length > 0)
                {
                    
    try
                    {
                        
    if (am.AuthenticateUser(this.txtUsername.Text, this.txtPassword.Text, this.chkPersistLogin.Checked))
                        {
                            
    //通过认证
                            Context.Response.Redirect(Context.Request.RawUrl);
                        }
                        
    else
                        {
                            
    //认证失败
                        }
                    }
                    
    catch (Exception ex)
                    {

                    }
                }
            }


    退出登录用

    protected void btnLogout_Click(object sender, System.EventArgs e)
            {

                AuthenticationModule am = (AuthenticationModule)Context.ApplicationInstance.Modules["AuthenticationModule"];
                am.Logout();

                Context.Response.Redirect(Context.Request.RawUrl);
            }


    这样就实现了身份认证功能

    然后可以方便的实现权限认证
    在User类中实现相应的权限逻辑 如: 表示当前用户是否有权限浏览指定的节点

    public bool CanView(Node node)
            {
                
    foreach (Permission p in node.NodePermissions)
                {
                    
    if (p.ViewAllowed && IsInRole(p.Role))
                    {
                        
    return true;
                    }
                }
                
    return false;
            }


    在Page代码中嵌入验证代码即可

    User CuyahogaUser =  this.User.Identity as User;
    if(CuyahogaUser.CanView())
    {
    }

    权限认证模块还是挺简单.
    别忘了在web.config中对AuthenticationModule进行注册

  • 相关阅读:
    中专毕业后我的七年(励志篇,年轻人必看)
    Excel实战技巧之[二级条件级联]
    kingston DataTraveler2.0 4GU盘量产成功
    Windows XP SP3增强补丁 V1.3 破解uxtheme.dll和TCP/IP连接数的破解
    诺基亚系列手机型号命名研究
    硬件检测相关工具大全
    最好的MacOSX美化包——MacXize(支持SP3)
    我终于把《新概念英语》三册&四册全背下来了
    IBM T22故障
    Windows通用克隆系统入门基础知识简介
  • 原文地址:https://www.cnblogs.com/Leo_wl/p/1893199.html
Copyright © 2011-2022 走看看