2012-10-18 23 views
6

symfonyのデフォルトの場所app/Resources/views/からテンプレートファイルをbase.html.twigという単純な場所に移動しようとしました。カスタムの場所はtheme/です。symfony2:Twig:カスタムテンプレートファイルのデフォルト設定

テンプレートファイルが含まれています

{% extends '::base.html.twig' %} 
    {% block body %} 
     Hello world! 
    {% endblock %} 

エラーがUnable to find template "::base.html.twig" in "AcmeCoreCoreBundle:Default:index.html.twig".を言ってにつながるコントローラ固有のテンプレートを使用して、コントローラAcme\Core\CoreBundle\Controllerにより、上記のテンプレートファイルの拡張

<!DOCTYPE html> 
    <html> 
    <head> 
    ... 
    </head> 
    <body> 
     {% block body %}{% endblock %} 
    </body> 
    </html> 

symfonyにグローバル空間でのテンプレートファイルの場所を教えてもらうにはどうすればいいですか?

ありがとうございます。

+0

は '\ Twig_Loader_Filesystem ::関数addpath( '__main __' $パス、$名前空間=)'([ソース]を参照(httpsで行うことができます://github.com/fabpot/Twig/blob/master/lib/Twig/Loader/Filesystem.php))どこから呼び出すかはわかりません。 TwigBundleの設定も見ていますが、そこにオプションがあるようには見えません。誰かがこれをさらに発展させたいなら、それは助けになるかもしれない。 –

答えて

7

アダムのヒントのため、私は自分で質問に答えることができます。誰でも興味があれば私の答えを提供したいと思います。

AcmeDemoBundleは簡単に使用できるtwig拡張子(クラスAcme\DemoBundle\Twig\Extension\DemoExtension)を提供します。コンストラクタを

に変更してください
public function __construct(FilesystemLoader $loader) 
    { 
    $this->loader = $loader; 
    $this->loader->addPath('path/to/your/directory'); 
    } 

これで、twig拡張を登録するようにsymfonyに指示してください。あなたのconfig.ymlファイル(例えばapp/config/config.yml)を編集し、

services: 
    demo.twig.extension 
     class: Acme\DemoBundle\Twig\Extension\DemoExtension 
     tags: 
     - { name: twig.extension } 
     arguments: 
     - @Twig.loader 

なく、少なくとも最後には、あなたの拡張小枝ファイルを変更し、デフォルトのテンプレートの名前空間から::を削除追加: {% extends 'base.html.twig' %}

$this->get('twig.loader')->addPath('path/to/your/directory'); 

そして、あなたのテンプレートで、このパスを使用することができます:あなたは(サービス)-containerから「twig.loader'サービスを得ることができ、アクションから

+1

私のヒントがあなたに正しい方向を指してくれてうれしく思います。このソリューションは、私が最初に提供しようと考えていたものよりもエレガントです。 –

1

@bestaはtwigの拡張子を付けて、twigローダーをコンストラクターに注入しました。しかし、小枝の延長では、環境を使用することができます:

class YourTwigExtension extends \Twig_Extension { 
... 
    public function initRuntime(\Twig_Environment $environment) { 
     $this->environment = $environment; 
     $this->environment->getLoader()->addPath(__DIR__ . '/Resources/views'); 
    } 
... 
} 
5

私はこれを実行する方がはるかに迅速です別の解決策を見つけることができました。私は最初にこの質問について受け入れられた答えを試しましたが、まだそのような経路の問題を抱えていました。私は、私はこのようなtwig.loaderコンテナへのパスを追加したテンプレートを呼び出すレンダリング直前に

$this->container->get('twig.loader')->addPath('../../../../theme/', $namespace = '__main__'); 

今すぐテンプレートを小枝は、ルートフォルダに「テーマ」と呼ばれるディレクトリからレンダリングされます。私はFabien Pontencier自身(SymfonyとTwigのクリエイター)から、ここに小枝のバグへの返信としてこの解決策を見つけました。https://github.com/symfony/symfony/issues/1912

+0

これを正確に探しています! – Subdigger

11

あなたがうまくやりたいことを正確に行うためのネイティブ機能があります。 Escentiallyあなたはapp/configのtwig設定にtwig名前空間を追加できます。

twig: 
    # ... 
    paths: 
     "%kernel.root_dir%/../vendor/acme/foo-bar/templates": foo_bar 

これはフォルダvendor/acme/foo-bar/templatesにエイリアスを作成し、あなたは、コントローラからいずれかのテンプレートをレンダリングするためにそれを使用することができます:

return $this->render(
    '@foo_bar/template.html.twig', 
    $data 
); 

または他の小枝テンプレートから

{% include '@foo_bar/template.html.twig' %} 
YML、このような

出典:official cookbook http://symfony.com/doc/current/cookbook/templating/namespaced_paths.html

1

これが世界的に行われることを前提としているとしたら、この種のものはcompiler passで行われることを意図しています。

それは、このような非常にクリーンで効率的な次のようになります。

<?php 

use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface; 
use Symfony\Component\DependencyInjection\ContainerBuilder; 

class CustomCompilerPass implements CompilerPassInterface 
{ 
    public function process(ContainerBuilder $container) 
    { 
     $loader = $container->getDefinition('twig.loader'); 
     $loader->addMethodCall('addPath', array('/path/to/views')); 
    } 
} 
+0

これはうまくいかず、 ''存在しないサービス "" twig.loader "'が戻ってきます。あなたは 'twig.loader.filesystem'を使う必要があります。 – sschueller