【问题标题】:symfony2: how to parameter localization so we can have 2 languages?symfony2:如何对本地化进行参数化,以便我们可以拥有 2 种语言?
【发布时间】:2015-06-15 14:51:35
【问题描述】:

在我的 symfony2 应用程序中,我设置了 JMSI18nRoutingBundle : http://jmsyst.com/bundles/JMSI18nRoutingBundle

我有以下配置:

jms_i18n_routing:
    default_locale: fr
    locales: [fr, en]
    strategy: prefix_except_default

我已经设置了一个控制器操作来更改语言环境:

/**
 * @Route("/public/change_locale/{locale}", name="change_locale", requirements={"locale" = "fr|en"})
 * @Template(":Core/Admin:test.html.twig")
 * @param Request $request
 * @param string $locale
 * @return array
 */
public function changeLocaleAction(Request $request, $locale)
{
    $request->setLocale($locale);
    $this->get('session')->set('_locale', $locale);

    return $this->redirectToRoute('home');
}

我发现会话中没有保留区域设置。由于我不明白的原因,在 twig 中生成路线时不会自动使用语言环境。 所以我来建立一个监听器来重新分配请求和会话的语言环境,但它仍然不能正常工作,我不能简单地将我的语言环境从“fr”更改为“en”并拥有我的布局点的所有路线到包含“en”语言环境参数的路由

在实现这个捆绑包的过程中我遗漏了什么?

我的听众:

<?php

namespace AppBundle\EventListener;

use Symfony\Component\DependencyInjection\ContainerInterface;
use Symfony\Component\HttpFoundation\Session\Session;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
use Symfony\Component\HttpKernel\HttpKernelInterface;

class LocaleListener
{
    private $container;

    public function __construct(ContainerInterface $container)
    {
        $this->container = $container;
    }

    public function setLocale(GetResponseEvent $event)
    {
        if (HttpKernelInterface::MASTER_REQUEST !== $event->getRequestType()) {
            return;
        }

        $request = $event->getRequest();
        if (!$request->hasPreviousSession()) {
            $request->setLocale($request->getPreferredLanguage($this->container->getParameter('jms_i18n_routing.locales')));
            return;
        }

        // on essaie de voir si la locale a été fixée dans le paramètre de routing _locale
        if ($locale = $request->attributes->get('_locale')) {
            $request->getSession()->set('_locale', $locale);
            $request->setLocale($locale);
        } else {
            // si aucune locale n'a été fixée explicitement dans la requête, on utilise celle de la session
            $request->setLocale($request->getSession()->get('_locale', $this->container->getParameter('jms_i18n_routing.default_locale')));
        }


}
}

EDIT1:

事实证明,如果我将 _locale 参数添加到我所有模板中的所有路由中,它就可以工作。 但是我很乐意避免这种情况,并且捆绑文档说使用请求上下文的语言环境以防我们不指定参数:http://jmsyst.com/bundles/JMSI18nRoutingBundle/master/usage 好吧,根据我的经验,捆绑包的这个功能无法正常工作

我不想编辑所有路线以添加 _locale 参数:

接待专业人士

EDIT2:

深入研究,我首先尝试覆盖twig的路径功能。它有效,如果我在路径函数中添加语言环境参数,我的模板路径现在会考虑语言环境。

但是,这不是正确的方法。

我发现 JMSi18nRoutingBundle 扩展了 symfony 路由器,它调用 $this->context。

似乎不是 null 的上下文没有 locale 参数。我可能需要在我的听众中改变这一点……有什么想法吗?

【问题讨论】:

    标签: php symfony internationalization twig locale


    【解决方案1】:

    我上次编辑时走在正确的道路上:请求上下文参数 _locale 也必须定义:

    我的听众变成了:

    <?php
    
    namespace AppBundle\EventListener;
    
    use Symfony\Component\DependencyInjection\ContainerInterface;
    use Symfony\Component\HttpFoundation\Session\Session;
    use Symfony\Component\HttpKernel\Event\GetResponseEvent;
    use Symfony\Component\HttpKernel\HttpKernelInterface;
    use Symfony\Component\Routing\RequestContext;
    
    class LocaleListener
    {
        /**
         * @var RequestContext
         */
        private $context;
        private $locales;
        private $defautLocales;
    
        public function __construct(RequestContext $context, $locales, $defautLocales)
        {
            $this->context = $context;
            $this->locales = $locales;
            $this->defautLocales = $defautLocales;
        }
    
        public function setLocale(GetResponseEvent $event)
        {  
            $request = $event->getRequest();
    
            if (!$request->hasPreviousSession()) {
                $request->setLocale($request->getPreferredLanguage($this->locales));
                return;
            }
    
            // on essaie de voir si la locale a été fixée dans le paramètre de routing _locale
            if ($locale = $request->attributes->get('_locale')) {
                $request->getSession()->set('_locale', $locale);
            } else {
                // si aucune locale n'a été fixée explicitement dans la requête, on utilise celle de la session
                $locale = $request->getSession()->get('_locale', $this->defautLocales);
            }
    
            $request->setLocale($locale);
            $this->context->setParameter('_locale', $locale);
    
        }
    }
    

    以及定义:

    locale_listener:
        class: %locale_listener.class%
        tags:
            - { name: kernel.event_listener, event: kernel.request, method: setLocale, priority: 17}
        arguments: [@router.request_context, '%jms_i18n_routing.locales%', '%jms_i18n_routing.default_locale%']
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-09-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-01-03
      • 1970-01-01
      • 2012-12-17
      相关资源
      最近更新 更多