123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282 |
- <?php
- /*
- * This file is part of the Symfony package.
- *
- * (c) Fabien Potencier <fabien@symfony.com>
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
- namespace Symfony\Component\Translation;
- use Symfony\Component\Translation\Loader\LoaderInterface;
- use Symfony\Component\Translation\Exception\NotFoundResourceException;
- /**
- * Translator.
- *
- * @author Fabien Potencier <fabien@symfony.com>
- *
- * @api
- */
- class Translator implements TranslatorInterface
- {
- /**
- * @var MessageCatalogueInterface[]
- */
- protected $catalogues = array();
- /**
- * @var string
- */
- protected $locale;
- /**
- * @var array
- */
- private $fallbackLocales = array();
- /**
- * @var LoaderInterface[]
- */
- private $loaders = array();
- /**
- * @var array
- */
- private $resources = array();
- /**
- * @var MessageSelector
- */
- private $selector;
- /**
- * Constructor.
- *
- * @param string $locale The locale
- * @param MessageSelector|null $selector The message selector for pluralization
- *
- * @api
- */
- public function __construct($locale, MessageSelector $selector = null)
- {
- $this->locale = $locale;
- $this->selector = $selector ?: new MessageSelector();
- }
- /**
- * Adds a Loader.
- *
- * @param string $format The name of the loader (@see addResource())
- * @param LoaderInterface $loader A LoaderInterface instance
- *
- * @api
- */
- public function addLoader($format, LoaderInterface $loader)
- {
- $this->loaders[$format] = $loader;
- }
- /**
- * Adds a Resource.
- *
- * @param string $format The name of the loader (@see addLoader())
- * @param mixed $resource The resource name
- * @param string $locale The locale
- * @param string $domain The domain
- *
- * @api
- */
- public function addResource($format, $resource, $locale, $domain = null)
- {
- if (null === $domain) {
- $domain = 'messages';
- }
- $this->resources[$locale][] = array($format, $resource, $domain);
- if (in_array($locale, $this->fallbackLocales)) {
- $this->catalogues = array();
- } else {
- unset($this->catalogues[$locale]);
- }
- }
- /**
- * {@inheritdoc}
- *
- * @api
- */
- public function setLocale($locale)
- {
- $this->locale = $locale;
- }
- /**
- * {@inheritdoc}
- *
- * @api
- */
- public function getLocale()
- {
- return $this->locale;
- }
- /**
- * Sets the fallback locale(s).
- *
- * @param string|array $locales The fallback locale(s)
- *
- * @deprecated since 2.3, to be removed in 3.0. Use setFallbackLocales() instead.
- *
- * @api
- */
- public function setFallbackLocale($locales)
- {
- $this->setFallbackLocales(is_array($locales) ? $locales : array($locales));
- }
- /**
- * Sets the fallback locales.
- *
- * @param array $locales The fallback locales
- *
- * @api
- */
- public function setFallbackLocales(array $locales)
- {
- // needed as the fallback locales are linked to the already loaded catalogues
- $this->catalogues = array();
- $this->fallbackLocales = $locales;
- }
- /**
- * Gets the fallback locales.
- *
- * @return array $locales The fallback locales
- *
- * @api
- */
- public function getFallbackLocales()
- {
- return $this->fallbackLocales;
- }
- /**
- * {@inheritdoc}
- *
- * @api
- */
- public function trans($id, array $parameters = array(), $domain = null, $locale = null)
- {
- if (null === $locale) {
- $locale = $this->getLocale();
- }
- if (null === $domain) {
- $domain = 'messages';
- }
- if (!isset($this->catalogues[$locale])) {
- $this->loadCatalogue($locale);
- }
- return strtr($this->catalogues[$locale]->get((string) $id, $domain), $parameters);
- }
- /**
- * {@inheritdoc}
- *
- * @api
- */
- public function transChoice($id, $number, array $parameters = array(), $domain = null, $locale = null)
- {
- if (null === $locale) {
- $locale = $this->getLocale();
- }
- if (null === $domain) {
- $domain = 'messages';
- }
- if (!isset($this->catalogues[$locale])) {
- $this->loadCatalogue($locale);
- }
- $id = (string) $id;
- $catalogue = $this->catalogues[$locale];
- while (!$catalogue->defines($id, $domain)) {
- if ($cat = $catalogue->getFallbackCatalogue()) {
- $catalogue = $cat;
- $locale = $catalogue->getLocale();
- } else {
- break;
- }
- }
- return strtr($this->selector->choose($catalogue->get($id, $domain), (int) $number, $locale), $parameters);
- }
- protected function loadCatalogue($locale)
- {
- try {
- $this->doLoadCatalogue($locale);
- } catch (NotFoundResourceException $e) {
- if (!$this->computeFallbackLocales($locale)) {
- throw $e;
- }
- }
- $this->loadFallbackCatalogues($locale);
- }
- private function doLoadCatalogue($locale)
- {
- $this->catalogues[$locale] = new MessageCatalogue($locale);
- if (isset($this->resources[$locale])) {
- foreach ($this->resources[$locale] as $resource) {
- if (!isset($this->loaders[$resource[0]])) {
- throw new \RuntimeException(sprintf('The "%s" translation loader is not registered.', $resource[0]));
- }
- $this->catalogues[$locale]->addCatalogue($this->loaders[$resource[0]]->load($resource[1], $locale, $resource[2]));
- }
- }
- }
- private function loadFallbackCatalogues($locale)
- {
- $current = $this->catalogues[$locale];
- foreach ($this->computeFallbackLocales($locale) as $fallback) {
- if (!isset($this->catalogues[$fallback])) {
- $this->doLoadCatalogue($fallback);
- }
- $current->addFallbackCatalogue($this->catalogues[$fallback]);
- $current = $this->catalogues[$fallback];
- }
- }
- protected function computeFallbackLocales($locale)
- {
- $locales = array();
- foreach ($this->fallbackLocales as $fallback) {
- if ($fallback === $locale) {
- continue;
- }
- $locales[] = $fallback;
- }
- if (strrchr($locale, '_') !== false) {
- array_unshift($locales, substr($locale, 0, -strlen(strrchr($locale, '_'))));
- }
- return array_unique($locales);
- }
- }
|