ASP.NET会员ChangePassword控件-需要检查先前的密码

5

我有一个新表,用来存储旧密码,我需要检查是否存在匹配。

如果存在匹配,我需要让ChangePassword控件不改变密码。我需要告诉用户这个密码已经被使用过,请选择一个新的密码。

我似乎无法打断控件改变密码的操作。也许我使用了错误的事件。

以下是我的代码片段,或者说我希望它能够工作。

非常感谢您的帮助。

protected void ChangePassword1_ChangedPassword(object sender, EventArgs e)
    {
        MembershipUser user = Membership.GetUser();
        string usrName = "";
        if (user != null)
        {
            string connStr = ConfigurationManager.ConnectionStrings["LocalSqlServer"].ConnectionString;
            SqlConnection mySqlConnection = new SqlConnection(connStr);
            SqlCommand mySqlCommand = mySqlConnection.CreateCommand();
            mySqlCommand.CommandText = "Select UserName from OldPasswords where UserName = 'test'";
            mySqlConnection.Open();
            SqlDataReader mySqlDataReader = mySqlCommand.ExecuteReader(CommandBehavior.Default);
            while (mySqlDataReader.Read())
            {
                usrName = mySqlDataReader["UserName"].ToString();
                if (usrName == user.ToString())
                {

                    Label1.Text = "Match";
                }
                else
                {
                    Label1.Text = "NO Match!";
                }
            }

1
我不确定你在这里想要做什么。你谈论想要验证旧密码,但是你的SQL语句只检索用户名,从未检查密码。你如何验证密码本身? - cortijon
是的,你说得对,那段代码在另一页上,我只是很快地组合了一个测试页面,抱歉造成了混淆。我只是在打断进程本身方面遇到了麻烦。 感谢你的意见。 - Steve
@Sky - 是的,我已经全部完成了,现在正在清理代码,进行更多测试。我很快就会发布所有内容。 再次感谢你的帮助! - Steve
我所需要的一切感谢就是点赞和勾选!很高兴能够帮忙。 - Sky Sanders
1个回答

6

史蒂夫,你覆盖了错误的方法。你想要覆盖可取消的ChangingPassword方法。

尝试这样做:

protected void ChangePassword1_ChangingPassword(object sender, LoginCancelEventArgs e)
{
    // do your lookup here, 
    bool passwordHasBeenPreviouslyUsed = true;

    if (passwordHasBeenPreviouslyUsed)
    {
        e.Cancel = true;
        // notify of error
        return;
    }

}

根据之前的问答,您永远不应该存储用户密码。去会员表获取盐并使用它来哈希传入的密码以与已经在查找表中存储的盐哈希值进行比较。祝好运。
(1)-当CEO发现他的密码以可利用的格式存储时,您的立场将有多站得住脚?我们黑魔法师受到信任,但这种信任也带来了风险。请注意。 ;-)
编辑:
一个工作示例:
ChangePassword.aspx
<%@ Page Language="C#" %>
<%@ Import Namespace="System.Diagnostics"%>

<script runat="server">
    protected void Page_Load(object sender, EventArgs e)
    {

    }

    protected void ChangePassword1_ChangingPassword(object sender, LoginCancelEventArgs e)
    {
        // works for me!
        Debugger.Break();
    }
</script>

<!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></title>
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <asp:ChangePassword ID="ChangePassword1" runat="server" OnChangingPassword="ChangePassword1_ChangingPassword">
        </asp:ChangePassword>
    </div>
    </form>
</body>
</html>

更新:您可能还感兴趣的是,在更高的范围内定义一个处理程序,以监视所有密码活动:

考虑以下内容:

public void SetupPasswordActionHook()
{

    //Occurs when a user is created, a password is changed, or a password is reset.
    Membership.ValidatingPassword += Membership_ValidatingPassword;
}

void Membership_ValidatingPassword(object sender, ValidatePasswordEventArgs e)
{

    // Gets a value that indicates whether the System.Web.Security.MembershipProvider.ValidatingPassword event is being raised during a 
    // call to the System.Web.Security.MembershipProvider.CreateUser() method.

    // true if the System.Web.Security.MembershipProvider.ValidatingPassword event is being raised during a call to the 
    // System.Web.Security.MembershipProvider.CreateUser() method; otherwise, false.
    bool isNewUser = e.IsNewUser;

    // Gets the password for the current create-user, change-password, or reset-password action.

    // The password for the current create-user, change-password, or reset-password action.
    string password = e.Password;

    // Gets the name of the membership user for the current create-user, change-password, or reset-password action.

    // The name of the membership user for the current create-user, change-password, or reset-password action.
    string username = e.UserName;

    // Gets or sets a value that indicates whether the current create-user, change-password, or reset-password action will be canceled.

    // true if the current create-user, change-password, or reset-password action will be canceled; otherwise, false. The default is false.
    e.Cancel = true;

    // Gets or sets an exception that describes the reason for the password-validation failure.

    // An System.Exception that describes the reason for the password-validation failure.
    e.FailureInformation = new Exception("This is why I failed your password");

}

非常感谢您提供的代码示例,我会尝试一下。当然,我不会以明文格式保存任何内容,密码在两个表中都是哈希值,并且我会将盐值与其一起存储。我获取用户输入的密码,然后将其与我在“OldPassword”表中拥有的密码进行比较。 再次感谢您的帮助。 - Steve
@Steve -(戴上心灵魔法师帽子)嗯...我感觉您可能没有在控件上指定ChangingPassword事件处理程序为ChangePassword1_ChangingPassword。(摘下心灵魔法师帽子)我做得怎么样?;-) - Sky Sanders
@Steve - 我正在清理一些旧代码,发现另一个在较高范围内处理密码活动的示例,可能会很有趣。 - Sky Sanders
@SkySanders,非常好的回答,但我更喜欢术士这个词。 - AaA

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接