我需要檢查在訪問 BooksController 時是否收到標題“X-API-User-Name = admin”。
我使用這個檔案https://symfony.com/doc/current/event_dispatcher/before_after_filters.html
代碼 這是我的中間件
namespace App\Event;
use App\Controller\BooksController;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpKernel\Event\ControllerEvent;
use Symfony\Component\HttpKernel\KernelEvents;
use Symfony\Component\HttpKernel\Event\ResponseEvent;
class HeaderChecker implements EventSubscriberInterface
{
const HEADER = 'X-API-User-Name';
public function onKernelController(ControllerEvent $event): void
{
$controller = $event->getController();
if (is_array($controller)) {
$controller = $controller[0];
}
if ($controller instanceof BooksController) {
$header = $event->getRequest()->headers->has(self::HEADER);
if (!$header) return new JsonResponse(['message' => 'Header X-API-User-Name is not found'], Response::HTTP_FORBIDDEN);
$admin = $event->getRequest()->headers->get(self::HEADER);
if ($admin !== 'admin') return new JsonResponse(['message' => 'Header X-API-User-Name is not valid'], Response::HTTP_FORBIDDEN);
}
}
public static function getSubscribedEvents(): array
{
return [
KernelEvents::CONTROLLER => 'onKernelController'
];
}
}
service.yaml 代碼
App\Event\HeaderChecker:
tags:
- { name: kernel.event_subscriber, event: kernel.exception, method: 'onKernelController' }
問題:通過 var_dump 我檢查了資料是否進入,但事情是這樣的。如果 X-API-User-Name 不是管理員,我需要發送狀態為 403 的 JsonResponse。但是如果 X-API-User-Name 不是管理員,我的 EventSubscriber 類不會回傳 JsonResponse。我的錯誤是什么?
uj5u.com熱心網友回復:
這里發生了幾件事。如果您使用的是 EventSubscriber,則無需在 services.yaml 中添加任何其他行。從評論中我想你已經明白了這一點。
要驗證您的偵聽器連接是否正確,請使用bin/console debug:event-dispatcher kernel.controller. 你的聽眾應該出現。您也可以簡單地添加一個轉儲陳述句。
清除后,請注意您的 onKernelController 方法的回傳型別為 void。你可以回傳任何你想要的東西,但這不會有什么不同。您回傳的任何內容都將被忽略。這實際上帶來了所有這些如何實施的問題?在我看來,查看 HttpKernel::handleRaw 方法非常有指導意義。乍一看有點不知所措,但它確實顯示了內核事件何時被觸發以及之后會發生什么。
回到如何指示需要 json 回應的問題,諸如 RequestEvent 之類的事件具有 setResponse 方法。唉,你不知道帶有請求事件的控制器。
遺憾的是,ControllerEvent 不是 setResponse 方法。相反,它有一個 setController 方法,這意味著您可以實際更改控制器。
所以你需要做一個控制器動作來回傳你的 json 回應。然后你使用 $kernel->setController($controller) 來使用它。由于檔案中有示例,我不會顯示詳細代碼。
這有點牽連。僅檢查控制器操作本身中的標頭并完成它可能會更容易。另一方面,一旦你讓它作業并理解它為什么作業,那么你就擁有了一個對未來非常有用的工具。
最后一個想法:如果這是關于訪問控制,那么您可能應該拋出一個拒絕訪問的例外。給黑客內部安全資訊毫無意義。是否真的存在合法用戶應該能夠在沒有標頭的情況下訪問此控制器的情況?
轉載請註明出處,本文鏈接:https://www.uj5u.com/caozuo/385413.html
