gskema
gskema

Reputation: 3211

Return a response from KernelEvents::CONTROLLER subscriber

I'm implementing a controller filter using this pattern:

http://symfony.com/doc/current/event_dispatcher/before_after_filters.html#creating-an-event-listener

However, instead of throwing an HTTP exception I would like to return a response.

How can I do that? What's the best/most acceptable way in SF2?

public function onKernelController(FilterControllerEvent $event)
{
    if (!$event->isMasterRequest()) {
        return;
    }

    $controller = $event->getController();

    // $controller passed can be either a class or a Closure.
    // This is not usual in Symfony but it may happen.
    // If it is a class, it comes in array format
    if (!is_array($controller)) {
        return;
    }

    if ($controller[0] instanceof ResourceServerAuthorizedController) {
        $request = $event->getRequest();

        $response = $this->resourceServer->authorize($request);
        if (!$response->isOk()) {
            return $response; // ??? HERE
        }
    }
}

Upvotes: 2

Views: 2885

Answers (2)

BentCoder
BentCoder

Reputation: 12730

If you want to manipulate response for any given reason, you can do something like below which has some generic logic. You need to implement whatever else you want to do with it.

If you look for onKernelController in http://www.inanzzz.com/ site, you'll find 7 examples where it was used.

services:
    application_frontend.listener.player:
        class: Application\FrontendBundle\Listener\PlayerListener
        tags:
            - { name: kernel.event_listener, event: kernel.controller, method: onKernelController }

LISTENER

use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpKernel\Event\FilterControllerEvent;

....

    public function onKernelController(FilterControllerEvent $event)
    {
        if (!$event->isMasterRequest()) {
            return;
        }

        $controller = $event->getController();
        if (!is_array($controller)) {
            return;
        }

        if (!$controller[0] instanceof YourController) {
            return;
        }

        $message = 'Bye inanzzz';

        $event->setController(
            function() use ($message) {
                return new Response($message, 200);
            }
        );
    }

....

Upvotes: 4

Daniella
Daniella

Reputation: 129

At this level of kernel.controller you can't manipulate the response (for this you need kernel.response, and you need to use setResponse method - but there you can't verify the controller type). If you really need the controller type what you can do in this case is changing the controller with any callable:

$replacementController = new ReplacementController();
$event->setController($replacementController->getReplacementMethod());

Hope this answers to your question.

Upvotes: 1

Related Questions