Как я могу создать ссылку на текущий в моем шаблоне?
Я хочу создать переключатель языка, который должен ссылаться на текущую страницу на разных языках, поэтому все параметры должны быть одинаковыми, кроме локали.
Как я могу создать ссылку на текущий в моем шаблоне?
Я хочу создать переключатель языка, который должен ссылаться на текущую страницу на разных языках, поэтому все параметры должны быть одинаковыми, кроме локали.
Я заканчиваю тем, что запускаю свою собственную функцию для этого. Я хоть и был сначала включен где-то в FrameworkBundle
но ничего по этому поводу не нашел. Вот шаги, которые я предпринял.
Сначала я создал функцию расширения Twig, которая выводит тот же маршрут, что и тот, который пользователь посещает в данный момент (включая параметры и строку запроса). Я оставил этот шаг вам. Вы можете посмотреть эту ссылку из хорошего учебника по Symfony2 для описания того, как создать расширение Twig, если вы еще не знаете, как это сделать. Я мог бы помочь вам с этим, если вам это нужно.
Следующим шагом является создание самой функции, которая будет переключать локаль текущего маршрута. Этой функции потребуются объекты Request
и Router
в качестве зависимостей. В моем личном случае я поместил эту функцию в специальный сервис с именем RoutingHelper
service. Затем этот сервис используется моей функцией расширения Twig. Вот определение службы, которое я добавил в контейнер зависимостей:
acme.helper.routing:
class: Application\AcmeBundle\Helper\RoutingHelper
scope: "request"
arguments:
request: "@request"
router: "@router"
И конструктор моего сервиса:
protected $request;
protected $router;
public function __construct($request, $router)
{
$this->request = $request;
$this->router = $router;
}
Параметр $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);
}
По сути, он делает то, что до сих пор делали другие, но также обрабатывает параметры и строку запроса. Метод filterPrivateKeys
удалит частный атрибут из атрибутов маршрута. Эти атрибуты начинаются со знака подчеркивания и не должны передаваться обратно в генератор маршрутов. Вот его определение:
private function filterPrivateKeys($attributes)
{
$filteredAttributes = array();
foreach ($attributes as $key => $value) {
if (!empty($key) && $key[0] != '_') {
$filteredAttributes[$key] = $value;
}
}
return $filteredAttributes;
}
В конце концов, я могу сделать это в своем представлении Twig, чтобы создать ссылки для переключения языков:
{% block language_bar %}
<a href="{{ localize_route('en') }}"> English </a>
<a href="{{ localize_route('fr') }}"> Français </a>
{% endblock %}
Изменить:
Вот мое определение службы расширения ветки:
acme.twig.extension:
class: Application\AcmeBundle\Twig\Extension\AcmeExtension
arguments:
container: "@service_container"
tags:
- { name: twig.extension }
И в функции расширения ветки у меня есть этот вызов: $routingHelper = $this->container->get('acme.helper.routing');
Это должно устранить исключение, связанное с расширением области действия, поскольку расширение ветки не входит в область запроса.
Обновление:
Теперь с Symfony 2.1 возможно иметь переключатель локали более простым способом, чем раньше. Действительно, версия Symfony 2.1 представила новый параметр для маршрутов, который упрощает более переключение локали. Вот код, все в ветке
{% 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) }}
Это по-прежнему несколько строк кода ветки, но его можно включить в блок Twig для упрощения повторного использования. Спасибо stof от сообщества Symfony за приведенный выше код.
Надеюсь, это то, что вы ищете.
С уважением,
Мэтт
<a href="{{ path(app.request.attributes.get('_route')) }}">Current page</a>
Аналогичный вопрос: переключение языка без изменения текущей страницы