How to disable a doctrine filter in a param converter

I'm using the doctrine softdeleteable extension on a project and have my controller action set up as such.

/**
 * @Route("address/{id}/")
 * @Method("GET")
 * @ParamConverter("address", class="MyBundle:Address")
 * @Security("is_granted('view', address)")
 */
public function getAddressAction(Address $address)
{

This works great as it returns NotFound if the object is deleted, however I want to grant access to users with ROLE_ADMIN to be able to see soft deleted content.

Does there already exist a way to get the param converter to disable the filter or am I going to have to create my own custom param converter?


There are no existing ways to do it, but I've solved this problem by creating my own annotation, that disables softdeleteable filter before ParamConverter does its job.

AcmeBundle/Annotation/IgnoreSoftDelete.php:

namespace AcmeBundleAnnotation;

use DoctrineCommonAnnotationsAnnotation;

/**
 * @Annotation
 * @Target({"CLASS", "METHOD"})
 */
class IgnoreSoftDelete extends Annotation { }

AcmeBundle/EventListener/AnnotationListener.php:

namespace AcmeBundleEventListener;

use DoctrineCommonUtilClassUtils;
use DoctrineCommonAnnotationsReader;
use SymfonyComponentHttpKernelEventFilterControllerEvent;

class AnnotationListener {

    protected $reader;

    public function __construct(Reader $reader) {
        $this->reader = $reader;
    }

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

        list($controller, $method, ) = $controller;

        $this->ignoreSoftDeleteAnnotation($controller, $method);
    }

    private function readAnnotation($controller, $method, $annotation) {
        $classReflection = new ReflectionClass(ClassUtils::getClass($controller));
        $classAnnotation = $this->reader->getClassAnnotation($classReflection, $annotation);

        $objectReflection = new ReflectionObject($controller);
        $methodReflection = $objectReflection->getMethod($method);
        $methodAnnotation = $this->reader->getMethodAnnotation($methodReflection, $annotation);

        if (!$classAnnotation && !$methodAnnotation) {
            return false;
        }

        return [$classAnnotation, $classReflection, $methodAnnotation, $methodReflection];
    }

    private function ignoreSoftDeleteAnnotation($controller, $method) {
        static $class = 'AcmeBundleAnnotationIgnoreSoftDelete';

        if ($this->readAnnotation($controller, $method, $class)) {
            $em = $controller->get('doctrine.orm.entity_manager');
            $em->getFilters()->disable('softdeleteable');
        }
    }

}

AcmeBundle/Resources/config/services.yml:

services:
    acme.annotation_listener:
        class: AcmeBundleEventListenerAnnotationListener
        arguments: [@annotation_reader]
        tags:
            - { name: kernel.event_listener, event: kernel.controller }

AcmeBundle/Controller/DefaultController.php:

namespace AcmeBundleController;

use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
use SensioBundleFrameworkExtraBundleConfigurationTemplate;
use AcmeBundleAnnotationIgnoreSoftDelete;
use AcmeBundleEntityUser;

class DefaultController extends Controller {

    /**
     * @Route("/{id}")
     * @IgnoreSoftDelete
     * @Template
     */
    public function indexAction(User $user) {
        return ['user' => $user];
    }

}

Annotation can be applied to individual action methods and to entire controller classes.

链接地址: http://www.djcxy.com/p/65034.html

上一篇: 可删除)在symfony中过滤原则

下一篇: 如何禁用参数转换器中的原则过滤器