2012-06-24 36 views
8

Làm thế nào tôi có thể định nghĩa một hàm tạo trong bộ điều khiển Symfony2. Tôi muốn lấy dữ liệu người dùng đã đăng nhập có sẵn trong tất cả các phương thức của bộ điều khiển của mình, Hiện tại tôi làm một việc như thế này trong mọi hành động của bộ điều khiển để có được người dùng đã đăng nhập.Constructor trong Bộ điều khiển Symfony2

$em = $this->getDoctrine()->getEntityManager("pp_userdata"); 
$user = $this->get("security.context")->getToken()->getUser(); 

tôi muốn làm điều đó một lần trong một constructor và làm cho người dùng đăng nhập sẵn trên tất cả hành động của tôi

Trả lời

12

Đối với một giải pháp chung để thực hiện mã trước mọi hành động điều khiển bạn có thể đính kèm một người biết lắng nghe sự kiện vào kernel.controller sự kiện như vậy:

<service id="your_app.listener.before_controller" class="App\CoreBundle\EventListener\BeforeControllerListener" scope="request"> 
    <tag name="kernel.event_listener" event="kernel.controller" method="onKernelController"/> 
    <argument type="service" id="security.context"/> 
</service> 

Sau đó, trong bạn BeforeControllerListener bạn sẽ kiểm tra bộ điều khiển để xem nếu nó thực hiện một giao diện, nếu có, bạn sẽ gọi một phương thức từ giao diện và vượt qua trong giây ngữ cảnh thuần khiết.

<?php 

namespace App\CoreBundle\EventListener; 

use Symfony\Component\HttpKernel\Event\FilterControllerEvent; 
use Symfony\Component\Security\Core\SecurityContextInterface; 
use App\CoreBundle\Model\InitializableControllerInterface; 

/** 
* @author Matt Drollette <[email protected]> 
*/ 
class BeforeControllerListener 
{ 

    protected $security_context; 

    public function __construct(SecurityContextInterface $security_context) 
    { 
     $this->security_context = $security_context; 
    } 

    public function onKernelController(FilterControllerEvent $event) 
    { 
     $controller = $event->getController(); 

     if (!is_array($controller)) { 
      // not a object but a different kind of callable. Do nothing 
      return; 
     } 

     $controllerObject = $controller[0]; 

     // skip initializing for exceptions 
     if ($controllerObject instanceof ExceptionController) { 
      return; 
     } 

     if ($controllerObject instanceof InitializableControllerInterface) { 
      // this method is the one that is part of the interface. 
      $controllerObject->initialize($event->getRequest(), $this->security_context); 
     } 
    } 
} 

Sau đó, bất kỳ bộ điều khiển mà bạn muốn có người sử dụng luôn có sẵn, bạn sẽ chỉ thực hiện giao diện và thiết lập của người dùng như vậy:

use App\CoreBundle\Model\InitializableControllerInterface; 

class DefaultController implements InitializableControllerInterface 
{ 
    /** 
    * Current user. 
    * 
    * @var User 
    */ 
    private $user; 

    /** 
    * {@inheritdoc} 
    */ 
    public function initialize(Request $request, SecurityContextInterface $security_context) 
    { 
     $this->user = $security_context->getToken()->getUser(); 
    } 
// .... 
} 

Giao diện là gì khác hơn là

namespace App\CoreBundle\Model; 

use Symfony\Component\HttpFoundation\Request; 
use Symfony\Component\Security\Core\SecurityContextInterface; 

interface InitializableControllerInterface 
{ 
    public function initialize(Request $request, SecurityContextInterface $security_context); 
} 
+0

ai biết cách để viết các cấu hình trong yaml? chúng tôi sử dụng yaml và tôi không biết cách thêm 'đối số'. Tôi đọc này: http://symfony.com/doc/current/cookbook/service_container/event_listener.html cũng như không có sự giúp đỡ rõ ràng là – Toskan

+0

@Toskan bạn chỉ có thể làm một cái gì đó như: 'arguments: [" @em "," @ some_service "]' – takeit

+0

app.listener.constructor_listener: lớp: AppBundle \ EventListener \ ConstructorListener phạm vi: yêu cầu đối số: - {loại: dịch vụ, id: security.context} tags: - {name: kernel.event_listener , event: kernel.controller, phương thức: onKernelController} http://pastebin.com/NTySb68a – r4ccoon

2

Cách tiếp cận của tôi là:

  1. Thực hiện một trống Interface InitializableControllerInterface
  2. Make kiện Listener cho
 
namespace ACMEBundle\Event; 

use Symfony\Component\HttpKernel\Event\FilterControllerEvent; 

class ControllerConstructor 
{ 
    public function onKernelController(FilterControllerEvent $event) 
    { 
     $controller = $event->getController(); 
     if (!is_array($controller)) { 
      // not a object but a different kind of callable. Do nothing 
      return; 
     } 

     $controllerObject = $controller[0]; 
     if ($controllerObject instanceof InitializableControllerInterface) { 
      $controllerObject->__init($event->getRequest()); 
     } 
    } 
} 
  1. Trong điều khiển của bạn add:
 
class ProfileController extends Controller implements 
     InitializableControllerInterface 
{ 
public function __init() 
    { 
$this->user = $security_context->getToken()->getUser(); 
} 

Và bạn sẽ có thể để có được $ this-> người dùng trong mỗi hành động.

Trân

3

tôi runnig hơi muộn, nhưng trong một bộ điều khiển bạn chỉ có thể truy cập người dùng:

$this->getUser(); 

Nên làm việc kể từ 2.1

Các vấn đề liên quan