我最终为此推出了自己的功能.我虽然起初它被包含在某个地方,FrameworkBundle但没有找到任何关于它.这是我采取的步骤.
首先,我创建了一个Twig扩展函数,它将输出与用户当前访问的路径相同的路径(包括参数和查询字符串).我把这一步留给了你.如果你不知道如何创建一个Twig扩展,你可以从Symfony2的一个很好的教程中查看这个链接.如果你需要,我可以帮你.
下一步是创建将切换当前路由的语言环境的函数本身.此函数将需要Request和Router对象作为依赖项.在我个人的案例中,我把这个功能放在一个专门的服务命名RoutingHelper服务中.然后我的Twig扩展功能使用此服务.这里我添加到依赖容器中的服务定义:
acme.helper.routing:
class: Application\AcmeBundle\Helper\RoutingHelper
scope: "request"
arguments:
request: "@request"
router: "@router"
Run Code Online (Sandbox Code Playgroud)
我服务的构造函数:
protected $request;
protected $router;
public function __construct($request, $router)
{
$this->request = $request;
$this->router = $router;
}
Run Code Online (Sandbox Code Playgroud)
$ locale参数是要切换到的新语言环境.这里的功能:
public function localizeCurrentRoute($locale)
{
$attributes = $this->request->attributes->all();
$query = $this->request->query->all();
$route = $attributes['_route'];
# This will add query parameters to attributes and filter out attributes starting with _
$attributes = array_merge($query, $this->filterPrivateKeys($attributes));
$attributes['_locale'] = $locale;
return $this->router->generate($route, $attributes);
}
Run Code Online (Sandbox Code Playgroud)
从本质上讲,它完成了其他人迄今为止所做的工作,但它也处理参数和查询字符串.该方法filterPrivateKeys将从路由属性中删除私有属性.这些属性是以下划线开头的属性,不应传递回路由生成器.这里有它的定义:
private function filterPrivateKeys($attributes)
{
$filteredAttributes = array();
foreach ($attributes as $key => $value) {
if (!empty($key) && $key[0] != '_') {
$filteredAttributes[$key] = $value;
}
}
return $filteredAttributes;
}
Run Code Online (Sandbox Code Playgroud)
最后,我能够在我的Twig视图中创建切换区域设置的链接:
{% block language_bar %}
<a href="{{ localize_route('en') }}"> English </a>
<a href="{{ localize_route('fr') }}"> Français </a>
{% endblock %}
Run Code Online (Sandbox Code Playgroud)
编辑:
这里是我的twig扩展服务定义:
acme.twig.extension:
class: Application\AcmeBundle\Twig\Extension\AcmeExtension
arguments:
container: "@service_container"
tags:
- { name: twig.extension }
Run Code Online (Sandbox Code Playgroud)
在枝条扩展功能中,我有这个电话: $routingHelper = $this->container->get('acme.helper.routing');
这应该解决范围扩大异常发生,因为twig扩展不在请求范围内.
更新:
现在,Symfony 2.1可以比以前更容易地使用区域设置切换器.实际上,2.1版本的Symfony为路由引入了一个新参数,使得更容易进行区域设置切换器.这里是代码,都在树枝上
{% set route_params = app.request.attributes.get('_route_params') %}
{# merge the query string params if you want to keep them when switching the locale #}
{% set route_params = route_params|merge(app.request.query.all) %}
{# merge the additional params you want to change #}
{% set route_params = route_params|merge({'_locale': 'fr'}) %}
{{ path(app.request.attributes.get('_route'), route_params) }}
Run Code Online (Sandbox Code Playgroud)
它仍然是几行twig代码,但可以包含在Twig块中以便于重用.来自Symfony社区的stof对上面代码的信任.
希望这是你正在寻找的.
问候,
马特