Browse Source

adding feature and unit tests for issue ZF-7289

git-svn-id: http://framework.zend.com/svn/framework/standard/trunk@22611 44c647ce-9c0f-0410-b52a-842ac1e357ba
dragonbe 15 years ago
parent
commit
4b796ce8f1

+ 38 - 1
library/Zend/Auth/Adapter/DbTable.php

@@ -114,6 +114,15 @@ class Zend_Auth_Adapter_DbTable implements Zend_Auth_Adapter_Interface
      * @var array
      */
     protected $_resultRow = null;
+    
+    /**
+     * $_ambiguityIdentity - Flag to indicate same Identity can be used with 
+     * different credentials. Default is FALSE and need to be set to true to
+     * allow ambiguity usage.
+     * 
+     * @var boolean
+     */
+    protected $_ambiguityIdentity = false;
 
     /**
      * __construct() - Sets configuration options
@@ -256,6 +265,34 @@ class Zend_Auth_Adapter_DbTable implements Zend_Auth_Adapter_Interface
         $this->_credential = $credential;
         return $this;
     }
+    
+    /**
+     * setAmbiguityIdentity() - sets a flag for usage of identical identities
+     * with unique credentials. It accepts integers (0, 1) or boolean (true,
+     * false) parameters. Default is false.
+     * 
+     * @param  int|bool $flag
+     * @return Zend_Auth_Adapter_DbTable
+     */
+    public function setAmbiguityIdentity($flag)
+    {
+        if (is_integer($flag)) {
+            $this->_ambiguityIdentity = (1 === $flag ? true : false);
+        } elseif (is_bool($flag)) {
+            $this->_ambiguityIdentity = $flag;
+        }
+        return $this;
+    }
+    /**
+     * getAmbiguityIdentity() - returns TRUE for usage of multiple identical 
+     * identies with different credentials, FALSE if not used.
+     * 
+     * @return bool
+     */
+    public function getAmbiguityIdentity()
+    {
+        return $this->_ambiguityIdentity;
+    }
 
     /**
      * getDbSelect() - Return the preauthentication Db Select object for userland select query modification
@@ -460,7 +497,7 @@ class Zend_Auth_Adapter_DbTable implements Zend_Auth_Adapter_Interface
             $this->_authenticateResultInfo['code'] = Zend_Auth_Result::FAILURE_IDENTITY_NOT_FOUND;
             $this->_authenticateResultInfo['messages'][] = 'A record with the supplied identity could not be found.';
             return $this->_authenticateCreateAuthResult();
-        } elseif (count($resultIdentities) > 1) {
+        } elseif (count($resultIdentities) > 1 && false === $this->getAmbiguityIdentity()) {
             $this->_authenticateResultInfo['code'] = Zend_Auth_Result::FAILURE_IDENTITY_AMBIGUOUS;
             $this->_authenticateResultInfo['messages'][] = 'More than one record matches the supplied identity.';
             return $this->_authenticateCreateAuthResult();

+ 57 - 0
tests/Zend/Auth/Adapter/DbTable/BasicSqliteTest.php

@@ -397,6 +397,63 @@ class Zend_Auth_Adapter_DbTable_BasicSqliteTest extends PHPUnit_Framework_TestCa
         // restore adapter
         Zend_Db_Table_Abstract::setDefaultAdapter($tmp);
     }
+    /**
+     * Test to see same usernames with different passwords can not authenticate
+     * when flag is not set. This is the current state of 
+     * Zend_Auth_Adapter_DbTable (up to ZF 1.10.6)
+     * 
+     * @group   ZF-7289
+     */
+    public function testEqualUsernamesDifferentPasswordShouldNotAuthenticateWhenFlagIsNotSet()
+    {
+        $this->_db->insert('users', array (
+            'username' => 'my_username',
+            'password' => 'my_otherpass',
+            'real_name' => 'Test user 2',
+        ));
+        
+        // test if user 1 can authenticate
+        $this->_adapter->setIdentity('my_username')
+                       ->setCredential('my_password');
+        $result = $this->_adapter->authenticate();
+        $this->assertTrue(in_array('More than one record matches the supplied identity.',
+            $result->getMessages()));
+        $this->assertFalse($result->isValid());
+    }
+    /**
+     * Test to see same usernames with different passwords can authenticate when
+     * a flag is set
+     * 
+     * @group   ZF-7289
+     */
+    public function testEqualUsernamesDifferentPasswordShouldAuthenticateWhenFlagIsSet()
+    {
+        $this->_db->insert('users', array (
+            'username' => 'my_username',
+            'password' => 'my_otherpass',
+            'real_name' => 'Test user 2',
+        ));
+        
+        // test if user 1 can authenticate
+        $this->_adapter->setIdentity('my_username')
+                       ->setCredential('my_password')
+                       ->setAmbiguityIdentity(true);
+        $result = $this->_adapter->authenticate();
+        $this->assertFalse(in_array('More than one record matches the supplied identity.',
+            $result->getMessages()));
+        $this->assertTrue($result->isValid());
+        $this->assertEquals('my_username', $result->getIdentity());
+        
+        // test if user 2 can authenticate
+        $this->_adapter->setIdentity('my_username')
+                       ->setCredential('my_otherpass')
+                       ->setAmbiguityIdentity(true);
+        $result2 = $this->_adapter->authenticate();
+        $this->assertFalse(in_array('More than one record matches the supplied identity.',
+            $result->getMessages()));
+        $this->assertTrue($result->isValid());
+        $this->assertEquals('my_username', $result->getIdentity());
+    }
 
 
     protected function _setupDbAdapter($optionalParams = array())