-
-
Notifications
You must be signed in to change notification settings - Fork 3
/
Copy pathSession.php
executable file
·119 lines (106 loc) · 3.73 KB
/
Session.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
<?php
/**
* Copyright 2021 Jeremy Presutti <Jeremy@Presutti.us>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
declare(strict_types=1);
namespace Feast\Session;
use Feast\Exception\ResponseException;
use Feast\Exception\SessionNotStartedException;
use Feast\Interfaces\ConfigInterface;
use Feast\Interfaces\ResponseInterface;
use Feast\ServiceContainer\ContainerException;
use Feast\ServiceContainer\NotFoundException;
use Feast\ServiceContainer\ServiceContainerItemInterface;
use Feast\Traits\DependencyInjected;
use stdClass;
/**
* Manage session variables. Also handles session security if "strictIp" setting
* is enabled.
*/
class Session implements ServiceContainerItemInterface
{
use DependencyInjected;
private bool $sessionEnabled = true;
/**
* Initial creation of Feast_Session.
*
* If Strict IP setting is enabled, the session is destroyed if the IP doesn't match.
*
* @param ConfigInterface $config
* @throws ContainerException
* @throws NotFoundException
*/
public function __construct(ConfigInterface $config)
{
$this->checkInjected();
/** @var bool $isEnabled */
$isEnabled = $config->getSetting('session.enabled', true);
if ($isEnabled === false) {
$this->sessionEnabled = false;
return;
}
session_name((string)$config->getSetting('session.name', 'Feast_Session'));
session_set_cookie_params((int)$config->getSetting('session.timeout', 0));
session_start();
$Feast = $this->getNamespace('Feast');
/** @var bool $strictIp */
$strictIp = $config->getSetting('session.strictIp', false);
if ($strictIp) {
/** @psalm-suppress PossiblyUndefinedArrayOffset */
if (isset($Feast->ipAddress) && $Feast->ipAddress !== $_SERVER['REMOTE_ADDR']) {
session_destroy();
$response = di(ResponseInterface::class);
/** @psalm-suppress PossiblyUndefinedArrayOffset */
$response->redirect($_SERVER['REQUEST_URI']);
}
}
/** @psalm-suppress PossiblyUndefinedArrayOffset */
$Feast->ipAddress = $_SERVER['REMOTE_ADDR'];
}
/**
* Return session namespace by name. Creates if non-existent.
*
* @param string $namespace
* @return stdClass
* @throws SessionNotStartedException
*/
public function getNamespace(string $namespace): stdClass
{
if ($this->sessionEnabled === false) {
throw new SessionNotStartedException('Session not started',);
}
if (!isset($_SESSION[$namespace]) || $_SESSION[$namespace] instanceof stdClass === false) {
$_SESSION[$namespace] = new stdClass();
}
return $_SESSION[$namespace];
}
/**
* Destroy a namespace in the session.
*
* @param string $namespace
* @throws SessionNotStartedException
*/
public function destroyNamespace(string $namespace): void
{
if ($this->sessionEnabled === false) {
throw new SessionNotStartedException('Session not started',);
}
unset($_SESSION[$namespace]);
}
public function isEnabled(): bool
{
return $this->sessionEnabled;
}
}