Files
alrahma_sunday_school_api/app/Http/Controllers/Api/Auth/IpBanController.php
T
2026-03-11 17:53:15 -04:00

116 lines
3.6 KiB
PHP

<?php
namespace App\Http\Controllers\Api\Auth;
use App\Http\Controllers\Api\BaseApiController;
use App\Http\Requests\Security\IpBanIndexRequest;
use App\Http\Requests\Security\IpBanRequest;
use App\Http\Requests\Security\IpUnbanRequest;
use App\Http\Resources\Security\IpBanCollection;
use App\Http\Resources\Security\IpBanResource;
use App\Models\IpAttempt;
use App\Services\Security\IpBanCommandService;
use App\Services\Security\IpBanQueryService;
use Illuminate\Http\JsonResponse;
use Illuminate\Support\Facades\Log;
use Symfony\Component\HttpFoundation\Response;
class IpBanController extends BaseApiController
{
public function __construct(
private IpBanQueryService $queryService,
private IpBanCommandService $commandService
) {
parent::__construct();
}
public function index(IpBanIndexRequest $request): JsonResponse
{
$this->authorize('viewAny', IpAttempt::class);
$filters = $request->validated();
$page = (int) ($filters['page'] ?? 1);
$perPage = (int) ($filters['per_page'] ?? 20);
$bans = $this->queryService->paginate($filters, $page, $perPage);
$collection = new IpBanCollection($bans);
return $this->success([
'bans' => $collection->toArray($request),
'meta' => $collection->with($request)['meta'],
]);
}
public function show(int $id): JsonResponse
{
$ban = $this->queryService->find($id);
if (!$ban) {
return $this->error('IP record not found.', Response::HTTP_NOT_FOUND);
}
$this->authorize('view', $ban);
return $this->success([
'ban' => new IpBanResource($ban),
]);
}
public function ban(IpBanRequest $request): JsonResponse
{
$this->authorize('create', IpAttempt::class);
$validated = $request->validated();
$id = $validated['id'] ?? null;
$ip = $validated['ip'] ?? null;
$hours = (int) ($validated['hours'] ?? 24);
try {
$ban = $this->commandService->banNow($id ? (int) $id : null, $ip ? (string) $ip : null, $hours);
} catch (\Throwable $e) {
Log::error('IP ban failed: ' . $e->getMessage());
return $this->error('Unable to ban IP.', Response::HTTP_INTERNAL_SERVER_ERROR);
}
if (!$ban) {
return $this->error('IP record not found.', Response::HTTP_NOT_FOUND);
}
return $this->success([
'ban' => new IpBanResource($ban),
], 'IP banned.');
}
public function unban(IpUnbanRequest $request): JsonResponse
{
$this->authorize('update', IpAttempt::class);
$validated = $request->validated();
$all = filter_var($validated['all'] ?? false, FILTER_VALIDATE_BOOLEAN);
try {
if ($all) {
$count = $this->commandService->unbanAll();
return $this->success([
'count' => $count,
], $count . ' IP(s) unbanned.');
}
$ban = $this->commandService->unbanOne(
isset($validated['id']) ? (int) $validated['id'] : null,
$validated['ip'] ?? null
);
} catch (\Throwable $e) {
Log::error('IP unban failed: ' . $e->getMessage());
return $this->error('Unable to unban IP.', Response::HTTP_INTERNAL_SERVER_ERROR);
}
if (!$ban) {
return $this->error('IP record not found.', Response::HTTP_NOT_FOUND);
}
return $this->success([
'ban' => new IpBanResource($ban),
], 'IP unbanned.');
}
}