[FEATURE] Ip access block

This commit is contained in:
Simon Sessingø
2021-03-30 20:38:18 +02:00
parent 5a917a6905
commit 57047d23ea
4 changed files with 154 additions and 0 deletions

View File

@@ -82,6 +82,7 @@ You can donate any amount of your choice by [clicking here](https://www.paypal.c
- [Custom EventHandlers](#custom-eventhandlers)
- [Advanced](#advanced)
- [Disable multiple route rendering](#disable-multiple-route-rendering)
- [Restrict access to IP](#restrict-access-to-ip)
- [Url rewriting](#url-rewriting)
- [Changing current route](#changing-current-route)
- [Bootmanager: loading routes dynamically](#bootmanager-loading-routes-dynamically)
@@ -1370,6 +1371,31 @@ By default the router will try to execute all routes that matches a given url. T
This behavior can be easily disabled by setting `SimpleRouter::enableMultiRouteRendering(false)` in your `routes.php` file. This is the same behavior as version 3 and below.
## Restrict access to IP
You can white- and blacklist access to IP's using the build in `IpBlockAccess` middleware.
Create your own Middleware and extend the `IpBlockAccess` class.
You can use `*` to restrict access to a range of ips.
```php
use \Pecee\Http\Middleware\IpBlockAccess;
class IpBlockMiddleware extends IpBlockAccess {
protected $ipBlacklist = [
'5.5.5.5',
'8.8.*',
];
protected $ipWhitelist = [
'8.8.2.2',
];
}
```
## Url rewriting
### Changing current route

View File

@@ -0,0 +1,43 @@
<?php
namespace Pecee\Http\Middleware;
use Pecee\Http\Request;
use Pecee\SimpleRouter\Exceptions\HttpException;
abstract class IpBlockAccess implements IMiddleware
{
protected $ipBlacklist = [];
protected $ipWhitelist = [];
protected function validate(string $ip): bool
{
// Accept ip that is in white-list
if(in_array($ip, $this->ipWhitelist, true) === true) {
return true;
}
foreach ($this->ipBlacklist as $blackIp) {
// Blocks range (8.8.*)
if ($blackIp[strlen($blackIp) - 1] === '*' && strpos($ip, trim($blackIp, '*')) === 0) {
return false;
}
// Blocks exact match
if ($blackIp === $ip) {
return false;
}
}
return true;
}
public function handle(Request $request): void
{
if($this->validate((string)$request->getIp()) === false) {
throw new HttpException(sprintf('Restricted ip. Access to %s has been blocked', $request->getIp()), 403);
}
}
}

View File

@@ -0,0 +1,71 @@
<?php
require_once 'Dummy/DummyController.php';
require_once 'Dummy/Middleware/IpBlockMiddleware.php';
class CustomMiddlewareTest extends \PHPUnit\Framework\TestCase
{
public function testIpBlock() {
$this->expectException(\Pecee\SimpleRouter\Exceptions\HttpException::class);
global $_SERVER;
// Test exact ip
$_SERVER['remote-addr'] = '5.5.5.5';
TestRouter::group(['middleware' => IpBlockMiddleware::class], function() {
TestRouter::get('/fail', 'DummyController@method1');
});
TestRouter::debug('/fail');
// Test ip-range
$_SERVER['remote-addr'] = '8.8.4.4';
TestRouter::router()->reset();
TestRouter::group(['middleware' => IpBlockMiddleware::class], function() {
TestRouter::get('/fail', 'DummyController@method1');
});
TestRouter::debug('/fail');
}
public function testIpSuccess() {
global $_SERVER;
// Test ip that is not blocked
$_SERVER['remote-addr'] = '6.6.6.6';
TestRouter::router()->reset();
TestRouter::group(['middleware' => IpBlockMiddleware::class], function() {
TestRouter::get('/success', 'DummyController@method1');
});
TestRouter::debug('/success');
// Test ip in whitelist
$_SERVER['remote-addr'] = '8.8.2.2';
TestRouter::router()->reset();
TestRouter::group(['middleware' => IpBlockMiddleware::class], function() {
TestRouter::get('/success', 'DummyController@method1');
});
TestRouter::debug('/success');
$this->assertTrue(true);
}
}

View File

@@ -0,0 +1,14 @@
<?php
class IpBlockMiddleware extends \Pecee\Http\Middleware\IpBlockAccess {
protected $ipBlacklist = [
'5.5.5.5',
'8.8.*',
];
protected $ipWhitelist = [
'8.8.2.2',
];
}