move into sonardesk
This commit is contained in:
@@ -0,0 +1,39 @@
|
||||
<?php
|
||||
|
||||
namespace Modules\Security\Services;
|
||||
|
||||
use Modules\Security\Models\IpRule;
|
||||
|
||||
final class IpRuleService
|
||||
{
|
||||
public function isBlocked(string $ip, string $scope = 'admin'): bool
|
||||
{
|
||||
$column = $scope === 'login' ? 'applies_to_login' : 'applies_to_admin';
|
||||
$rules = IpRule::query()->where('is_active', true)->where($column, true)->get();
|
||||
$allow = $rules->where('type', 'allow');
|
||||
if ($allow->isNotEmpty() && ! $allow->contains(fn (IpRule $rule) => $this->matches($ip, $rule->address))) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return $rules->where('type', 'deny')->contains(fn (IpRule $rule) => $this->matches($ip, $rule->address));
|
||||
}
|
||||
|
||||
private function matches(string $ip, string $rule): bool
|
||||
{
|
||||
if ($ip === $rule) {
|
||||
return true;
|
||||
}
|
||||
if (! str_contains($rule, '/')) {
|
||||
return false;
|
||||
}
|
||||
[$subnet,$bits] = explode('/', $rule, 2);
|
||||
$bits = (int) $bits;
|
||||
if (filter_var($ip, FILTER_VALIDATE_IP, FILTER_FLAG_IPV4) && filter_var($subnet, FILTER_VALIDATE_IP, FILTER_FLAG_IPV4)) {
|
||||
$mask = -1 << (32 - $bits);
|
||||
|
||||
return (ip2long($ip) & $mask) === (ip2long($subnet) & $mask);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user