敏捷工具包 最大失败登录尝试次数


Agiletoolkit Maximum number of failed login attempts

agiletoolkit Auth/basic 类允许尝试登录,没有任何限制。我正在寻找一种限制失败登录尝试次数的方法,我试图覆盖此类的某些方法,但它使用 ajax 重新加载,因此 php 代码无法正确执行。

欢迎任何建议。

非常感谢,

受 StackOverflow 的启发,我实现了以下保护:

对于每个用户,我们存储软/硬锁。硬锁会拒绝验证密码,即使密码正确。软锁定是一段时间,之后我们将重置"不成功的尝试"计数器。每次您输入错误的密码时,软锁和硬锁都会增加,使您等待更长时间(但不是永远)逐渐增加会有一个合理的限制,因此如果您的攻击者试图入侵您的帐户一个小时 - 他只会尝试几次,但您的帐户可以在几个小时后登录。我已经在我的一个项目中实现了这一点,尽管它不是控制器,而是内置代码。请查看评论,希望对您和其他人有所帮助:

在"用户模型"中添加:

$this->addField('pwd_locked_until');
$this->addField('pwd_failure_count');
$this->addField('pwd_soft_unlock');

您还需要两种方法:

/* Must be called when user unsuccessfully tried to log-in */
function passwordIncorrect(){
    $su=strtotime($this['pwd_soft_unlock']);
    if($su && $su>time()){
        // aw, they repeatedly typed password in, lets teach them power of two!
        $this['pwd_failure_count']=$this['pwd_failure_count']+1;
        if($this['pwd_failure_count']>3){
            $this['pwd_locked_until']=date('Y-m-d H:i:s',time()
                +pow(2,min($this['pwd_failure_count'],20)));
            $this['pwd_soft_unlock']=date('Y-m-d H:i:s',time()
                +max(2*pow(2,min($this['pwd_failure_count'],20)),60*5));
        }
    }else{
        $this['pwd_failure_count']=1;
        $this['pwd_soft_unlock']=date('Y-m-d H:i:s',time() +60*5);
    }
    $this->save();
}

/* Must be called when user logs in successfully */
function loginSuccessful(){
    $this['last_seen']=date('Y-m-d H:i:s');
    $this['pwd_soft_unlock']=null;
    $this->save();
}

最后 - 您可以将其用作登录表单:

class Form_Login extends Form {
  function init(){
    parent::init();
    $form=$this;
    $form->setModel('User',array('email','password'));
    $form->addSubmit('Login');
    if($form->isSubmitted()){
        $auth=$this->api->auth;
        $l=$form->get('email');
        $p=$form->get('password');
        // check to see if user with such email exist
        $u=$this->add('Model_User');
        $u->tryLoadBy('email',$form->get('email'));
        // user may have also typed his username
        if(!$u->loaded()){
            $u->tryLoadBy('user_name',$form->get('email'));
        }
        // incorrect email - but say that password is wrong
        if(!$u->loaded())$form->getElement('password')
            ->displayFieldError('Incorrect Login');
        // if login is locked, don't verify password at all
        $su=strtotime($u['pwd_locked_until']);
        if($su>time()){
            $form->getElement('password')
                ->displayFieldError('Account is locked for '.
                $this->add('Controller_Fancy')
            ->fancy_datetime($u['pwd_locked_until']));
        }
        // check account
        if($auth->verifyCredentials($u['email'],$p)){
            // resets incorrect login statistics
            $u->loginSuccessful();
            $auth->login($l);
            // redirect user
            $form->js()->univ()->location($this->api->url('/'))->execute();
        }else{
            // incorrect password, register failed attempt
            $u->passwordIncorrect();
            $form->getElement('password')->displayFieldError('Incorrect Login');
        }
    }
  }
}

这应该由某人转换为附加组件。

我认为您可以使用 afterLoad 钩子在会话或 cookie 中存储Model_User(通常用于身份验证)的使用次数,然后在您需要的地方检查它。

哎呀。登录失败。所以你的模型没有加载。您只需要计算登录表单按钮的点击次数并将其存储在某个地方(cookie,数据库)。因此,创建您自己的登录表单,并在提交表单时添加一些条件,例如:

    $m = $this->add('Model_User');
    $f = $this->add("Form");
    $f->setModel($m, array('email', 'password'));
    $f->addSubmit("Log In");
    if ($f->isSubmitted()){
        //Limmiting
        if($_COOKIE[$this->api->name."_count_failed_login"] >= 5/*Here's you limit number*/){
            /*redirect or something else*/
        }
        if (/*here should be you condition*/){
            $_COOKIE[$this->api->name."_count_failed_login"] = 0;
            $this->api->auth->login($f->get("email"));
            $f->js()->univ()->redirect("index")->execute();
        }else{
            /* when login is failed*/
            if($_COOKIE[$this->api->name."_count_failed_login"]){
                $_COOKIE[$this->api->name."_count_failed_login"]++;
            }else{
                $_COOKIE[$this->api->name."_count_failed_login"] = 1;
            }
            $this->js()->univ()->alert('Wrong username or password')->execute();
        }
    }

我没有检查它。也许需要一些邻接。只是一个想法。

希望有帮助。