LocaleConfigSubscriber.php 4.65 KB
Newer Older
1 2 3
<?php
/**
 * @file
4
 * Contains \Drupal\locale\LocaleConfigSubscriber.
5 6 7 8 9
 */

namespace Drupal\locale;

use Drupal\Core\Config\Config;
10 11
use Drupal\Core\Config\Context\ConfigContext;
use Drupal\Core\Config\Context\ContextInterface;
12 13
use Drupal\Core\Config\ConfigEvent;
use Drupal\Core\Config\StorageDispatcher;
14
use Drupal\Core\Language\Language;
15
use Drupal\Core\Language\LanguageManager;
16 17 18
use Symfony\Component\HttpKernel\HttpKernelInterface;
use Symfony\Component\HttpKernel\KernelEvents;
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
19 20 21 22 23 24 25 26
use Symfony\Component\EventDispatcher\EventSubscriberInterface;


/**
 * Locale Config helper
 *
 * $config is always a DrupalConfig object.
 */
27
class LocaleConfigSubscriber implements EventSubscriberInterface {
28

29
  /**
30
   * The language manager.
31 32 33 34 35
   *
   * @var \Drupal\Core\Language\LanguageManager
   */
  protected $languageManager;

36 37 38 39 40
  /**
   * Default configuration context.
   *
   * @var \Drupal\Core\Config\Context\ContextInterface
   */
41 42
  protected $defaultConfigContext;

43 44 45 46 47
  /**
   * Constructs a LocaleConfigSubscriber object.
   *
   * @param \Drupal\Core\Language\LanguageManager $language_manager
   *   The language manager service.
48 49
   * @param \Drupal\Core\Config\Context\ConfigContext $config_context
   *   The configuration context service.
50
   */
51
  public function __construct(LanguageManager $language_manager, ContextInterface $config_context) {
52
    $this->languageManager = $language_manager;
53 54 55 56
    $this->defaultConfigContext = $config_context;
  }

  /**
57
   * Initializes configuration context with language.
58 59 60 61 62 63 64
   *
   * @param \Drupal\Core\Config\ConfigEvent $event
   *   The Event to process.
   */
  public function configContext(ConfigEvent $event) {
    $context = $event->getContext();

65 66
    // If there is a language set explicitly in the current context, use it.
    // Otherwise check if there is a user set in the current context,
67 68 69 70 71 72
    // to set the language based on the preferred language of the user.
    // Otherwise set it based on the negotiated interface language.
    if ($language = $context->get('language')) {
      $context->set('locale.language', $language);
    }
    elseif ($account = $context->get('user.account')) {
73
      $context->set('locale.language', language_load($account->getPreferredLangcode()));
74
    }
75
    elseif ($language = $this->languageManager->getLanguage(Language::TYPE_INTERFACE)) {
76 77
      $context->set('locale.language', $language);
    }
78 79
  }

80 81 82
  /**
   * Override configuration values with localized data.
   *
83
   * @param \Drupal\Core\Config\ConfigEvent $event
84 85 86
   *   The Event to process.
   */
  public function configLoad(ConfigEvent $event) {
87 88 89 90 91 92 93 94 95 96 97 98
    $context = $event->getContext();
    if ($language = $context->get('locale.language')) {
      $config = $event->getConfig();
      $locale_name = $this->getLocaleConfigName($config->getName(), $language);
      // Check to see if the config storage has an appropriately named file
      // containing override data.
      if ($override = $event->getConfig()->getStorage()->read($locale_name)) {
        $config->setOverride($override);
      }
    }
  }

99 100 101 102 103 104
  /**
   * Sets the negotiated interface language on the default configuration context.
   *
   * @param \Symfony\Component\HttpKernel\Event\GetResponseEvent $event
   *   Kernel event to respond to.
   */
105
  public function onKernelRequestSetDefaultConfigContextLocale(GetResponseEvent $event) {
106 107 108 109 110
    // Re-initialize the default configuration context to ensure any cached
    // configuration object are reset and can be translated. This will invoke
    // the config context event which will retrieve the negotiated language
    // from the language manager in configContext().
    $this->defaultConfigContext->init();
111 112 113 114 115 116 117
  }

  /**
   * Get configuration name for this language.
   *
   * It will be the same name with a prefix depending on language code:
   * locale.config.LANGCODE.NAME
118 119 120 121 122 123 124
   *
   * @param string $name
   *   The name of the config object.
   * @param \Drupal\Core\Language\Language $language
   *   The language object.
   *
   * @return string
125
   *   The localized config name.
126
   */
127
  public function getLocaleConfigName($name, Language $language) {
128
    return 'locale.config.' . $language->id . '.' . $name;
129 130 131 132 133 134
  }

  /**
   * Implements EventSubscriberInterface::getSubscribedEvents().
   */
  static function getSubscribedEvents() {
135
    $events['config.context'][] = array('configContext', 20);
136
    $events['config.load'][] = array('configLoad', 20);
137 138 139
    // Set the priority above the one from the RouteListener (priority 32)
    // so ensure that the context is cleared before the routing system steps in.
    $events[KernelEvents::REQUEST][] = array('onKernelRequestSetDefaultConfigContextLocale', 48);
140 141 142
    return $events;
  }
}