[ Index ]

PHP Cross Reference of Joomla 4.2.2 documentation

title

Body

[close]

/libraries/src/Service/Provider/ -> Session.php (source)

   1  <?php
   2  
   3  /**
   4   * Joomla! Content Management System
   5   *
   6   * @copyright   (C) 2018 Open Source Matters, Inc. <https://www.joomla.org>
   7   * @license     GNU General Public License version 2 or later; see LICENSE
   8   */
   9  
  10  namespace Joomla\CMS\Service\Provider;
  11  
  12  use Joomla\CMS\Application\AdministratorApplication;
  13  use Joomla\CMS\Application\ApplicationHelper;
  14  use Joomla\CMS\Application\CMSApplicationInterface;
  15  use Joomla\CMS\Application\ConsoleApplication;
  16  use Joomla\CMS\Application\SiteApplication;
  17  use Joomla\CMS\Factory;
  18  use Joomla\CMS\Installation\Application\InstallationApplication;
  19  use Joomla\CMS\Session\EventListener\MetadataManagerListener;
  20  use Joomla\CMS\Session\MetadataManager;
  21  use Joomla\CMS\Session\SessionFactory;
  22  use Joomla\CMS\Session\SessionManager;
  23  use Joomla\CMS\Session\Storage\JoomlaStorage;
  24  use Joomla\Database\DatabaseInterface;
  25  use Joomla\DI\Container;
  26  use Joomla\DI\Exception\DependencyResolutionException;
  27  use Joomla\DI\ServiceProviderInterface;
  28  use Joomla\Event\DispatcherInterface;
  29  use Joomla\Event\LazyServiceEventListener;
  30  use Joomla\Event\Priority;
  31  use Joomla\Registry\Registry;
  32  use Joomla\Session\HandlerInterface;
  33  use Joomla\Session\SessionEvents;
  34  use Joomla\Session\SessionInterface;
  35  use Joomla\Session\Storage\RuntimeStorage;
  36  use Joomla\Session\StorageInterface;
  37  
  38  // phpcs:disable PSR1.Files.SideEffects
  39  \defined('JPATH_PLATFORM') or die;
  40  // phpcs:enable PSR1.Files.SideEffects
  41  
  42  /**
  43   * Service provider for the application's session dependency
  44   *
  45   * @since  4.0.0
  46   */
  47  class Session implements ServiceProviderInterface
  48  {
  49      /**
  50       * Registers the service provider with a DI container.
  51       *
  52       * @param   Container  $container  The DI container.
  53       *
  54       * @return  void
  55       *
  56       * @since   4.0.0
  57       */
  58      public function register(Container $container)
  59      {
  60          $container->share(
  61              'session.web.administrator',
  62              function (Container $container) {
  63                  /** @var Registry $config */
  64                  $config = $container->get('config');
  65                  $app    = Factory::getApplication();
  66  
  67                  // Generate a session name.
  68                  $name = ApplicationHelper::getHash($config->get('session_name', AdministratorApplication::class));
  69  
  70                  // Calculate the session lifetime.
  71                  $lifetime = $config->get('lifetime') ? $config->get('lifetime') * 60 : 900;
  72  
  73                  // Initialize the options for the Session object.
  74                  $options = [
  75                      'name'   => $name,
  76                      'expire' => $lifetime,
  77                  ];
  78  
  79                  if ($config->get('force_ssl') >= 1) {
  80                      $options['force_ssl'] = true;
  81                  }
  82  
  83                  $handler = $container->get('session.factory')->createSessionHandler($options);
  84  
  85                  if (!$container->has('session.handler')) {
  86                      $this->registerSessionHandlerAsService($container, $handler);
  87                  }
  88  
  89                  return $this->buildSession(
  90                      new JoomlaStorage($app->input, $handler, $options),
  91                      $app,
  92                      $container->get(DispatcherInterface::class),
  93                      $options
  94                  );
  95              },
  96              true
  97          );
  98  
  99          $container->share(
 100              'session.web.installation',
 101              function (Container $container) {
 102                  /** @var Registry $config */
 103                  $config = $container->get('config');
 104                  $app    = Factory::getApplication();
 105  
 106                  /**
 107                   * Session handler for the session is always filesystem so it doesn't flip to the database after
 108                   * configuration.php has been written to
 109                   */
 110                  $config->set('session_handler', 'filesystem');
 111  
 112                  /**
 113                   * Generate a session name - unlike all the other apps we don't have either a secret or a session name
 114                   * (that's not the app name) until we complete installation which then leads to us dropping things like
 115                   * language preferences after installation as the app refreshes.
 116                   */
 117                  $name = md5(serialize(JPATH_ROOT . InstallationApplication::class));
 118  
 119                  // Calculate the session lifetime.
 120                  $lifetime = $config->get('lifetime') ? $config->get('lifetime') * 60 : 900;
 121  
 122                  // Initialize the options for the Session object.
 123                  $options = [
 124                      'name'   => $name,
 125                      'expire' => $lifetime,
 126                  ];
 127  
 128                  $handler = $container->get('session.factory')->createSessionHandler($options);
 129  
 130                  if (!$container->has('session.handler')) {
 131                      $this->registerSessionHandlerAsService($container, $handler);
 132                  }
 133  
 134                  return $this->buildSession(
 135                      new JoomlaStorage($app->input, $handler),
 136                      $app,
 137                      $container->get(DispatcherInterface::class),
 138                      $options
 139                  );
 140              },
 141              true
 142          );
 143  
 144          $container->share(
 145              'session.web.site',
 146              function (Container $container) {
 147                  /** @var Registry $config */
 148                  $config = $container->get('config');
 149                  $app    = Factory::getApplication();
 150  
 151                  // Generate a session name.
 152                  $name = ApplicationHelper::getHash($config->get('session_name', SiteApplication::class));
 153  
 154                  // Calculate the session lifetime.
 155                  $lifetime = $config->get('lifetime') ? $config->get('lifetime') * 60 : 900;
 156  
 157                  // Initialize the options for the Session object.
 158                  $options = [
 159                      'name'   => $name,
 160                      'expire' => $lifetime,
 161                  ];
 162  
 163                  if ($config->get('force_ssl') == 2) {
 164                      $options['force_ssl'] = true;
 165                  }
 166  
 167                  $handler = $container->get('session.factory')->createSessionHandler($options);
 168  
 169                  if (!$container->has('session.handler')) {
 170                      $this->registerSessionHandlerAsService($container, $handler);
 171                  }
 172  
 173                  return $this->buildSession(
 174                      new JoomlaStorage($app->input, $handler, $options),
 175                      $app,
 176                      $container->get(DispatcherInterface::class),
 177                      $options
 178                  );
 179              },
 180              true
 181          );
 182  
 183          $container->share(
 184              'session.cli',
 185              function (Container $container) {
 186                  /** @var Registry $config */
 187                  $config = $container->get('config');
 188                  $app    = Factory::getApplication();
 189  
 190                  // Generate a session name.
 191                  $name = ApplicationHelper::getHash($config->get('session_name', ConsoleApplication::class));
 192  
 193                  // Calculate the session lifetime.
 194                  $lifetime = $config->get('lifetime') ? $config->get('lifetime') * 60 : 900;
 195  
 196                  // Initialize the options for the Session object.
 197                  $options = [
 198                      'name'   => $name,
 199                      'expire' => $lifetime,
 200                  ];
 201  
 202                  // Unlike the web apps, we will only toggle the force SSL setting based on it being enabled and not based on client
 203                  if ($config->get('force_ssl') >= 1) {
 204                      $options['force_ssl'] = true;
 205                  }
 206  
 207                  $handler = $container->get('session.factory')->createSessionHandler($options);
 208  
 209                  if (!$container->has('session.handler')) {
 210                      $this->registerSessionHandlerAsService($container, $handler);
 211                  }
 212  
 213                  return $this->buildSession(
 214                      new RuntimeStorage(),
 215                      $app,
 216                      $container->get(DispatcherInterface::class),
 217                      $options
 218                  );
 219              },
 220              true
 221          );
 222  
 223          $container->alias(SessionFactory::class, 'session.factory')
 224              ->share(
 225                  'session.factory',
 226                  function (Container $container) {
 227                      $factory = new SessionFactory();
 228                      $factory->setContainer($container);
 229  
 230                      return $factory;
 231                  },
 232                  true
 233              );
 234  
 235          $container->alias(SessionManager::class, 'session.manager')
 236              ->share(
 237                  'session.manager',
 238                  function (Container $container) {
 239                      if (!$container->has('session.handler')) {
 240                          throw new DependencyResolutionException(
 241                              'The "session.handler" service has not been created, make sure you have created the "session" service first.'
 242                          );
 243                      }
 244  
 245                      return new SessionManager($container->get('session.handler'));
 246                  },
 247                  true
 248              );
 249  
 250          $container->alias(MetadataManager::class, 'session.metadata_manager')
 251              ->share(
 252                  'session.metadata_manager',
 253                  function (Container $container) {
 254                      /*
 255                       * Normally we should inject the application as a dependency via $container->get() however there is not
 256                       * a 'app' or CMSApplicationInterface::class key for the primary application of the request so we need to
 257                       * rely on the application having been injected to the global Factory otherwise we cannot build the service
 258                       */
 259                      if (!Factory::$application) {
 260                          throw new DependencyResolutionException(
 261                              sprintf(
 262                                  'Creating the "session.metadata_manager" service requires %s::$application be initialised.',
 263                                  Factory::class
 264                              )
 265                          );
 266                      }
 267  
 268                      return new MetadataManager(Factory::$application, $container->get(DatabaseInterface::class));
 269                  },
 270                  true
 271              );
 272  
 273          $container->alias(MetadataManagerListener::class, 'session.event_listener.metadata_manager')
 274              ->share(
 275                  'session.event_listener.metadata_manager',
 276                  function (Container $container) {
 277                      return new MetadataManagerListener($container->get(MetadataManager::class), $container->get('config'));
 278                  },
 279                  true
 280              );
 281  
 282          $listener = new LazyServiceEventListener($container, 'session.event_listener.metadata_manager', 'onAfterSessionStart');
 283  
 284          /** @var DispatcherInterface $dispatcher */
 285          $dispatcher = $container->get(DispatcherInterface::class);
 286          $dispatcher->addListener(SessionEvents::START, $listener);
 287      }
 288  
 289      /**
 290       * Build the root session service
 291       *
 292       * @param   StorageInterface         $storage     The session storage engine.
 293       * @param   CMSApplicationInterface  $app         The application instance.
 294       * @param   DispatcherInterface      $dispatcher  The event dispatcher.
 295       * @param   array                    $options     The configured session options.
 296       *
 297       * @return  SessionInterface
 298       *
 299       * @since   4.0.0
 300       */
 301      private function buildSession(
 302          StorageInterface $storage,
 303          CMSApplicationInterface $app,
 304          DispatcherInterface $dispatcher,
 305          array $options
 306      ): SessionInterface {
 307          $input = $app->input;
 308  
 309          if (method_exists($app, 'afterSessionStart')) {
 310              $dispatcher->addListener(SessionEvents::START, [$app, 'afterSessionStart'], Priority::HIGH);
 311          }
 312  
 313          $session = new \Joomla\CMS\Session\Session($storage, $dispatcher, $options);
 314  
 315          return $session;
 316      }
 317  
 318      /**
 319       * Registers the session handler as a service
 320       *
 321       * @param   Container                 $container       The container to register the service to.
 322       * @param   \SessionHandlerInterface  $sessionHandler  The session handler.
 323       *
 324       * @return  void
 325       *
 326       * @since   4.0.0
 327       */
 328      private function registerSessionHandlerAsService(Container $container, \SessionHandlerInterface $sessionHandler): void
 329      {
 330          // Alias the session handler to the core SessionHandlerInterface for improved autowiring and discoverability
 331          $container->alias(\SessionHandlerInterface::class, 'session.handler')
 332              ->share(
 333                  'session.handler',
 334                  $sessionHandler,
 335                  true
 336              );
 337  
 338          // If the session handler implements the extended interface, register an alias for that as well
 339          if ($sessionHandler instanceof HandlerInterface) {
 340              $container->alias(HandlerInterface::class, 'session.handler');
 341          }
 342      }
 343  }


Generated: Wed Sep 7 05:41:13 2022 Chilli.vc Blog - For Webmaster,Blog-Writer,System Admin and Domainer