Sep
13
2006
Changing password without entering old password
Another thing bothering me is the need (for an already logged in user) to enter the old password when changing to a new password. Same sort of solution as for using email as username - i.e we need to hide the CurrentPassword textbox control (by specifying a template).
<asp:ChangePassword ID="ChangePassword1" runat="server" OnChangingPassword="ChangePassword1_ChangingPassword" OnChangedPassword="ChangePassword1_ChangedPassword">
<SuccessTemplate>
<span id="Span1" class="content2">Your password has been updated.</span>
</SuccessTemplate>
<ChangePasswordTemplate>
<asp:TextBox ID="CurrentPassword" runat="server" TextMode="Password" Visible="false"></asp:TextBox>
<span id="Span1" class="content2">Your new password:</span> <span class="cred2">*</span><br />
<asp:TextBox ID="NewPassword" runat="server" TextMode="Password"></asp:TextBox>
<asp:RequiredFieldValidator ID="NewPasswordRequired" runat="server" ControlToValidate="NewPassword"
ErrorMessage="New Password is required." ToolTip="New Password is required."
ValidationGroup="ChangePassword1">*</asp:RequiredFieldValidator>
<br />
<span id="Span2" class="content2"> Confirm new password:</span> <span class="cred2">*</span> <br />
<asp:TextBox ID="ConfirmNewPassword" runat="server" TextMode="Password"></asp:TextBox>
<asp:RequiredFieldValidator ID="ConfirmNewPasswordRequired" runat="server" ControlToValidate="ConfirmNewPassword"
ErrorMessage="Confirm New Password is required." ToolTip="Confirm New Password is required."
ValidationGroup="ChangePassword1">*</asp:RequiredFieldValidator>
<asp:CompareValidator ID="NewPasswordCompare" runat="server" ControlToCompare="NewPassword"
ControlToValidate="ConfirmNewPassword" Display="Dynamic" ErrorMessage="The Confirm New Password must match the New Password entry."
ValidationGroup="ChangePassword1"></asp:CompareValidator>
<br />
<asp:Button ID="ChangePasswordPushButton" runat="server" CommandName="ChangePassword"
Text="Update" ValidationGroup="ChangePassword1" CssClass="submit" Width="68px" OnClick="ChangePasswordPushButton_Click" />
<asp:Literal ID="FailureText" runat="server" EnableViewState="False"></asp:Literal>
</ChangePasswordTemplate>
</asp:ChangePassword>
As you can see we have set CurrentPassword Visible="false"
However, we also need some code. The thing is the provider needs the current password to allow for a change, but the idea is here to Reset it (generate a new one) and set the ChangePassword textbox to the newly generated password just before the provider changes it.
We hook into the ChangingPassword event:
protected void ChangePassword1_ChangingPassword(object sender, LoginCancelEventArgs e)
{
MembershipUser mu = Membership.GetUser();
TextBox oBox = ChangePassword1.ChangePasswordTemplateContainer.FindControl("CurrentPassword") as TextBox;
oBox.Text = mu.ResetPassword();
}
So we gets the textbox by using FindControl, and we set the textbox value to the current members ResetPassword() (which will reset the password and return the newly generated one).
So, next step is that the ChangePassword control tries to change the password - and it will work cause the CurrentPassword textbox contains the current password.
This scheme will not only be great if you want to spare your visitors to enter the old password, but is also useful when creating some sort of admin routine, where you (as system admin) should be able to change password for a user, wothout knowing what their current password is.