ali1 / cakephp-bruteforce
CakePHP 插件用于暴力破解保护
5.0.3
2020-03-13 08:42 UTC
Requires
- php: >=7.2
- ext-json: *
- ali1/brute-force-shield: ^1.0.2
- cakephp/cakephp: ^4.0
Requires (Dev)
- fig-r/psr2r-sniffer: dev-master
- phpstan/phpstan: 0.12
- phpunit/phpunit: ^8.0
README
这是一个 CakePHP 插件,用于轻松实现控制器方法的暴力破解保护。
Ali1/BruteForceShield 组件包装器 Ali1/BruteForceShield
特性
- 基于 IP 地址的保护
- 使用缓存类存储尝试,因此无需安装数据库
- 记录被阻止的尝试(使用 CakePHP 日志)
- 不计重复尝试(例如,如果用户多次尝试相同的用户名/密码组合)
- 可以在达到正常限制之前阻止同一用户名的多次尝试(以给用户输入正确用户名的机会,如果他们一直在尝试错误的一个)
- 可以应用于 AppController::initialize,以便在使用身份验证插件时进行更简单的设置
- 抛出可捕获的异常,可以可选地捕获
要求
- Composer
- CakePHP 4.0+
- PHP 7.2+
安装
在您的 CakePHP 根目录中:运行以下命令
composer require ali1/cakephp-bruteforce
然后,在您的项目根目录中的 Application.php 中,添加以下代码片段
// In project_root/Application.php: $this->addPlugin('Bruteforce');
或者,您可以使用以下 shell 命令在 bootstrap.php 中自动启用插件
bin/cake plugin load Bruteforce
基本使用
加载组件
// in AppController.php or any controller public function initialize(): void { parent::initialize(); $this->loadComponent('Bruteforce.Bruteforce'); }
应用保护($this->Bruteforce->validate
必须在实际验证或操作用户提交的数据之前执行)
public function login(): void { $config = new \Ali1\BruteForceShield\Configuration(); // see possible options below /** * @param string $name a unique string to store the data under (different $name for different uses of Brute * force protection within the same application. * @param array $data an array of data, can use $this->request->getData() * @param \Ali1\BruteForceShield\Configuration|null $config options * @param string $cache Cache to use (default: 'default'). Make sure to use one with a duration longer than your time window otherwise you will not be protected. * @return void */ $this->Bruteforce->validate( 'login', ['username' => $this->request->getData('username'), 'password' => $this->request->getData('password')], $config, 'default' ); // the user will never get here if fails Brute Force Protection // a TooManyAttemptsException will be thrown // usual login code here }
配置选项
validate
的第三个参数是 \Ali1\BruteForceShield\Configuration 对象。
有关配置暴力破解保护的说明,请参阅 此处。
用法
用于用户名/密码暴力破解的方法
// UsersController.php public $components = ['Bruteforce.Bruteforce']; ... public function login() { // prior to actually verifying data $bruteConfig = new \Ali1\BruteForceShield\Configuration(); $bruteConfig->setTotalAttemptsLimit(5); $bruteConfig->setStricterLimitOnKey('username', 3); // setting a limit of 5 above, then a different limit here would mean the user has 3 chances to get the password right, but then an additional 2 chances if they try a different username $bruteConfig->addUnencryptedKey('username'); // adding this would mean you could see which usernames are being attacked in your log files $this->Bruteforce->validate( 'login', // unique name for this BruteForce action ['username' => $this->request->getData('username'), 'password' => $this->request->getData('password')], $bruteConfig ); // rest of the login code to authorize the attempt }
防止基于 URL 的暴力破解
非表单数据也可以进行暴力破解
/** * @param string|null $hashedid * * @return void */ public function publicAuthUrl(string $hashedid): void { try { $bruteConfig = new Configuration(); $bruteConfig->addUnencryptedKey('hashedid'); $this->Bruteforce->validate( 'publicHash', ['hashedid' => $hashedid], $bruteConfig ); } catch (\Bruteforce\Exception\TooManyAttemptsException $e) { $this->Flash->error('Too many requests attempted. Please try again in a few minutes'); return $this->redirect('/'); } // then check if URL is actually valid
使用用户插件(例如 CakeDC/Users)
虽然不理想,但在使用您不想扩展或修改的插件时,可以将 validate
方法放在 AppController.php 的 initialize
方法中,因为这将在此插件的用户验证之前运行。
// AppController.php::initialize() $this->loadComponent('Bruteforce.Bruteforce'); // Keep above any authentication components if running on initialize (default) $this->Bruteforce->validate( 'login', // unique name for this BruteForce action ['username' => $this->request->getData('username'), 'password' => $this->request->getData('password')] // user entered data ); // this will not affect any other action except ones containing POSTed usernames and passwords (empty challenges never get counted or blocked)