Aggiornato Composer
This commit is contained in:
@@ -35,8 +35,8 @@ abstract class AbstractSessionHandler implements \SessionHandlerInterface, \Sess
|
||||
public function open($savePath, $sessionName)
|
||||
{
|
||||
$this->sessionName = $sessionName;
|
||||
if (!headers_sent() && !ini_get('session.cache_limiter') && '0' !== ini_get('session.cache_limiter')) {
|
||||
header(sprintf('Cache-Control: max-age=%d, private, must-revalidate', 60 * (int) ini_get('session.cache_expire')));
|
||||
if (!headers_sent() && !\ini_get('session.cache_limiter') && '0' !== \ini_get('session.cache_limiter')) {
|
||||
header(sprintf('Cache-Control: max-age=%d, private, must-revalidate', 60 * (int) \ini_get('session.cache_expire')));
|
||||
}
|
||||
|
||||
return true;
|
||||
@@ -126,7 +126,7 @@ abstract class AbstractSessionHandler implements \SessionHandlerInterface, \Sess
|
||||
#[\ReturnTypeWillChange]
|
||||
public function destroy($sessionId)
|
||||
{
|
||||
if (!headers_sent() && filter_var(ini_get('session.use_cookies'), \FILTER_VALIDATE_BOOLEAN)) {
|
||||
if (!headers_sent() && filter_var(\ini_get('session.use_cookies'), \FILTER_VALIDATE_BOOLEAN)) {
|
||||
if (!$this->sessionName) {
|
||||
throw new \LogicException(sprintf('Session name cannot be empty, did you forget to call "parent::open()" in "%s"?.', static::class));
|
||||
}
|
||||
@@ -141,7 +141,7 @@ abstract class AbstractSessionHandler implements \SessionHandlerInterface, \Sess
|
||||
*/
|
||||
if (null === $cookie || isset($_COOKIE[$this->sessionName])) {
|
||||
if (\PHP_VERSION_ID < 70300) {
|
||||
setcookie($this->sessionName, '', 0, ini_get('session.cookie_path'), ini_get('session.cookie_domain'), filter_var(ini_get('session.cookie_secure'), \FILTER_VALIDATE_BOOLEAN), filter_var(ini_get('session.cookie_httponly'), \FILTER_VALIDATE_BOOLEAN));
|
||||
setcookie($this->sessionName, '', 0, \ini_get('session.cookie_path'), \ini_get('session.cookie_domain'), filter_var(\ini_get('session.cookie_secure'), \FILTER_VALIDATE_BOOLEAN), filter_var(\ini_get('session.cookie_httponly'), \FILTER_VALIDATE_BOOLEAN));
|
||||
} else {
|
||||
$params = session_get_cookie_params();
|
||||
unset($params['lifetime']);
|
||||
|
||||
@@ -77,7 +77,7 @@ class MemcachedSessionHandler extends AbstractSessionHandler
|
||||
#[\ReturnTypeWillChange]
|
||||
public function updateTimestamp($sessionId, $data)
|
||||
{
|
||||
$this->memcached->touch($this->prefix.$sessionId, time() + (int) ($this->ttl ?? ini_get('session.gc_maxlifetime')));
|
||||
$this->memcached->touch($this->prefix.$sessionId, $this->getCompatibleTtl());
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -87,7 +87,20 @@ class MemcachedSessionHandler extends AbstractSessionHandler
|
||||
*/
|
||||
protected function doWrite(string $sessionId, string $data)
|
||||
{
|
||||
return $this->memcached->set($this->prefix.$sessionId, $data, time() + (int) ($this->ttl ?? ini_get('session.gc_maxlifetime')));
|
||||
return $this->memcached->set($this->prefix.$sessionId, $data, $this->getCompatibleTtl());
|
||||
}
|
||||
|
||||
private function getCompatibleTtl(): int
|
||||
{
|
||||
$ttl = (int) ($this->ttl ?? \ini_get('session.gc_maxlifetime'));
|
||||
|
||||
// If the relative TTL that is used exceeds 30 days, memcached will treat the value as Unix time.
|
||||
// We have to convert it to an absolute Unix time at this point, to make sure the TTL is correct.
|
||||
if ($ttl > 60 * 60 * 24 * 30) {
|
||||
$ttl += time();
|
||||
}
|
||||
|
||||
return $ttl;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -121,7 +121,7 @@ class MongoDbSessionHandler extends AbstractSessionHandler
|
||||
*/
|
||||
protected function doWrite(string $sessionId, string $data)
|
||||
{
|
||||
$expiry = new UTCDateTime((time() + (int) ini_get('session.gc_maxlifetime')) * 1000);
|
||||
$expiry = new UTCDateTime((time() + (int) \ini_get('session.gc_maxlifetime')) * 1000);
|
||||
|
||||
$fields = [
|
||||
$this->options['time_field'] => new UTCDateTime(),
|
||||
@@ -144,7 +144,7 @@ class MongoDbSessionHandler extends AbstractSessionHandler
|
||||
#[\ReturnTypeWillChange]
|
||||
public function updateTimestamp($sessionId, $data)
|
||||
{
|
||||
$expiry = new UTCDateTime((time() + (int) ini_get('session.gc_maxlifetime')) * 1000);
|
||||
$expiry = new UTCDateTime((time() + (int) \ini_get('session.gc_maxlifetime')) * 1000);
|
||||
|
||||
$this->getCollection()->updateOne(
|
||||
[$this->options['id_field'] => $sessionId],
|
||||
|
||||
@@ -19,19 +19,19 @@ namespace Symfony\Component\HttpFoundation\Session\Storage\Handler;
|
||||
class NativeFileSessionHandler extends \SessionHandler
|
||||
{
|
||||
/**
|
||||
* @param string $savePath Path of directory to save session files
|
||||
* Default null will leave setting as defined by PHP.
|
||||
* '/path', 'N;/path', or 'N;octal-mode;/path
|
||||
* @param string|null $savePath Path of directory to save session files
|
||||
* Default null will leave setting as defined by PHP.
|
||||
* '/path', 'N;/path', or 'N;octal-mode;/path
|
||||
*
|
||||
* @see https://php.net/session.configuration#ini.session.save-path for further details.
|
||||
*
|
||||
* @throws \InvalidArgumentException On invalid $savePath
|
||||
* @throws \RuntimeException When failing to create the save directory
|
||||
*/
|
||||
public function __construct(string $savePath = null)
|
||||
public function __construct(?string $savePath = null)
|
||||
{
|
||||
if (null === $savePath) {
|
||||
$savePath = ini_get('session.save_path');
|
||||
$savePath = \ini_get('session.save_path');
|
||||
}
|
||||
|
||||
$baseDir = $savePath;
|
||||
@@ -49,7 +49,11 @@ class NativeFileSessionHandler extends \SessionHandler
|
||||
throw new \RuntimeException(sprintf('Session Storage was not able to create directory "%s".', $baseDir));
|
||||
}
|
||||
|
||||
ini_set('session.save_path', $savePath);
|
||||
ini_set('session.save_handler', 'files');
|
||||
if ($savePath !== \ini_get('session.save_path')) {
|
||||
ini_set('session.save_path', $savePath);
|
||||
}
|
||||
if ('files' !== \ini_get('session.save_handler')) {
|
||||
ini_set('session.save_handler', 'files');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -112,16 +112,16 @@ class PdoSessionHandler extends AbstractSessionHandler
|
||||
/**
|
||||
* Username when lazy-connect.
|
||||
*
|
||||
* @var string
|
||||
* @var string|null
|
||||
*/
|
||||
private $username = '';
|
||||
private $username = null;
|
||||
|
||||
/**
|
||||
* Password when lazy-connect.
|
||||
*
|
||||
* @var string
|
||||
* @var string|null
|
||||
*/
|
||||
private $password = '';
|
||||
private $password = null;
|
||||
|
||||
/**
|
||||
* Connection options when lazy-connect.
|
||||
@@ -344,7 +344,7 @@ class PdoSessionHandler extends AbstractSessionHandler
|
||||
*/
|
||||
protected function doWrite(string $sessionId, string $data)
|
||||
{
|
||||
$maxlifetime = (int) ini_get('session.gc_maxlifetime');
|
||||
$maxlifetime = (int) \ini_get('session.gc_maxlifetime');
|
||||
|
||||
try {
|
||||
// We use a single MERGE SQL query when supported by the database.
|
||||
@@ -391,14 +391,14 @@ class PdoSessionHandler extends AbstractSessionHandler
|
||||
#[\ReturnTypeWillChange]
|
||||
public function updateTimestamp($sessionId, $data)
|
||||
{
|
||||
$expiry = time() + (int) ini_get('session.gc_maxlifetime');
|
||||
$expiry = time() + (int) \ini_get('session.gc_maxlifetime');
|
||||
|
||||
try {
|
||||
$updateStmt = $this->pdo->prepare(
|
||||
"UPDATE $this->table SET $this->lifetimeCol = :expiry, $this->timeCol = :time WHERE $this->idCol = :id"
|
||||
);
|
||||
$updateStmt->bindParam(':id', $sessionId, \PDO::PARAM_STR);
|
||||
$updateStmt->bindParam(':expiry', $expiry, \PDO::PARAM_INT);
|
||||
$updateStmt->bindValue(':id', $sessionId, \PDO::PARAM_STR);
|
||||
$updateStmt->bindValue(':expiry', $expiry, \PDO::PARAM_INT);
|
||||
$updateStmt->bindValue(':time', time(), \PDO::PARAM_INT);
|
||||
$updateStmt->execute();
|
||||
} catch (\PDOException $e) {
|
||||
@@ -530,8 +530,8 @@ class PdoSessionHandler extends AbstractSessionHandler
|
||||
return $dsn;
|
||||
}
|
||||
}
|
||||
// If "unix_socket" is not in the query, we continue with the same process as pgsql
|
||||
// no break
|
||||
// If "unix_socket" is not in the query, we continue with the same process as pgsql
|
||||
// no break
|
||||
case 'pgsql':
|
||||
$dsn ?? $dsn = 'pgsql:';
|
||||
|
||||
@@ -687,7 +687,7 @@ class PdoSessionHandler extends AbstractSessionHandler
|
||||
throw new \RuntimeException('Failed to read session: INSERT reported a duplicate id but next SELECT did not return any data.');
|
||||
}
|
||||
|
||||
if (!filter_var(ini_get('session.use_strict_mode'), \FILTER_VALIDATE_BOOLEAN) && self::LOCK_TRANSACTIONAL === $this->lockMode && 'sqlite' !== $this->driver) {
|
||||
if (!filter_var(\ini_get('session.use_strict_mode'), \FILTER_VALIDATE_BOOLEAN) && self::LOCK_TRANSACTIONAL === $this->lockMode && 'sqlite' !== $this->driver) {
|
||||
// In strict mode, session fixation is not possible: new sessions always start with a unique
|
||||
// random id, so that concurrency is not possible and this code path can be skipped.
|
||||
// Exclusive-reading of non-existent rows does not block, so we need to do an insert to block
|
||||
@@ -935,7 +935,7 @@ class PdoSessionHandler extends AbstractSessionHandler
|
||||
protected function getConnection()
|
||||
{
|
||||
if (null === $this->pdo) {
|
||||
$this->connect($this->dsn ?: ini_get('session.save_path'));
|
||||
$this->connect($this->dsn ?: \ini_get('session.save_path'));
|
||||
}
|
||||
|
||||
return $this->pdo;
|
||||
|
||||
@@ -79,7 +79,7 @@ class RedisSessionHandler extends AbstractSessionHandler
|
||||
*/
|
||||
protected function doWrite(string $sessionId, string $data): bool
|
||||
{
|
||||
$result = $this->redis->setEx($this->prefix.$sessionId, (int) ($this->ttl ?? ini_get('session.gc_maxlifetime')), $data);
|
||||
$result = $this->redis->setEx($this->prefix.$sessionId, (int) ($this->ttl ?? \ini_get('session.gc_maxlifetime')), $data);
|
||||
|
||||
return $result && !$result instanceof ErrorInterface;
|
||||
}
|
||||
@@ -132,6 +132,6 @@ class RedisSessionHandler extends AbstractSessionHandler
|
||||
#[\ReturnTypeWillChange]
|
||||
public function updateTimestamp($sessionId, $data)
|
||||
{
|
||||
return (bool) $this->redis->expire($this->prefix.$sessionId, (int) ($this->ttl ?? ini_get('session.gc_maxlifetime')));
|
||||
return (bool) $this->redis->expire($this->prefix.$sessionId, (int) ($this->ttl ?? \ini_get('session.gc_maxlifetime')));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -11,7 +11,10 @@
|
||||
|
||||
namespace Symfony\Component\HttpFoundation\Session\Storage\Handler;
|
||||
|
||||
use Doctrine\DBAL\Configuration;
|
||||
use Doctrine\DBAL\DriverManager;
|
||||
use Doctrine\DBAL\Schema\DefaultSchemaManagerFactory;
|
||||
use Doctrine\DBAL\Tools\DsnParser;
|
||||
use Symfony\Component\Cache\Adapter\AbstractAdapter;
|
||||
use Symfony\Component\Cache\Traits\RedisClusterProxy;
|
||||
use Symfony\Component\Cache\Traits\RedisProxy;
|
||||
@@ -60,7 +63,7 @@ class SessionHandlerFactory
|
||||
case str_starts_with($connection, 'rediss:'):
|
||||
case str_starts_with($connection, 'memcached:'):
|
||||
if (!class_exists(AbstractAdapter::class)) {
|
||||
throw new \InvalidArgumentException(sprintf('Unsupported DSN "%s". Try running "composer require symfony/cache".', $connection));
|
||||
throw new \InvalidArgumentException('Unsupported Redis or Memcached DSN. Try running "composer require symfony/cache".');
|
||||
}
|
||||
$handlerClass = str_starts_with($connection, 'memcached:') ? MemcachedSessionHandler::class : RedisSessionHandler::class;
|
||||
$connection = AbstractAdapter::createConnection($connection, ['lazy' => true]);
|
||||
@@ -69,9 +72,18 @@ class SessionHandlerFactory
|
||||
|
||||
case str_starts_with($connection, 'pdo_oci://'):
|
||||
if (!class_exists(DriverManager::class)) {
|
||||
throw new \InvalidArgumentException(sprintf('Unsupported DSN "%s". Try running "composer require doctrine/dbal".', $connection));
|
||||
throw new \InvalidArgumentException('Unsupported PDO OCI DSN. Try running "composer require doctrine/dbal".');
|
||||
}
|
||||
$connection = DriverManager::getConnection(['url' => $connection])->getWrappedConnection();
|
||||
$connection[3] = '-';
|
||||
$params = class_exists(DsnParser::class) ? (new DsnParser())->parse($connection) : ['url' => $connection];
|
||||
$config = new Configuration();
|
||||
if (class_exists(DefaultSchemaManagerFactory::class)) {
|
||||
$config->setSchemaManagerFactory(new DefaultSchemaManagerFactory());
|
||||
}
|
||||
|
||||
$connection = DriverManager::getConnection($params, $config);
|
||||
// The condition should be removed once support for DBAL <3.3 is dropped
|
||||
$connection = method_exists($connection, 'getNativeConnection') ? $connection->getNativeConnection() : $connection->getWrappedConnection();
|
||||
// no break;
|
||||
|
||||
case str_starts_with($connection, 'mssql://'):
|
||||
|
||||
@@ -30,6 +30,16 @@ class StrictSessionHandler extends AbstractSessionHandler
|
||||
$this->handler = $handler;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if this handler wraps an internal PHP session save handler using \SessionHandler.
|
||||
*
|
||||
* @internal
|
||||
*/
|
||||
public function isWrapper(): bool
|
||||
{
|
||||
return $this->handler instanceof \SessionHandler;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return bool
|
||||
*/
|
||||
|
||||
@@ -95,12 +95,12 @@ class MetadataBag implements SessionBagInterface
|
||||
/**
|
||||
* Stamps a new session's metadata.
|
||||
*
|
||||
* @param int $lifetime Sets the cookie lifetime for the session cookie. A null value
|
||||
* will leave the system settings unchanged, 0 sets the cookie
|
||||
* to expire with browser session. Time is in seconds, and is
|
||||
* not a Unix timestamp.
|
||||
* @param int|null $lifetime Sets the cookie lifetime for the session cookie. A null value
|
||||
* will leave the system settings unchanged, 0 sets the cookie
|
||||
* to expire with browser session. Time is in seconds, and is
|
||||
* not a Unix timestamp.
|
||||
*/
|
||||
public function stampNew(int $lifetime = null)
|
||||
public function stampNew(?int $lifetime = null)
|
||||
{
|
||||
$this->stampCreated($lifetime);
|
||||
}
|
||||
@@ -158,10 +158,10 @@ class MetadataBag implements SessionBagInterface
|
||||
$this->name = $name;
|
||||
}
|
||||
|
||||
private function stampCreated(int $lifetime = null): void
|
||||
private function stampCreated(?int $lifetime = null): void
|
||||
{
|
||||
$timeStamp = time();
|
||||
$this->meta[self::CREATED] = $this->meta[self::UPDATED] = $this->lastUsed = $timeStamp;
|
||||
$this->meta[self::LIFETIME] = $lifetime ?? (int) ini_get('session.cookie_lifetime');
|
||||
$this->meta[self::LIFETIME] = $lifetime ?? (int) \ini_get('session.cookie_lifetime');
|
||||
}
|
||||
}
|
||||
|
||||
@@ -62,7 +62,7 @@ class MockArraySessionStorage implements SessionStorageInterface
|
||||
*/
|
||||
protected $bags = [];
|
||||
|
||||
public function __construct(string $name = 'MOCKSESSID', MetadataBag $metaBag = null)
|
||||
public function __construct(string $name = 'MOCKSESSID', ?MetadataBag $metaBag = null)
|
||||
{
|
||||
$this->name = $name;
|
||||
$this->setMetadataBag($metaBag);
|
||||
@@ -94,7 +94,7 @@ class MockArraySessionStorage implements SessionStorageInterface
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function regenerate(bool $destroy = false, int $lifetime = null)
|
||||
public function regenerate(bool $destroy = false, ?int $lifetime = null)
|
||||
{
|
||||
if (!$this->started) {
|
||||
$this->start();
|
||||
@@ -204,7 +204,7 @@ class MockArraySessionStorage implements SessionStorageInterface
|
||||
return $this->started;
|
||||
}
|
||||
|
||||
public function setMetadataBag(MetadataBag $bag = null)
|
||||
public function setMetadataBag(?MetadataBag $bag = null)
|
||||
{
|
||||
if (null === $bag) {
|
||||
$bag = new MetadataBag();
|
||||
|
||||
@@ -30,7 +30,7 @@ class MockFileSessionStorage extends MockArraySessionStorage
|
||||
/**
|
||||
* @param string|null $savePath Path of directory to save session files
|
||||
*/
|
||||
public function __construct(string $savePath = null, string $name = 'MOCKSESSID', MetadataBag $metaBag = null)
|
||||
public function __construct(?string $savePath = null, string $name = 'MOCKSESSID', ?MetadataBag $metaBag = null)
|
||||
{
|
||||
if (null === $savePath) {
|
||||
$savePath = sys_get_temp_dir();
|
||||
@@ -68,7 +68,7 @@ class MockFileSessionStorage extends MockArraySessionStorage
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function regenerate(bool $destroy = false, int $lifetime = null)
|
||||
public function regenerate(bool $destroy = false, ?int $lifetime = null)
|
||||
{
|
||||
if (!$this->started) {
|
||||
$this->start();
|
||||
|
||||
@@ -28,7 +28,7 @@ class MockFileSessionStorageFactory implements SessionStorageFactoryInterface
|
||||
/**
|
||||
* @see MockFileSessionStorage constructor.
|
||||
*/
|
||||
public function __construct(string $savePath = null, string $name = 'MOCKSESSID', MetadataBag $metaBag = null)
|
||||
public function __construct(?string $savePath = null, string $name = 'MOCKSESSID', ?MetadataBag $metaBag = null)
|
||||
{
|
||||
$this->savePath = $savePath;
|
||||
$this->name = $name;
|
||||
|
||||
@@ -97,7 +97,7 @@ class NativeSessionStorage implements SessionStorageInterface
|
||||
*
|
||||
* @param AbstractProxy|\SessionHandlerInterface|null $handler
|
||||
*/
|
||||
public function __construct(array $options = [], $handler = null, MetadataBag $metaBag = null)
|
||||
public function __construct(array $options = [], $handler = null, ?MetadataBag $metaBag = null)
|
||||
{
|
||||
if (!\extension_loaded('session')) {
|
||||
throw new \LogicException('PHP extension "session" is required.');
|
||||
@@ -141,10 +141,46 @@ class NativeSessionStorage implements SessionStorageInterface
|
||||
throw new \RuntimeException('Failed to start the session: already started by PHP.');
|
||||
}
|
||||
|
||||
if (filter_var(ini_get('session.use_cookies'), \FILTER_VALIDATE_BOOLEAN) && headers_sent($file, $line)) {
|
||||
if (filter_var(\ini_get('session.use_cookies'), \FILTER_VALIDATE_BOOLEAN) && headers_sent($file, $line)) {
|
||||
throw new \RuntimeException(sprintf('Failed to start the session because headers have already been sent by "%s" at line %d.', $file, $line));
|
||||
}
|
||||
|
||||
$sessionId = $_COOKIE[session_name()] ?? null;
|
||||
/*
|
||||
* Explanation of the session ID regular expression: `/^[a-zA-Z0-9,-]{22,250}$/`.
|
||||
*
|
||||
* ---------- Part 1
|
||||
*
|
||||
* The part `[a-zA-Z0-9,-]` is related to the PHP ini directive `session.sid_bits_per_character` defined as 6.
|
||||
* See https://www.php.net/manual/en/session.configuration.php#ini.session.sid-bits-per-character.
|
||||
* Allowed values are integers such as:
|
||||
* - 4 for range `a-f0-9`
|
||||
* - 5 for range `a-v0-9`
|
||||
* - 6 for range `a-zA-Z0-9,-`
|
||||
*
|
||||
* ---------- Part 2
|
||||
*
|
||||
* The part `{22,250}` is related to the PHP ini directive `session.sid_length`.
|
||||
* See https://www.php.net/manual/en/session.configuration.php#ini.session.sid-length.
|
||||
* Allowed values are integers between 22 and 256, but we use 250 for the max.
|
||||
*
|
||||
* Where does the 250 come from?
|
||||
* - The length of Windows and Linux filenames is limited to 255 bytes. Then the max must not exceed 255.
|
||||
* - The session filename prefix is `sess_`, a 5 bytes string. Then the max must not exceed 255 - 5 = 250.
|
||||
*
|
||||
* ---------- Conclusion
|
||||
*
|
||||
* The parts 1 and 2 prevent the warning below:
|
||||
* `PHP Warning: SessionHandler::read(): Session ID is too long or contains illegal characters. Only the A-Z, a-z, 0-9, "-", and "," characters are allowed.`
|
||||
*
|
||||
* The part 2 prevents the warning below:
|
||||
* `PHP Warning: SessionHandler::read(): open(filepath, O_RDWR) failed: No such file or directory (2).`
|
||||
*/
|
||||
if ($sessionId && $this->saveHandler instanceof AbstractProxy && 'files' === $this->saveHandler->getSaveHandlerName() && !preg_match('/^[a-zA-Z0-9,-]{22,250}$/', $sessionId)) {
|
||||
// the session ID in the header is invalid, create a new one
|
||||
session_id(session_create_id());
|
||||
}
|
||||
|
||||
// ok to try and start the session
|
||||
if (!session_start()) {
|
||||
throw new \RuntimeException('Failed to start the session.');
|
||||
@@ -197,7 +233,7 @@ class NativeSessionStorage implements SessionStorageInterface
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function regenerate(bool $destroy = false, int $lifetime = null)
|
||||
public function regenerate(bool $destroy = false, ?int $lifetime = null)
|
||||
{
|
||||
// Cannot regenerate the session ID for non-active sessions.
|
||||
if (\PHP_SESSION_ACTIVE !== session_status()) {
|
||||
@@ -208,7 +244,7 @@ class NativeSessionStorage implements SessionStorageInterface
|
||||
return false;
|
||||
}
|
||||
|
||||
if (null !== $lifetime && $lifetime != ini_get('session.cookie_lifetime')) {
|
||||
if (null !== $lifetime && $lifetime != \ini_get('session.cookie_lifetime')) {
|
||||
$this->save();
|
||||
ini_set('session.cookie_lifetime', $lifetime);
|
||||
$this->start();
|
||||
@@ -243,7 +279,7 @@ class NativeSessionStorage implements SessionStorageInterface
|
||||
unset($_SESSION[$key]);
|
||||
}
|
||||
}
|
||||
if ([$key = $this->metadataBag->getStorageKey()] === array_keys($_SESSION)) {
|
||||
if ($_SESSION && [$key = $this->metadataBag->getStorageKey()] === array_keys($_SESSION)) {
|
||||
unset($_SESSION[$key]);
|
||||
}
|
||||
|
||||
@@ -319,7 +355,7 @@ class NativeSessionStorage implements SessionStorageInterface
|
||||
return $this->bags[$name];
|
||||
}
|
||||
|
||||
public function setMetadataBag(MetadataBag $metaBag = null)
|
||||
public function setMetadataBag(?MetadataBag $metaBag = null)
|
||||
{
|
||||
if (null === $metaBag) {
|
||||
$metaBag = new MetadataBag();
|
||||
@@ -419,9 +455,10 @@ class NativeSessionStorage implements SessionStorageInterface
|
||||
*/
|
||||
public function setSaveHandler($saveHandler = null)
|
||||
{
|
||||
if (!$saveHandler instanceof AbstractProxy &&
|
||||
!$saveHandler instanceof \SessionHandlerInterface &&
|
||||
null !== $saveHandler) {
|
||||
if (!$saveHandler instanceof AbstractProxy
|
||||
&& !$saveHandler instanceof \SessionHandlerInterface
|
||||
&& null !== $saveHandler
|
||||
) {
|
||||
throw new \InvalidArgumentException('Must be instance of AbstractProxy; implement \SessionHandlerInterface; or be null.');
|
||||
}
|
||||
|
||||
@@ -450,7 +487,7 @@ class NativeSessionStorage implements SessionStorageInterface
|
||||
* PHP takes the return value from the read() handler, unserializes it
|
||||
* and populates $_SESSION with the result automatically.
|
||||
*/
|
||||
protected function loadSession(array &$session = null)
|
||||
protected function loadSession(?array &$session = null)
|
||||
{
|
||||
if (null === $session) {
|
||||
$session = &$_SESSION;
|
||||
|
||||
@@ -29,7 +29,7 @@ class NativeSessionStorageFactory implements SessionStorageFactoryInterface
|
||||
/**
|
||||
* @see NativeSessionStorage constructor.
|
||||
*/
|
||||
public function __construct(array $options = [], $handler = null, MetadataBag $metaBag = null, bool $secure = false)
|
||||
public function __construct(array $options = [], $handler = null, ?MetadataBag $metaBag = null, bool $secure = false)
|
||||
{
|
||||
$this->options = $options;
|
||||
$this->handler = $handler;
|
||||
|
||||
@@ -23,7 +23,7 @@ class PhpBridgeSessionStorage extends NativeSessionStorage
|
||||
/**
|
||||
* @param AbstractProxy|\SessionHandlerInterface|null $handler
|
||||
*/
|
||||
public function __construct($handler = null, MetadataBag $metaBag = null)
|
||||
public function __construct($handler = null, ?MetadataBag $metaBag = null)
|
||||
{
|
||||
if (!\extension_loaded('session')) {
|
||||
throw new \LogicException('PHP extension "session" is required.');
|
||||
|
||||
@@ -28,7 +28,7 @@ class PhpBridgeSessionStorageFactory implements SessionStorageFactoryInterface
|
||||
/**
|
||||
* @see PhpBridgeSessionStorage constructor.
|
||||
*/
|
||||
public function __construct($handler = null, MetadataBag $metaBag = null, bool $secure = false)
|
||||
public function __construct($handler = null, ?MetadataBag $metaBag = null, bool $secure = false)
|
||||
{
|
||||
$this->handler = $handler;
|
||||
$this->metaBag = $metaBag;
|
||||
|
||||
@@ -11,6 +11,8 @@
|
||||
|
||||
namespace Symfony\Component\HttpFoundation\Session\Storage\Proxy;
|
||||
|
||||
use Symfony\Component\HttpFoundation\Session\Storage\Handler\StrictSessionHandler;
|
||||
|
||||
/**
|
||||
* @author Drak <drak@zikula.org>
|
||||
*/
|
||||
@@ -22,7 +24,7 @@ class SessionHandlerProxy extends AbstractProxy implements \SessionHandlerInterf
|
||||
{
|
||||
$this->handler = $handler;
|
||||
$this->wrapper = $handler instanceof \SessionHandler;
|
||||
$this->saveHandlerName = $this->wrapper ? ini_get('session.save_handler') : 'user';
|
||||
$this->saveHandlerName = $this->wrapper || ($handler instanceof StrictSessionHandler && $handler->isWrapper()) ? \ini_get('session.save_handler') : 'user';
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -80,17 +80,17 @@ interface SessionStorageInterface
|
||||
* Otherwise session data could get lost again for concurrent requests with the
|
||||
* new ID. One result could be that you get logged out after just logging in.
|
||||
*
|
||||
* @param bool $destroy Destroy session when regenerating?
|
||||
* @param int $lifetime Sets the cookie lifetime for the session cookie. A null value
|
||||
* will leave the system settings unchanged, 0 sets the cookie
|
||||
* to expire with browser session. Time is in seconds, and is
|
||||
* not a Unix timestamp.
|
||||
* @param bool $destroy Destroy session when regenerating?
|
||||
* @param int|null $lifetime Sets the cookie lifetime for the session cookie. A null value
|
||||
* will leave the system settings unchanged, 0 sets the cookie
|
||||
* to expire with browser session. Time is in seconds, and is
|
||||
* not a Unix timestamp.
|
||||
*
|
||||
* @return bool
|
||||
*
|
||||
* @throws \RuntimeException If an error occurs while regenerating this storage
|
||||
*/
|
||||
public function regenerate(bool $destroy = false, int $lifetime = null);
|
||||
public function regenerate(bool $destroy = false, ?int $lifetime = null);
|
||||
|
||||
/**
|
||||
* Force the session to be saved and closed.
|
||||
|
||||
Reference in New Issue
Block a user