2013-05-05 84 views
3

我想管理員能夠/admin和成員重定向到/member當用戶被識別,但得到的主頁(/)。

控制器看起來是這樣的:

public function indexAction() 
{ 
    if ($this->get('security.context')->isGranted('ROLE_ADMIN')) 
    { 
     return new RedirectResponse($this->generateUrl('app_admin_homepage')); 
    } 
    else if ($this->get('security.context')->isGranted('ROLE_USER')) 
    { 
     return new RedirectResponse($this->generateUrl('app_member_homepage')); 
    } 
    return $this->forward('AppHomeBundle:Default:home'); 
} 

如果我的用戶登錄,它工作得很好,沒有任何問題。但是,如果他們都沒有,我的i18n的開關讓我得到一個不錯的例外:

合併過濾器只使用數組或哈希工作在 「AppHomeBundle:默認:home.html.twig」。

行崩潰:

{{ path(app.request.get('_route'), app.request.get('_route_params')|merge({'_locale': 'fr'})) }} 

如果我看app.request.get('_route_params'),它是空的,以及app.request.get('_route')

當然,我可以通過替換return $this->forward('AppHomeBundle:Default:home');return $this->homeAction();來解決我的問題,但我沒有明白。

是overwritting用戶要求的內部請求?

注:我使用Symfony version 2.2.1 - app/dev/debug

編輯

使用forward當在Symfony的源代碼,看,創建一個子請求,我們不在同一個範圍了。

/** 
* Forwards the request to another controller. 
* 
* @param string $controller The controller name (a string like BlogBundle:Post:index) 
* @param array $path  An array of path parameters 
* @param array $query  An array of query parameters 
* 
* @return Response A Response instance 
*/ 
public function forward($controller, array $path = array(), array $query = array()) 
{ 
    $path['_controller'] = $controller; 
    $subRequest = $this->container->get('request')->duplicate($query, null, $path); 

    return $this->container->get('http_kernel')->handle($subRequest, HttpKernelInterface::SUB_REQUEST); 
} 

通過查看Symfony2's scopes文檔,他們告訴爲什麼請求是範圍本身,以及如何處理它。但他們不知道爲什麼轉發時創建子請求。

一些更多的谷歌搜索把我的事件監聽器,在那裏我瞭解到,子請求可以被處理(details)。好的,對於子請求類型,但這仍然不能解釋爲什麼用戶請求被刪除。

我的問題是:

爲什麼用戶的要求被取消,並在轉發時不被複制?

+0

相反,你應該使用事件偵聽器此功能。事件監聽器可以處理當用戶使用ROLE_USRR嘗試爲ROLE_ADMIN用戶打開主頁時的情況。您可以通過創建FilterControllerEvent Listener並將其重定向到特定的控制器/操作來完成此操作。我希望這會有所幫助:http://stackoverflow.com/questions/12916439/symfony2-redirect-for-event-listener/16167953#16167953 – NHG 2013-05-05 13:18:22

+0

實際上,如果用戶訪問ROLE_ADMIN頁面,則防火牆將引發403。一個管理員可以訪問ROLE_USER的頁面。無論如何,這個問題更一般:我可以根據接口實現從控制器或另一個控制器切換,而'forward'對於這樣的工作看起來很好。如果「轉發」更新請求,我真的不明白在哪種情況下應該使用它。 – 2013-05-05 13:49:27

回答

1

所以,控制器動作被分離邏輯的一部分。這個功能並不知道對方的任何事情。我的答案是 - 單一行動處理特定請求(例如特定的uri prarams)。 從SF2文檔(http://symfony.com/doc/current/book/controller.html#requests-controller-response-lifecycle):

2路由器從請求中讀取信息(例如,URI),找到匹配該信息的 路由,並從路由中讀取參數_controller ;

3從匹配的路由的控制器 執行和控制器中的代碼創建並返回一個響應 對象;

如果您的請求是路徑/和你想裏面的動作(可以說indexAction())處理這條路線,執行另一個控制器動作(例如fancyAction()),你應該準備fancyAction()了點。我的意思是關於使用(例如):

public function fancyAction($name, $color) 
{ 
    // ... create and return a Response object 
} 

代替:從SF2 DOSC

public function fancyAction() 
{ 
    $name = $this->getRequest()->get('name'); 
    $color = $this->getRequest()->get('color'); 
    // ... create and return a Response object 
} 

實施例:

public function indexAction($name) 
{ 
    $response = $this->forward('AcmeHelloBundle:Hello:fancy', array(
     'name' => $name, 
     'color' => 'green', 
    )); 

    // ... further modify the response or return it directly 

    return $response; 
} 

請注意further modify the response

如果你真的需要請求對象,你可以嘗試:

public function indexAction() 
{ 
    // prepare $request for fancyAction 

    $response = $this->forward('AcmeHelloBundle:Hello:fancy', array('request' => $request)); 

    // ... further modify the response or return it directly 

    return $response; 
} 

public function fancyAction(Request $request) 
{ 
    // use $request 
}