ZF1:身份验证功能的单元测试


ZF1: unit testing of authentication functionality

我是单元测试的新手,正在尝试在Zend Framework 1应用程序中实现Index控制器的第一组测试。

在这个控制器中,我有一个登录操作,它使用Zend_Auth来检查提供的用户凭据。我不太明白什么是测试它的最佳方法:

  1. 创建单独的测试数据库配置。在进行任何测试之前,上传带有数据库初始状态的SQL文件,并将此测试数据库设置为默认数据库。

  2. 重新定义(以某种方式)Zend_Auth,使其始终返回带有用户信息的预定义数组(或空数组),并测试此场景。我在Zend Framework 2中找到了这个实现,但在版本1中没有。

我将感谢ZF1中的任何建议和项目链接,这些项目具有与数据库连接的身份验证和功能的单元测试。


UPD-

以下是我要测试的索引控制器的登录操作

public function loginAction()
{
    $loginForm = new Form_Login();
    $modelUser = new Model_User();
    $formData = $this->getRequest()->getPost();
    $flashMessenger = $this->_helper->getHelper('FlashMessenger');
    if(!empty($formData)){
        if($loginForm->isValid($formData)){
            $authAdapter = new Zend_Auth_Adapter_DbTable(Zend_Db_Table::getDefaultAdapter());
            $authAdapter->setTableName('user')
                ->setIdentityColumn('email')
                ->setCredentialColumn('password')
                ->setCredentialTreatment('MD5(?)');
            $authAdapter->setIdentity($formData['form_email']);
            $authAdapter->setCredential($formData['form_password']);
            $auth = Zend_Auth::getInstance();
            $result = $auth->authenticate($authAdapter);
            if($result->isValid()) {
                $userData = $authAdapter->getResultRowObject();
                $modelUser->setTimestamp($userData->user_id);
                $this->_processLoggedInUser($userData);
            } else {
                $loginForm->addError("Incorrect email/password");
            }
        }
    }
    //Retrieve Facebook App ID
    $this->view->facebookAppId = Zend_Registry::get('facebookAppId');
    $this->view->googleClientId = Zend_Registry::get('googleClientId');
    $this->view->loginForm = $loginForm;
    $this->view->userMsg = $flashMessenger->getMessages();
}

所以,我想,也许我可以使用Zend_Test_DbAdapter,将其设置为默认适配器,并使其返回预定义的数据集?

我发现了在单元测试中使用db数据的两种方法:

1.

public function testStudentLogin()
{
    $config = new Zend_Config_Ini(APPLICATION_PATH."/configs/application.ini", APPLICATION_ENV);
    $testDatabaseConfig = $config->testDb;
    $connection = Zend_Db::factory($testDatabaseConfig);
    Zend_Db_Table::setDefaultAdapter($adapter);
    $this->request->setMethod('POST');
    $this->request->setPost(array('form_email' => 'student', 'form_password' => '123'));
    $this->dispatch('/index/login');
    $this->assertController('index');
    $this->assertAction('login');
    $this->assertRedirect('/index/student-professor');
}

因此,在application.ini中存储测试数据库凭据。然后通过适配器初始化与它的连接,并更改Zend_db_Table::setDefaultAdapter。

2.

public function testStudentLogin()
{
    $adapter   = new Zend_Test_DbAdapter();
    $stmt1Rows = array(array('user_id' => 1, 'email' => 'student', 'password' => '202cb962ac59075b964b07152d234b70', 'user_type' => 'consumer', 'zend_auth_credential_match' => 1));
    $stmt1     = Zend_Test_DbStatement::createSelectStatement($stmt1Rows);
    $adapter->appendStatementToStack($stmt1);
    $this->request->setMethod('POST');
    $this->request->setPost(array('form_email' => 'student', 'form_password' => '123'));
    $this->dispatch('/index/login');
    $this->assertController('index');
    $this->assertAction('login');
    $this->assertRedirect('/index/student-professor');
}

在这里,您可以使用Zend_Test_DbAdapter,在这里您可以预定义将返回的数据。我认为使用单独的数据库进行测试会使代码更干净,所以我可能会使用这种方法。如果您有其他想法/最佳实践,请告诉我