Zend 2 Auth与Bcrypt?

时间:2013-01-05 07:23:40

标签: zend-framework2 bcrypt zend-auth

Google没有太多解决方案(similar question but no answer)。

由于bcrypt每次都会生成一个新哈希,因此身份验证失败。我查看了代码(也许是自己扩展类),但它非常混乱(更喜欢本机解决方案)。如何将$bcrpt->verify()$identity->isValid()一起使用?

编辑:目前,我已经将认证DbTable类子类化,并且它正在运行,但我非常怀疑它是否已经过优化/“完全正确”。仍在寻找“优雅”的解决方案。

3 个答案:

答案 0 :(得分:15)

您可以使用:

Zend\Authentication\Adapter\DbTable\CallbackCheckAdapter

像这样:

use Zend\Authentication\Adapter\DbTable\CallbackCheckAdapter as AuthAdapter;
use Zend\Crypt\Password\Bcrypt;    

$credentialValidationCallback = function($dbCredential, $requestCredential) {
    return (new Bcrypt())->verify($requestCredential, $dbCredential);
};
$authAdapter = new AuthAdapter($dbAdapter, 'user', 'login', 'password', $credentialValidationCallback);
// ...

答案 1 :(得分:4)

正如你应该知道的那样,BCrypt使用盐来哈希。并且每次都会随机再次生成盐。如果您的数据库受到损害,这会大大增加查找所有密码的难度。因此,实际上,它每次都会生成一个新的哈希值。

我自己的解决方案是拥有自己的Zend\Authentication适配器,它将从数据库中检索用户模型(使用用户名/电子邮件),然后调用$user->checkPassword($credential); 。该方法将获得Zend\Crypt\Password\Bcrypt的实例。只需在给定密码上调用$bcrypt->verify(),在用户模型中调用哈希。

答案 2 :(得分:1)

我这样做了(测试代码并且有效)..;

if ($request->isPost()) {
            $form->setData($request->getPost());
            if ($form->isValid()) {

                $bcrypt = new Bcrypt();
                $user   = new User();
                $user->exchangeArray($form->getData());

                $password    = $user->password;
                $data        = $this->getUserTable()->selectUser($user->username);

                if (!$data)
                {
                    echo 'user not found';
                } else {

                    if ($bcrypt->verify($password, $data->hash)) {

                    $sm          = $this->getServiceLocator();
                    $dbAdapter   = $sm->get('Zend\Db\Adapter\Adapter');
                    $authAdapter = new AuthAdapter(
                                            $dbAdapter,
                                            'cms_users',
                                            'username',
                                            'hash'
                                        );
                    $authAdapter->setIdentity($user->username)
                                ->setCredential($data->hash);                           

                    $result = $auth->authenticate($authAdapter);
                    echo $result->getIdentity() . "\n\n";
                    // do you thing on succes/failure


                    } else {
                    echo 'invalid password';
                    }
                }
            }
        }