From 2d3fc218db53258ec63e11500f403ff3c51cfd20 Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 14 Jan 2020 09:42:33 +0100 Subject: [PATCH] Window: Differentiate between window and container id --- library/Icinga/Web/Window.php | 69 ++++++++++++++++++++++++++++++++--- 1 file changed, 64 insertions(+), 5 deletions(-) diff --git a/library/Icinga/Web/Window.php b/library/Icinga/Web/Window.php index e6f1a05e1..7b43d0536 100644 --- a/library/Icinga/Web/Window.php +++ b/library/Icinga/Web/Window.php @@ -3,29 +3,63 @@ namespace Icinga\Web; -use Icinga\Web\Session; +use Icinga\Application\Icinga; +use Icinga\Web\Session\SessionNamespace; class Window { const UNDEFINED = 'undefined'; + /** @var Window */ + protected static $window; + + /** @var string */ protected $id; + /** @var string */ + protected $containerId; + public function __construct($id) { - $this->id = $id; + $parts = explode('_', $id, 2); + if (isset($parts[1])) { + $this->id = $parts[0]; + $this->containerId = $id; + } else { + $this->id = $id; + } } + /** + * Get whether the window's ID is undefined + * + * @return bool + */ public function isUndefined() { return $this->id === self::UNDEFINED; } + /** + * Get the window's ID + * + * @return string + */ public function getId() { return $this->id; } + /** + * Get the container's ID + * + * @return string + */ + public function getContainerId() + { + return $this->containerId ?: $this->id; + } + /** * Return a window-aware session by using the given prefix * @@ -38,29 +72,54 @@ class Window { $session = Session::getSession(); - $identifier = $prefix . '_' . $this->id; + $identifier = $prefix . '_' . $this->getId(); if ($reset && $session->hasNamespace($identifier)) { $session->removeNamespace($identifier); } + $namespace = $session->getNamespace($identifier); $nsUndef = $prefix . '_' . self::UNDEFINED; - if (!$reset && $this->id !== self::UNDEFINED && $session->hasNamespace($nsUndef)) { - // We do not have any window-id on the very first request. Now we add + if (! $reset && ! $this->isUndefined() && $session->hasNamespace($nsUndef)) { + // We may not have any window-id on the very first request. Now we add // all values from the namespace, that has been created in this case, // to the new one and remove it afterwards. foreach ($session->getNamespace($nsUndef) as $name => $value) { $namespace->set($name, $value); } + $session->removeNamespace($nsUndef); } return $namespace; } + /** + * Generate a random string + * + * @return string + */ public static function generateId() { $letters = 'abcefghijklmnopqrstuvwxyz'; return substr(str_shuffle($letters), 0, 12); } + + /** + * @return Window + */ + public static function getInstance() + { + if (! isset(static::$window)) { + $id = Icinga::app()->getRequest()->getHeader('X-Icinga-WindowId'); + if (empty($id) || $id === static::UNDEFINED) { + $id = static::generateId(); + Icinga::app()->getResponse()->setHeader('X-Icinga-WindowId', $id); + } + + static::$window = new Window($id); + } + + return static::$window; + } }