Symfony Locale in Url

幾種方法:
  1. i18n-routing-bundle (link)
  2. router prefix + override decorating_translator (link)

期望:
  • 使用 aaa.bbb.com/en 或 /tw 可跳到指定語系的頁面

狀況:
  • 給 routing prefix 即可達成
  • 但只能給 zh_TW,只給 tw 會吃不到 語系檔,即使你更改語系檔名稱

作法:
  • 覆寫 tran key 找對應文字的那段





app/config/parameters.yaml
parameters:
    app_name: comismart
    locale: en
    app.locales: en|tw|cn
    locale_mapping: { tw: zh_TW, cn: zh_CN }

app/config/services.yaml
   app.decorating_translator:
        class:     AppBundle\Translation\Translator
        decorates: translator
        arguments:
            - '@app.decorating_translator.inner'
            # passing custom parameters
            - {'%%app_name%%': '%app_name%', '%%PRETTY_ERROR%%': 'This is not nice:'}
            - "%locale_mapping%"
        public:    false

Translation/Translator.php
namespace AppBundle\Translation;

use Symfony\Component\Translation\TranslatorBagInterface;
use Symfony\Component\Translation\TranslatorInterface;

class Translator implements TranslatorInterface, TranslatorBagInterface
{
    /** @var TranslatorBagInterface|TranslatorInterface */
    protected $translator;
    /** @var array */
    private $parameters;
    
    private $locale_mapping;

    /**
     * @param TranslatorInterface|TranslatorBagInterface $translator
     * @param array                                      $parameters
     */
    public function __construct($translator, $parameters, $locale_mapping = array())
    {
        $this->translator = $translator;
        $this->parameters = $parameters;
        $this->locale_mapping = $locale_mapping;
    }

    /**
     * @param string $id
     * @param array  $parameters
     * @param null   $domain
     * @param null   $locale
     *
     * @return string
     */
    public function trans($id, array $parameters = [], $domain = null, $locale = null)
    {
        $parameters = $this->updateParameters($parameters);

        return $this->translator->trans($id, $parameters, $domain, $locale);
    }

    /**
     * @param string $id
     * @param int    $number
     * @param array  $parameters
     * @param null   $domain
     * @param null   $locale
     *
     * @return string
     */
    public function transChoice($id, $number, array $parameters = [], $domain = null, $locale = null)
    {
        $parameters = $this->updateParameters($parameters);

        return $this->translator->transChoice($id, $number, $parameters, $domain, $locale);
    }

    /**
     * @param string $locale
     */
    public function setLocale($locale)
    {
        $locale = @$this->locale_mapping[$locale];
        if(empty($locale)) {
            $locale = 'en';
        }
        $this->translator->setLocale($locale);
    }

    /**
     * @return string
     */
    public function getLocale()
    {
        return $this->translator->getLocale();
    }

    /**
     * @param string|null $locale
     *
     * @return \Symfony\Component\Translation\MessageCatalogueInterface
     */
    public function getCatalogue($locale = null)
    {
        return $this->translator->getCatalogue($locale);
    }

    /**
     * @param array $parameters
     *
     * @return array
     */
    protected function updateParameters($parameters)
    {
        return array_merge($this->parameters, $parameters);
    }
}


app/config/routing.yml

cs_index:
    path:     /{_locale}/
    defaults: { _controller: AppBundle:Default:index }
cs_about:
    path:     /{_locale}/about
    defaults: { _controller: AppBundle:Default:about }

Symfony Locale in Url Symfony Locale in Url Reviewed by Wild on 4/16/2019 05:03:00 下午 Rating: 5

沒有留言:

沒有Google帳號也可發表意見唷!

技術提供:Blogger.