List:Commits« Previous MessageNext Message »
From:rburnett Date:February 25 2008 10:15pm
Subject:Connector/NET commit: r1193 - in branches/5.2: . MySql.Web/Providers/Properties MySql.Web/Providers/Source MySql.Web/Tests
View as plain text  
Modified:
   branches/5.2/CHANGES
   branches/5.2/MySql.Web/Providers/Properties/Resources.resx
   branches/5.2/MySql.Web/Providers/Source/MembershipProvider.cs
   branches/5.2/MySql.Web/Tests/UserManagement.cs
Log:
- Fixed password validation logic for creating users and changing passwords.
  It actually works now.  (bug #34792)

Before this patch we actually didn't have any logic to check the length, non-alpha-ness,
and regex complexity of the new passwords.  We do now.


Modified: branches/5.2/CHANGES
===================================================================
--- branches/5.2/CHANGES	2008-02-22 20:54:05 UTC (rev 1192)
+++ branches/5.2/CHANGES	2008-02-25 21:15:55 UTC (rev 1193)
@@ -8,6 +8,8 @@
   their application id if the connection string has not been set. (bug #34451)
 - Fixed installer that did not install the DDEX provider binary if 
   the Visual Studio 2005 component was not selected. (bug #34674)
+- Fixed password validation logic for creating users and changing passwords.
+  It actually works now.  (bug #34792)
 
 Version 5.2 - 2/11/2008
 . Added ClearPool and ClearAllPools features

Modified: branches/5.2/MySql.Web/Providers/Properties/Resources.resx
===================================================================
--- branches/5.2/MySql.Web/Providers/Properties/Resources.resx	2008-02-22 20:54:05 UTC
(rev 1192)
+++ branches/5.2/MySql.Web/Providers/Properties/Resources.resx	2008-02-25 21:15:55 UTC
(rev 1193)
@@ -211,4 +211,16 @@
   <data name="UnableToCreateUser" xml:space="preserve">
     <value>Unable to create user.</value>
   </data>
+  <data name="ChangePasswordCanceled" xml:space="preserve">
+    <value>Change password operation was canceled.</value>
+  </data>
+  <data name="NotEnoughNonAlphaNumericInPwd" xml:space="preserve">
+    <value>Non alpha numeric characters in '{0}' needs to be greater than or equal
to '{1}'.</value>
+  </data>
+  <data name="PasswordNotLongEnough" xml:space="preserve">
+    <value>The length of parameter '{0}' needs to be greater or equal to
'{1}'.</value>
+  </data>
+  <data name="ValidatePasswordCanceled" xml:space="preserve">
+    <value>The validate password operation was canceled.</value>
+  </data>
 </root>
\ No newline at end of file

Modified: branches/5.2/MySql.Web/Providers/Source/MembershipProvider.cs
===================================================================
--- branches/5.2/MySql.Web/Providers/Source/MembershipProvider.cs	2008-02-22 20:54:05 UTC
(rev 1192)
+++ branches/5.2/MySql.Web/Providers/Source/MembershipProvider.cs	2008-02-25 21:15:55 UTC
(rev 1193)
@@ -38,6 +38,7 @@
 using MySql.Web.Profile;
 using MySql.Web.Common;
 using System.Transactions;
+using System.Text.RegularExpressions;
 
 namespace MySql.Web.Security
 {
@@ -379,26 +380,30 @@
         /// Changes the password.
         /// </summary>
         /// <param name="username">The username.</param>
-        /// <param name="oldPwd">The old password.</param>
-        /// <param name="newPwd">The new password.</param>
+        /// <param name="oldPassword">The old password.</param>
+        /// <param name="newPassword">The new password.</param>
         /// <returns>true if the password was updated successfully, false if the
supplied old password
         /// is invalid, the user is locked out, or the user does not exist in the
database.</returns>
-        public override bool ChangePassword(string username, string oldPwd, string
newPwd)
+        public override bool ChangePassword(string username, string oldPassword, string
newPassword)
         {
             // this will return false if the username doesn't exist
-            if (!(ValidateUser(username, oldPwd)))
+            if (!(ValidateUser(username, oldPassword)))
                 return false;
 
-            ValidatePasswordEventArgs args = new ValidatePasswordEventArgs(username,
newPwd, true);
+            ValidatePasswordEventArgs args = new ValidatePasswordEventArgs(username,
newPassword, true);
             OnValidatingPassword(args);
             if (args.Cancel)
             {
                 if (!(args.FailureInformation == null))
                     throw args.FailureInformation;
                 else
-                    throw new ProviderException(Resources.NewPasswordValidationFailed);
+                    throw new ProviderException(Resources.ChangePasswordCanceled);
             }
 
+            // validate the password according to current guidelines
+            if (!ValidatePassword(newPassword, "newPassword", true))
+                return false;
+
             try
             {
                 using (MySqlConnection connection = new
MySqlConnection(connectionString))
@@ -416,8 +421,8 @@
                         @"UPDATE my_aspnet_Membership
                         SET Password = @pass, LastPasswordChangedDate =
@lastPasswordChangedDate 
                         WHERE userId=@userId", connection);
-                    cmd.Parameters.AddWithValue("@pass", 
-                        EncodePassword(newPwd, passwordKey, passwordFormat));
+                    cmd.Parameters.AddWithValue("@pass",
+                        EncodePassword(newPassword, passwordKey, passwordFormat));
                     cmd.Parameters.AddWithValue("@lastPasswordChangedDate",
DateTime.Now);
                     cmd.Parameters.AddWithValue("@userId", userId);
                     return cmd.ExecuteNonQuery() > 0;
@@ -511,6 +516,13 @@
                 return null;
             }
 
+            // now try to validate the password
+            if (!ValidatePassword(password, "password", false))
+            {
+                status = MembershipCreateStatus.InvalidPassword;
+                return null;
+            }
+
             // now check to see if we already have a member by this name
             MembershipUser u = GetUser(username, false);
             if (u != null)
@@ -1415,7 +1427,41 @@
             }
         }
 
+        private bool ValidatePassword(string password, string argumentName, bool
throwExceptions)
+        {
+            string exceptionString = null;
+            object correctValue = MinRequiredPasswordLength;
 
+            if (password.Length < MinRequiredPasswordLength)
+                exceptionString = Resources.PasswordNotLongEnough;
+            else
+            {
+                int count = 0;
+                foreach (char c in password)
+                    if (!char.IsLetterOrDigit(c))
+                        count++;
+                if (count < MinRequiredNonAlphanumericCharacters)
+                    exceptionString = Resources.NotEnoughNonAlphaNumericInPwd;
+                correctValue = MinRequiredNonAlphanumericCharacters;
+            }
+
+            if (exceptionString != null)
+            {
+                if (throwExceptions)
+                    throw new ArgumentException(
+                        string.Format(exceptionString, argumentName, correctValue),
+                        argumentName);
+                else
+                    return false;
+            }
+                
+            if (PasswordStrengthRegularExpression.Length > 0)
+                if (!Regex.IsMatch(password, PasswordStrengthRegularExpression))
+                    return false;
+
+            return true;
+        }
+
         #endregion
     }
 }

Modified: branches/5.2/MySql.Web/Tests/UserManagement.cs
===================================================================
--- branches/5.2/MySql.Web/Tests/UserManagement.cs	2008-02-22 20:54:05 UTC (rev 1192)
+++ branches/5.2/MySql.Web/Tests/UserManagement.cs	2008-02-25 21:15:55 UTC (rev 1193)
@@ -50,12 +50,13 @@
             NameValueCollection config = new NameValueCollection();
             config.Add("connectionStringName", "LocalMySqlServer");
             config.Add("applicationName", "/");
+            config.Add("passwordStrengthRegularExpression", "bar.*");
             config.Add("passwordFormat", format.ToString());
             provider.Initialize(null, config);
 
             // create the user
             MembershipCreateStatus status;
-            provider.CreateUser("foo", "bar", "foo@stripped", null, null, true, null, out
status);
+            provider.CreateUser("foo", "barbar!", "foo@stripped", null, null, true, null,
out status);
             Assert.AreEqual(MembershipCreateStatus.Success, status);
 
             // verify that the password format is hashed.
@@ -65,7 +66,7 @@
             Assert.AreEqual(format, rowFormat);
 
             //  then attempt to verify the user
-            Assert.IsTrue(provider.ValidateUser("foo", "bar"));
+            Assert.IsTrue(provider.ValidateUser("foo", "barbar!"));
         }
 
         [Test]
@@ -92,15 +93,87 @@
             CreateUserWithFormat(MembershipPasswordFormat.Clear);
         }
 
+        /// <summary>
+        /// Bug #34792 New User/Changing Password Validation Not working. 
+        /// </summary>
         [Test]
         public void ChangePassword()
         {
             CreateUserWithHashedPassword();
-            provider.ChangePassword("foo", "bar", "bar2");
-            provider.ValidateUser("foo", "bar2");
+            try
+            {
+                provider.ChangePassword("foo", "barbar!", "bar2");
+                Assert.Fail();
+            }
+            catch (ArgumentException ae1)
+            {
+                Assert.AreEqual("newPassword", ae1.ParamName);
+                Assert.IsTrue(ae1.Message.Contains("length of parameter"));
+            }
+
+            try
+            {
+                provider.ChangePassword("foo", "barbar!", "barbar2");
+                Assert.Fail();
+            }
+            catch (ArgumentException ae1)
+            {
+                Assert.AreEqual("newPassword", ae1.ParamName);
+                Assert.IsTrue(ae1.Message.Contains("alpha numeric"));
+            }
+
+            // now test regex strength testing
+            bool result = provider.ChangePassword("foo", "barbar!", "zzzxxx!");
+            Assert.IsFalse(result);
+
+            // now do one that should work
+            result = provider.ChangePassword("foo", "barbar!", "barfoo!");
+            Assert.IsTrue(result);
+
+            provider.ValidateUser("foo", "barfoo!");
         }
 
+        /// <summary>
+        /// Bug #34792 New User/Changing Password Validation Not working. 
+        /// </summary>
         [Test]
+        public void CreateUserWithErrors()
+        {
+            provider = new MySQLMembershipProvider();
+            NameValueCollection config = new NameValueCollection();
+            config.Add("connectionStringName", "LocalMySqlServer");
+            config.Add("applicationName", "/");
+            config.Add("passwordStrengthRegularExpression", "bar.*");
+            config.Add("passwordFormat", "Hashed");
+            provider.Initialize(null, config);
+
+            // first try to create a user with a password not long enough
+            MembershipCreateStatus status;
+            MembershipUser user = provider.CreateUser("foo", "xyz", 
+                "foo@stripped", null, null, true, null, out status);
+            Assert.IsNull(user);
+            Assert.AreEqual(MembershipCreateStatus.InvalidPassword, status);
+
+            // now with not enough non-alphas
+            user = provider.CreateUser("foo", "xyz1234",
+                "foo@stripped", null, null, true, null, out status);
+            Assert.IsNull(user);
+            Assert.AreEqual(MembershipCreateStatus.InvalidPassword, status);
+
+            // now one that doesn't pass the regex test
+            user = provider.CreateUser("foo", "xyzxyz!",
+                "foo@stripped", null, null, true, null, out status);
+            Assert.IsNull(user);
+            Assert.AreEqual(MembershipCreateStatus.InvalidPassword, status);
+
+            // now one that works
+            user = provider.CreateUser("foo", "barbar!",
+                "foo@stripped", null, null, true, null, out status);
+            Assert.IsNotNull(user);
+            Assert.AreEqual(MembershipCreateStatus.Success, status);
+        }
+
+        [Test]
         public void DeleteUser()
         {
             CreateUserWithHashedPassword();

Thread
Connector/NET commit: r1193 - in branches/5.2: . MySql.Web/Providers/Properties MySql.Web/Providers/Source MySql.Web/Testsrburnett25 Feb