2013-08-25 28 views
1

在我的Symfony2項目中,我使用Twig模板來呈現HTML,並且我需要一個「應用程序欄」來包含每個網站的頁面。這個欄的內容取決於用戶是誰,她擁有什麼特權等(換句話說,有一些業務邏輯需要在幕後執行)。顯而易見的解決方案似乎是在基本模板中添加應用程序欄(因爲它需要出現在每個頁面上)。然而,問題在於,如何從基本(父)Twig模板執行業務邏輯尚不清楚。從父樹枝模板調用PHP業務邏輯

@Flukey在this question中遇到了類似的問題,他的解決方案是從樹枝模板中的子控制器render,從而強制執行輔助控制器。要明確,他的解決方案如下所示:

{# ::base:html.twig #} 
<!DOCTYPE html> 
<html> 
    <head> 
     <title>blah</title> 
     {% block stylesheets %}{# default styles #}{% endblock %} 
    </head> 
    <body> 
     {# Question: is there a way to do add the app-bar without "render"? #} 
     {% render url('app_bar_route') %} 
     {% block body %}{% endblock %} 
     {% block javascripts %}{% endblock %} 
    </body> 
</html> 

而且孩子:

{# AcmeDemoBundle:userpage.html.twig #} 
{% extends '::base.html.twig' %} 
{% block body %}user content here; Twig file rendered from "primary" PHP Controller.{% endblock %} 

爲了使render工作,我們還要求要定義的路線:

# routing.yml 
app_bar_route: 
    pattern: /sitestructure/appbar 
    defaults: { _controller: SiteManagerBundle:AppBar:index } 

但是這個解決方案非常不利於我,原因如下:

  • 首先,這個方案意味着你必須在你的網站管理每個導航欄單獨的新URL
  • 其次,(在本例中http://mysite/sitestructure/appbar以上)的網站上的每個導航欄單獨的URL ,這似乎很雜亂
  • 第三,也有this concern about performance,我覺得非常明智的關注。我不明白爲什麼每個用戶對HTML頁面的請求都會導致兩個(或三個或四個)物理請求被髮送到服務器 - 爲該網站上的每個導航欄添加一個額外的render請求(更多nav-當網站變得更加複雜時,酒吧可能會被添加)。

那麼有沒有更好的方法來做到這一點?是否可以使用Twig的{% include %}功能而不是{% render %},如果是這樣,基模板的業務邏輯如何執行?

編輯: 爲了澄清,「商業邏輯」,我指的需要進行數據庫調用的類型 - 這不是邏輯我想代碼插入到模板的類型,所以我需要以某種方式獲得回到PHP類/函數。

EDIT2: 我真的很擔心打電話給子控制器嗎?也許我誤解了render引擎的工作方式。我認爲這會對Web服務器產生第二個HTTP請求(顯然不是來自Web瀏覽器,而是來自服務器本身的內部請求)。對我而言,這似乎意味着相當大的開銷,更不用說增加產生某種響應錯誤的機會。但後來也許我誤解了框架,在這種情況下,請教育我!

回答

0

我不確定我是否理解你的所有觀點。

你絕對可以讓一個app_bar模板,並將其包含在您的基本模板:

<body> 
    {{ include('@MyBundle/app_bar.html.twig') }} 
    {% block body %}{% endblock %} 
</body> 

你當然可以顯示app_bar不同項目根據用戶

{% if is_granted('ROLE_ADMINx') %} 
    <li><a href="{{ path('zayso_natgames_admin') }}">Admin</a></li> 
{% endif %} 

目前還不清楚什麼其他某種你需要的「商業邏輯」。如果它超出了簡單的條件,那麼你可以把代碼放在樹枝中。

我有種印象,你需要更多?也許多種類型的app_bar?我不明白關於「每個導航欄」的東西需要特別的東西。

您可能會誤解子控制器的實現方式。子控制器請求在內部完成。沒有往返瀏覽器。性能影響很小。不需要多個網址,只需要一個route_app_bar。

除非我完全誤解了這個問題。

+0

我談論的「業務邏輯」可能會包括數據庫調用(但我並不是真的想讓這個問題陷入太多細節)。主要的一點是,我需要回到PHP類來做一些額外的邏輯。我知道如何在Smarty中做到這一點,但Twig的哲學看起來有點不同。 – cartbeforehorse

+0

你可能是對的,我不明白子控制器是如何實現的。如果這一切都是在內部完成的,那麼它並沒有我想象的那麼糟糕。我只需要接受這是它的工作原理。 – cartbeforehorse

+1

枝條與Smarty不同。既用我投了枝杈。你可以用樹枝擴展的方式進行數據庫調用,但幾乎可以肯定地使用子控制器。這:http://symfony.com/doc/current/components/http_kernel/introduction.html可能有點壓倒性,但如果你向下滾動到接近底部,子請求被解釋。 – Cerad