• 使用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进行注册

  • 相关阅读:
    Java经典编程题50道之二十九
    Java经典编程题50道之二十八
    Java经典编程题50道之二十七
    Java经典编程题50道之二十六
    Java经典编程题50道之二十五
    Python3爬虫(十一) 爬虫与反爬虫
    Python3爬虫(十) 数据存储之非关系型数据库MongoDB
    Python3爬虫(九) 数据存储之关系型数据库MySQL
    Python3爬虫(八) 数据存储之TXT、JSON、CSV
    Python3爬虫(六) 解析库的使用之Beautiful Soup
  • 原文地址:https://www.cnblogs.com/Leo_wl/p/1893199.html
Copyright © 2020-2023  润新知