1: <?php
2:
3: /**
4: * This file is part of the Nette Framework (https://nette.org)
5: *
6: * Copyright (c) 2004 David Grudl (http://davidgrudl.com)
7: *
8: * For the full copyright and license information, please view
9: * the file license.txt that was distributed with this source code.
10: * @package Nette\Web
11: */
12:
13:
14:
15: /**
16: * Session namespace for Session.
17: *
18: * @author David Grudl
19: * @package Nette\Web
20: */
21: final class NSessionNamespace extends NObject implements IteratorAggregate, ArrayAccess
22: {
23: /** @var array session data storage */
24: private $data;
25:
26: /** @var array session metadata storage */
27: private $meta;
28:
29: /** @var bool */
30: public $warnOnUndefined = FALSE;
31:
32:
33:
34: /**
35: * Do not call directly. Use NSession::getNamespace().
36: */
37: public function __construct(& $data, & $meta)
38: {
39: $this->data = & $data;
40: $this->meta = & $meta;
41: }
42:
43:
44:
45: /**
46: * Returns an iterator over all namespace variables.
47: * @return ArrayIterator
48: */
49: public function getIterator()
50: {
51: if (isset($this->data)) {
52: return new ArrayIterator($this->data);
53: } else {
54: return new ArrayIterator;
55: }
56: }
57:
58:
59:
60: /**
61: * Sets a variable in this session namespace.
62: * @param string name
63: * @param mixed value
64: * @return void
65: */
66: public function __set($name, $value)
67: {
68: $this->data[$name] = $value;
69: if (is_object($value)) {
70: $this->meta[$name]['V'] = NClassReflection::from($value)->getAnnotation('serializationVersion');
71: }
72: }
73:
74:
75:
76: /**
77: * Gets a variable from this session namespace.
78: * @param string name
79: * @return mixed
80: */
81: public function &__get($name)
82: {
83: if ($this->warnOnUndefined && !array_key_exists($name, $this->data)) {
84: trigger_error("The variable '$name' does not exist in session namespace", E_USER_NOTICE);
85: }
86:
87: return $this->data[$name];
88: }
89:
90:
91:
92: /**
93: * Determines whether a variable in this session namespace is set.
94: * @param string name
95: * @return bool
96: */
97: public function __isset($name)
98: {
99: return isset($this->data[$name]);
100: }
101:
102:
103:
104: /**
105: * Unsets a variable in this session namespace.
106: * @param string name
107: * @return void
108: */
109: public function __unset($name)
110: {
111: unset($this->data[$name], $this->meta[$name]);
112: }
113:
114:
115:
116: /**
117: * Sets a variable in this session namespace.
118: * @param string name
119: * @param mixed value
120: * @return void
121: */
122: public function offsetSet($name, $value)
123: {
124: $this->__set($name, $value);
125: }
126:
127:
128:
129: /**
130: * Gets a variable from this session namespace.
131: * @param string name
132: * @return mixed
133: */
134: public function offsetGet($name)
135: {
136: return $this->__get($name);
137: }
138:
139:
140:
141: /**
142: * Determines whether a variable in this session namespace is set.
143: * @param string name
144: * @return bool
145: */
146: public function offsetExists($name)
147: {
148: return $this->__isset($name);
149: }
150:
151:
152:
153: /**
154: * Unsets a variable in this session namespace.
155: * @param string name
156: * @return void
157: */
158: public function offsetUnset($name)
159: {
160: $this->__unset($name);
161: }
162:
163:
164:
165: /**
166: * Sets the expiration of the namespace or specific variables.
167: * @param string|int|DateTime time, value 0 means "until the browser is closed"
168: * @param mixed optional list of variables / single variable to expire
169: * @return NSessionNamespace provides a fluent interface
170: */
171: public function setExpiration($time, $variables = NULL)
172: {
173: if (empty($time)) {
174: $time = NULL;
175: $whenBrowserIsClosed = TRUE;
176: } else {
177: $time = NDateTime53::from($time)->format('U');
178: $whenBrowserIsClosed = FALSE;
179: }
180:
181: if ($variables === NULL) { // to entire namespace
182: $this->meta['']['T'] = $time;
183: $this->meta['']['B'] = $whenBrowserIsClosed;
184:
185: } elseif (is_array($variables)) { // to variables
186: foreach ($variables as $variable) {
187: $this->meta[$variable]['T'] = $time;
188: $this->meta[$variable]['B'] = $whenBrowserIsClosed;
189: }
190:
191: } else { // to variable
192: $this->meta[$variables]['T'] = $time;
193: $this->meta[$variables]['B'] = $whenBrowserIsClosed;
194: }
195: return $this;
196: }
197:
198:
199:
200: /**
201: * Removes the expiration from the namespace or specific variables.
202: * @param mixed optional list of variables / single variable to expire
203: * @return void
204: */
205: public function removeExpiration($variables = NULL)
206: {
207: if ($variables === NULL) {
208: // from entire namespace
209: unset($this->meta['']['T'], $this->meta['']['B']);
210:
211: } elseif (is_array($variables)) {
212: // from variables
213: foreach ($variables as $variable) {
214: unset($this->meta[$variable]['T'], $this->meta[$variable]['B']);
215: }
216: } else {
217: unset($this->meta[$variables]['T'], $this->meta[$variable]['B']);
218: }
219: }
220:
221:
222:
223: /**
224: * Cancels the current session namespace.
225: * @return void
226: */
227: public function remove()
228: {
229: $this->data = NULL;
230: $this->meta = NULL;
231: }
232:
233: }
234: