From f9d70624765c8d5d5d00621e56dcbd6d87797b1d Mon Sep 17 00:00:00 2001 From: Eric Lippmann Date: Tue, 18 Nov 2014 12:51:06 +0100 Subject: [PATCH 01/17] Form: Add our element and decorator paths instead of calling createIcingaFormElement createIcingaFormElement lacks all stuff applied in Zend_Form::createElement(). --- library/Icinga/Web/Form.php | 39 +++++++++++++++---------------------- 1 file changed, 16 insertions(+), 23 deletions(-) diff --git a/library/Icinga/Web/Form.php b/library/Icinga/Web/Form.php index 20484c33e..854a6fa4a 100644 --- a/library/Icinga/Web/Form.php +++ b/library/Icinga/Web/Form.php @@ -11,7 +11,6 @@ use Zend_View_Interface; use Icinga\Application\Icinga; use Icinga\Web\Form\Decorator\NoScriptApply; use Icinga\Web\Form\Element\CsrfCounterMeasure; -use Icinga\Web\Form\FormElement; /** * Base class for forms providing CSRF protection, confirmation logic and auto submission @@ -139,6 +138,21 @@ class Form extends Zend_Form throw new LogicException('The option `onSuccess\' is not callable'); } + // Zend's plugin loader reverses the order of added prefix paths thus trying our paths first before trying + // Zend paths + $this->addPrefixPaths(array( + array( + 'prefix' => 'Icinga\\Web\\Form\\Element\\', + 'path' => Icinga::app()->getLibraryDir('Icinga/Web/Form/Element'), + 'type' => static::ELEMENT + ), + array( + 'prefix' => 'Icinga\\Web\\Form\\Decorator\\', + 'path' => Icinga::app()->getLibraryDir('Icinga/Web/Form/Decorator'), + 'type' => static::DECORATOR + ) + )); + parent::__construct($options); } @@ -464,9 +478,7 @@ class Form extends Zend_Form $options = array('decorators' => static::$defaultElementDecorators); } - if (($el = $this->createIcingaFormElement($type, $name, $options)) === null) { - $el = parent::createElement($type, $name, $options); - } + $el = parent::createElement($type, $name, $options); if ($el && $el->getAttrib('autosubmit')) { $noScript = new NoScriptApply(); // Non-JS environments @@ -738,25 +750,6 @@ class Form extends Zend_Form return array(); } - /** - * Create a new element located in the Icinga Web 2 library - * - * @param string $type The type of the element - * @param string $name The name of the element - * @param mixed $options The options for the element - * - * @return NULL|FormElement NULL in case the element is not found in the Icinga Web 2 library - * - * @see Form::$defaultElementDecorators For Icinga Web 2's default element decorators. - */ - protected function createIcingaFormElement($type, $name, $options = null) - { - $className = 'Icinga\\Web\\Form\\Element\\' . ucfirst($type); - if (class_exists($className)) { - return new $className($name, $options); - } - } - /** * Render this form * From 985df1124b2dd1f71257bca7668e427b3c3ec598 Mon Sep 17 00:00:00 2001 From: Alexander Fuhr Date: Tue, 18 Nov 2014 13:02:49 +0100 Subject: [PATCH 02/17] Update puppet vagrant provision to use new database schemas fixes #7698 --- .vagrant-puppet/manifests/default.pp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/.vagrant-puppet/manifests/default.pp b/.vagrant-puppet/manifests/default.pp index 117ad0836..c728d80ec 100644 --- a/.vagrant-puppet/manifests/default.pp +++ b/.vagrant-puppet/manifests/default.pp @@ -602,14 +602,14 @@ exec { 'create-pgsql-icingaweb-db': } exec { 'populate-icingaweb-mysql-db-tables': - unless => 'mysql -uicingaweb -picingaweb icingaweb -e "SELECT * FROM account;" &> /dev/null', - command => 'mysql -uicingaweb -picingaweb icingaweb < /vagrant/etc/schema/mysql.sql', + unless => 'mysql -uicingaweb -picingaweb icingaweb -e "SELECT * FROM icingaweb_group;" &> /dev/null', + command => 'mysql -uicingaweb -picingaweb icingaweb < /vagrant/etc/schema/mysql.schema.sql', require => [ Exec['create-mysql-icingaweb-db'] ] } exec { 'populate-icingweba-pgsql-db-tables': - unless => 'psql -U icingaweb -d icingaweb -c "SELECT * FROM account;" &> /dev/null', - command => 'sudo -u postgres psql -U icingaweb -d icingaweb -f /vagrant/etc/schema/pgsql.sql', + unless => 'psql -U icingaweb -d icingaweb -c "SELECT * FROM icingaweb_group;" &> /dev/null', + command => 'sudo -u postgres psql -U icingaweb -d icingaweb -f /vagrant/etc/schema/pgsql.schema.sql', require => [ Exec['create-pgsql-icingaweb-db'] ] } From 0c84bf614d505b3417bbe3b2ff5589b8748329b7 Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 18 Nov 2014 13:02:56 +0100 Subject: [PATCH 03/17] Split config functionality into two classes There is now Icinga\Application\Config as our ini configuration handler and Icinga\Data\ConfigObject as our general configuration container. refs #7147 --- library/Icinga/Application/Config.php | 334 ++++++------------ library/Icinga/Data/ConfigObject.php | 304 ++++++++++++++++ .../library/Icinga/Application/ConfigTest.php | 310 ++++++---------- .../library/Icinga/Data/ConfigObjectTest.php | 224 ++++++++++++ 4 files changed, 751 insertions(+), 421 deletions(-) create mode 100644 library/Icinga/Data/ConfigObject.php create mode 100644 test/php/library/Icinga/Data/ConfigObjectTest.php diff --git a/library/Icinga/Application/Config.php b/library/Icinga/Application/Config.php index 6a08eb93e..dcb837fde 100644 --- a/library/Icinga/Application/Config.php +++ b/library/Icinga/Application/Config.php @@ -6,15 +6,14 @@ namespace Icinga\Application; use Iterator; use Countable; -use ArrayAccess; -use LogicException; use UnexpectedValueException; +use Icinga\Data\ConfigObject; use Icinga\Exception\NotReadableError; /** - * Container for configuration values and global registry of application and module related configuration. + * Container for INI like configuration and global registry of application and module related configuration. */ -class Config implements Countable, Iterator, ArrayAccess +class Config implements Countable, Iterator { /** * Configuration directory where ALL (application and module) configuration is located @@ -38,14 +37,14 @@ class Config implements Countable, Iterator, ArrayAccess protected static $modules = array(); /** - * This config's data + * The internal ConfigObject * - * @var array + * @var ConfigObject */ - protected $data; + protected $config; /** - * The INI file this configuration has been loaded from or should be written to + * The INI file this config has been loaded from or should be written to * * @var string */ @@ -54,19 +53,11 @@ class Config implements Countable, Iterator, ArrayAccess /** * Create a new config * - * @param array $data The data to initialize the new config with + * @param ConfigObject $config The config object to handle */ - public function __construct(array $data = array()) + public function __construct(ConfigObject $config = null) { - $this->data = array(); - - foreach ($data as $key => $value) { - if (is_array($value)) { - $this->data[$key] = new static($value); - } else { - $this->data[$key] = $value; - } - } + $this->config = $config !== null ? $config : new ConfigObject(); } /** @@ -82,7 +73,7 @@ class Config implements Countable, Iterator, ArrayAccess /** * Set this config's file path * - * @param string $filepath The path to the config file + * @param string $filepath The path to the ini file * * @return self */ @@ -93,50 +84,33 @@ class Config implements Countable, Iterator, ArrayAccess } /** - * Deep clone this config - */ - public function __clone() - { - $array = array(); - foreach ($this->data as $key => $value) { - if ($value instanceof self) { - $array[$key] = clone $value; - } else { - $array[$key] = $value; - } - } - - $this->data = $array; - } - - /** - * Return the count of available sections and properties + * Return the count of available sections * * @return int */ public function count() { - return count($this->data); + return $this->config->count(); } /** - * Reset the current position of $this->data + * Reset the current position of the internal config object * - * @return mixed + * @return ConfigObject */ public function rewind() { - return reset($this->data); + return $this->config->rewind(); } /** - * Return the section's or property's value of the current iteration + * Return the section of the current iteration * - * @return mixed + * @return ConfigObject */ public function current() { - return current($this->data); + return $this->config->current(); } /** @@ -146,165 +120,47 @@ class Config implements Countable, Iterator, ArrayAccess */ public function valid() { - return key($this->data) !== null; + return $this->config->valid(); } /** - * Return the section's or property's name of the current iteration + * Return the section's name of the current iteration * - * @return mixed + * @return string */ public function key() { - return key($this->data); + return $this->config->key(); } /** - * Advance the position of the current iteration and return the new section's or property's value + * Advance the position of the current iteration and return the new section * - * @return mixed + * @return ConfigObject */ public function next() { - return next($this->data); + return $this->config->next(); } /** - * Return whether the given section or property is set - * - * @param string $key The name of the section or property - * - * @return bool - */ - public function __isset($key) - { - return isset($this->data[$key]); - } - - /** - * Return the value for the given property or the config for the given section - * - * @param string $key The name of the property or section - * - * @return mixed|NULL The value or NULL in case $key does not exist - */ - public function __get($key) - { - if (array_key_exists($key, $this->data)) { - return $this->data[$key]; - } - } - - /** - * Add a new property or section - * - * @param string $key The name of the new property or section - * @param mixed $value The value to set for the new property or section - */ - public function __set($key, $value) - { - if (is_array($value)) { - $this->data[$key] = new static($value); - } else { - $this->data[$key] = $value; - } - } - - /** - * Remove the given property or section - * - * @param string $key The property or section to remove - */ - public function __unset($key) - { - unset($this->data[$key]); - } - - /** - * Return whether the given section or property is set - * - * @param string $key The name of the section or property - * - * @return bool - */ - public function offsetExists($key) - { - return isset($this->$key); - } - - /** - * Return the value for the given property or the config for the given section - * - * @param string $key The name of the property or section - * - * @return mixed|NULL The value or NULL in case $key does not exist - */ - public function offsetGet($key) - { - return $this->$key; - } - - /** - * Add a new property or section - * - * @param string $key The name of the new property or section - * @param mixed $value The value to set for the new property or section - */ - public function offsetSet($key, $value) - { - if ($key === null) { - throw new LogicException('Appending values without an explicit key is not supported'); - } - - $this->$key = $value; - } - - /** - * Remove the given property or section - * - * @param string $key The property or section to remove - */ - public function offsetUnset($key) - { - unset($this->$key); - } - - /** - * Return whether this config has any data + * Return whether this config has any sections * * @return bool */ public function isEmpty() { - return $this->count() === 0; + return $this->config->isEmpty(); } /** - * Return the value for the given property or the config for the given section - * - * @param string $key The name of the property or section - * @param mixed $default The value to return in case the property or section is missing - * - * @return mixed - */ - public function get($key, $default = null) - { - $value = $this->$key; - if ($default !== null && $value === null) { - $value = $default; - } - - return $value; - } - - /** - * Return all section and property names + * Return this config's section names * * @return array */ public function keys() { - return array_keys($this->data); + return $this->config->keys(); } /** @@ -314,46 +170,7 @@ class Config implements Countable, Iterator, ArrayAccess */ public function toArray() { - $array = array(); - foreach ($this->data as $key => $value) { - if ($value instanceof self) { - $array[$key] = $value->toArray(); - } else { - $array[$key] = $value; - } - } - - return $array; - } - - /** - * Merge the given data with this config - * - * @param array|Config $data An array or a config - * - * @return self - */ - public function merge($data) - { - if ($data instanceof self) { - $data = $data->toArray(); - } - - foreach ($data as $key => $value) { - if (array_key_exists($key, $this->data)) { - if (is_array($value)) { - if ($this->data[$key] instanceof self) { - $this->data[$key]->merge($value); - } else { - $this->data[$key] = new static($value); - } - } else { - $this->data[$key] = $value; - } - } else { - $this->data[$key] = is_array($value) ? new static($value) : $value; - } - } + return $this->config->toArray(); } /** @@ -367,14 +184,14 @@ class Config implements Countable, Iterator, ArrayAccess * * @throws UnexpectedValueException In case the given section does not hold any configuration */ - public function fromSection($section, $key, $default = null) + public function get($section, $key, $default = null) { - $value = $this->$section; - if ($value instanceof self) { + $value = $this->config->$section; + if ($value instanceof ConfigObject) { $value = $value->$key; } elseif ($value !== null) { throw new UnexpectedValueException( - sprintf('Value "%s" is not of type "Config" or a sub-type of it', $value) + sprintf('Value "%s" is not of type "%s" or a sub-type of it', $value, get_class($this->config)) ); } @@ -385,6 +202,78 @@ class Config implements Countable, Iterator, ArrayAccess return $value; } + /** + * Return the given section + * + * @param string $name The section's name + * + * @return ConfigObject + */ + public function getSection($name) + { + $section = $this->config->get($name); + return $section !== null ? $section : new ConfigObject(); + } + + /** + * Set or replace a section + * + * @param string $name + * @param array|ConfigObject $config + * + * @return self + */ + public function setSection($name, $config = null) + { + if ($config === null) { + $config = new ConfigObject(); + } elseif (! $config instanceof ConfigObject) { + $config = new ConfigObject($config); + } + + $this->config->$name = $config; + return $this; + } + + /** + * Remove a section + * + * @param string $name + * + * @return self + */ + public function removeSection($name) + { + unset($this->config->$name); + return $this; + } + + /** + * Return whether the given section exists + * + * @param string $name + * + * @return bool + */ + public function hasSection($name) + { + return isset($this->config->$name); + } + + /** + * Initialize a new config using the given array + * + * The returned config has no file associated to it. + * + * @param array $array The array to initialize the config with + * + * @return Config + */ + public static function fromArray(array $array) + { + return new static(new ConfigObject($array)); + } + /** * Load configuration from the given INI file * @@ -394,19 +283,20 @@ class Config implements Countable, Iterator, ArrayAccess */ public static function fromIni($file) { - $config = new static(); + $emptyConfig = new static(); $filepath = realpath($file); if ($filepath === false) { - $config->setConfigFile($file); + $emptyConfig->setConfigFile($file); } elseif (is_readable($filepath)) { + $config = new static(new ConfigObject(parse_ini_file($filepath, true))); $config->setConfigFile($filepath); - $config->merge(parse_ini_file($filepath, true)); + return $config; } else { throw new NotReadableError(t('Cannot read config file "%s". Permission denied'), $filepath); } - return $config; + return $emptyConfig; } /** diff --git a/library/Icinga/Data/ConfigObject.php b/library/Icinga/Data/ConfigObject.php new file mode 100644 index 000000000..23b2e1651 --- /dev/null +++ b/library/Icinga/Data/ConfigObject.php @@ -0,0 +1,304 @@ +data = array(); + + foreach ($data as $key => $value) { + if (is_array($value)) { + $this->data[$key] = new static($value); + } else { + $this->data[$key] = $value; + } + } + } + + /** + * Deep clone this config + */ + public function __clone() + { + $array = array(); + foreach ($this->data as $key => $value) { + if ($value instanceof self) { + $array[$key] = clone $value; + } else { + $array[$key] = $value; + } + } + + $this->data = $array; + } + + /** + * Return the count of available sections and properties + * + * @return int + */ + public function count() + { + return count($this->data); + } + + /** + * Reset the current position of $this->data + * + * @return mixed + */ + public function rewind() + { + return reset($this->data); + } + + /** + * Return the section's or property's value of the current iteration + * + * @return mixed + */ + public function current() + { + return current($this->data); + } + + /** + * Return whether the position of the current iteration is valid + * + * @return bool + */ + public function valid() + { + return key($this->data) !== null; + } + + /** + * Return the section's or property's name of the current iteration + * + * @return mixed + */ + public function key() + { + return key($this->data); + } + + /** + * Advance the position of the current iteration and return the new section's or property's value + * + * @return mixed + */ + public function next() + { + return next($this->data); + } + + /** + * Return whether the given section or property is set + * + * @param string $key The name of the section or property + * + * @return bool + */ + public function __isset($key) + { + return isset($this->data[$key]); + } + + /** + * Return the value for the given property or the config for the given section + * + * @param string $key The name of the property or section + * + * @return mixed|NULL The value or NULL in case $key does not exist + */ + public function __get($key) + { + return $this->get($key); + } + + /** + * Add a new property or section + * + * @param string $key The name of the new property or section + * @param mixed $value The value to set for the new property or section + */ + public function __set($key, $value) + { + if (is_array($value)) { + $this->data[$key] = new static($value); + } else { + $this->data[$key] = $value; + } + } + + /** + * Remove the given property or section + * + * @param string $key The property or section to remove + */ + public function __unset($key) + { + unset($this->data[$key]); + } + + /** + * Return whether the given section or property is set + * + * @param string $key The name of the section or property + * + * @return bool + */ + public function offsetExists($key) + { + return isset($this->$key); + } + + /** + * Return the value for the given property or the config for the given section + * + * @param string $key The name of the property or section + * + * @return mixed|NULL The value or NULL in case $key does not exist + */ + public function offsetGet($key) + { + return $this->get($key); + } + + /** + * Add a new property or section + * + * @param string $key The name of the new property or section + * @param mixed $value The value to set for the new property or section + */ + public function offsetSet($key, $value) + { + if ($key === null) { + throw new LogicException('Appending values without an explicit key is not supported'); + } + + $this->$key = $value; + } + + /** + * Remove the given property or section + * + * @param string $key The property or section to remove + */ + public function offsetUnset($key) + { + unset($this->$key); + } + + /** + * Return whether this config has any data + * + * @return bool + */ + public function isEmpty() + { + return empty($this->data); + } + + /** + * Return the value for the given property or the config for the given section + * + * @param string $key The name of the property or section + * @param mixed $default The value to return in case the property or section is missing + * + * @return mixed + */ + public function get($key, $default = null) + { + if (array_key_exists($key, $this->data)) { + return $this->data[$key]; + } + + return $default !== null ? $default : null; + } + + /** + * Return all section and property names + * + * @return array + */ + public function keys() + { + return array_keys($this->data); + } + + /** + * Return this config's data as associative array + * + * @return array + */ + public function toArray() + { + $array = array(); + foreach ($this->data as $key => $value) { + if ($value instanceof self) { + $array[$key] = $value->toArray(); + } else { + $array[$key] = $value; + } + } + + return $array; + } + + /** + * Merge the given data with this config + * + * @param array|Config $data An array or a config + * + * @return self + */ + public function merge($data) + { + if ($data instanceof self) { + $data = $data->toArray(); + } + + foreach ($data as $key => $value) { + if (array_key_exists($key, $this->data)) { + if (is_array($value)) { + if ($this->data[$key] instanceof self) { + $this->data[$key]->merge($value); + } else { + $this->data[$key] = new static($value); + } + } else { + $this->data[$key] = $value; + } + } else { + $this->data[$key] = is_array($value) ? new static($value) : $value; + } + } + + return $this; + } +} diff --git a/test/php/library/Icinga/Application/ConfigTest.php b/test/php/library/Icinga/Application/ConfigTest.php index 4f4f77219..1e64da808 100644 --- a/test/php/library/Icinga/Application/ConfigTest.php +++ b/test/php/library/Icinga/Application/ConfigTest.php @@ -28,259 +28,171 @@ class ConfigTest extends BaseTestCase Config::$configDir = $this->oldConfigDir; } - public function testWhetherInitializingAConfigWithAssociativeArraysCreatesHierarchicalConfigObjects() + public function testWhetherConfigIsCountable() { - $config = new Config(array( - 'a' => 'b', - 'c' => 'd', - 'e' => array( - 'f' => 'g', - 'h' => 'i', - 'j' => array( - 'k' => 'l', - 'm' => 'n' - ) - ) - )); + $config = Config::fromArray(array('a' => 'b', 'c' => array('d' => 'e'))); - $this->assertInstanceOf( - get_class($config), - $config->e, - 'Config::__construct() does not accept two dimensional arrays' - ); - $this->assertInstanceOf( - get_class($config), - $config->e->j, - 'Config::__construct() does not accept multi dimensional arrays' - ); + $this->assertInstanceOf('Countable', $config, 'Config does not implement interface `Countable\''); + $this->assertEquals(2, count($config), 'Config does not count sections correctly'); } - /** - * @depends testWhetherInitializingAConfigWithAssociativeArraysCreatesHierarchicalConfigObjects - */ - public function testWhetherItIsPossibleToCloneConfigObjects() + public function testWhetherConfigIsTraversable() { - $config = new Config(array( - 'a' => 'b', - 'c' => array( - 'd' => 'e' - ) - )); - $newConfig = clone $config; + $config = Config::fromArray(array('a' => array(), 'c' => array())); + $config->setSection('e'); - $this->assertNotSame( - $config, - $newConfig, - 'Shallow cloning objects of type Config does not seem to work properly' - ); - $this->assertNotSame( - $config->c, - $newConfig->c, - 'Deep cloning objects of type Config does not seem to work properly' - ); - } - - public function testWhetherConfigObjectsAreCountable() - { - $config = new Config(array('a' => 'b', 'c' => array('d' => 'e'))); - - $this->assertInstanceOf('Countable', $config, 'Config objects do not implement interface `Countable\''); - $this->assertEquals(2, count($config), 'Config objects do not count properties and sections correctly'); - } - - public function testWhetherConfigObjectsAreTraversable() - { - $config = new Config(array('a' => 'b', 'c' => 'd')); - $config->e = 'f'; - - $this->assertInstanceOf('Iterator', $config, 'Config objects do not implement interface `Iterator\''); + $this->assertInstanceOf('Iterator', $config, 'Config does not implement interface `Iterator\''); $actual = array(); - foreach ($config as $key => $value) { - $actual[$key] = $value; + foreach ($config as $key => $_) { + $actual[] = $key; } $this->assertEquals( - array('a' => 'b', 'c' => 'd', 'e' => 'f'), + array('a', 'c', 'e'), $actual, - 'Config objects do not iterate properly in the order their values were inserted' + 'Config does not iterate properly in the order its sections were inserted' ); } - public function testWhetherOneCanCheckWhetherConfigObjectsHaveACertainPropertyOrSection() - { - $config = new Config(array('a' => 'b', 'c' => array('d' => 'e'))); - - $this->assertTrue(isset($config->a), 'Config objects do not seem to implement __isset() properly'); - $this->assertTrue(isset($config->c->d), 'Config objects do not seem to implement __isset() properly'); - $this->assertFalse(isset($config->d), 'Config objects do not seem to implement __isset() properly'); - $this->assertFalse(isset($config->c->e), 'Config objects do not seem to implement __isset() properly'); - $this->assertTrue(isset($config['a']), 'Config object do not seem to implement offsetExists() properly'); - $this->assertFalse(isset($config['d']), 'Config object do not seem to implement offsetExists() properly'); - } - - public function testWhetherItIsPossibleToAccessProperties() - { - $config = new Config(array('a' => 'b', 'c' => null)); - - $this->assertEquals('b', $config->a, 'Config objects do not allow property access'); - $this->assertNull($config['c'], 'Config objects do not allow offset access'); - $this->assertNull($config->d, 'Config objects do not return NULL as default'); - } - - public function testWhetherItIsPossibleToSetPropertiesAndSections() + public function testWhetherOneCanCheckIfAConfigHasAnySections() { $config = new Config(); - $config->a = 'b'; - $config['c'] = array('d' => 'e'); + $this->assertTrue($config->isEmpty(), 'Config does not report that it is empty'); - $this->assertTrue(isset($config->a), 'Config objects do not allow to set properties'); - $this->assertTrue(isset($config->c), 'Config objects do not allow to set offsets'); - $this->assertInstanceOf( - get_class($config), - $config->c, - 'Config objects do not convert arrays to config objects when set' - ); + $config->setSection('test'); + $this->assertFalse($config->isEmpty(), 'Config does report that it is empty although it is not'); } - /** - * @expectedException LogicException - */ - public function testWhetherItIsNotPossibleToAppendProperties() + public function testWhetherItIsPossibleToRetrieveAllSectionNames() { - $config = new Config(); - $config[] = 'test'; - } - - public function testWhetherItIsPossibleToUnsetPropertiesAndSections() - { - $config = new Config(array('a' => 'b', 'c' => array('d' => 'e'))); - unset($config->a); - unset($config['c']); - - $this->assertFalse(isset($config->a), 'Config objects do not allow to unset properties'); - $this->assertFalse(isset($config->c), 'Config objects do not allow to unset sections'); - } - - /** - * @depends testWhetherConfigObjectsAreCountable - */ - public function testWhetherOneCanCheckIfAConfigObjectHasAnyPropertiesOrSections() - { - $config = new Config(); - $this->assertTrue($config->isEmpty(), 'Config objects do not report that they are empty'); - - $config->test = 'test'; - $this->assertFalse($config->isEmpty(), 'Config objects do report that they are empty although they are not'); - } - - /** - * @depends testWhetherItIsPossibleToAccessProperties - */ - public function testWhetherItIsPossibleToRetrieveDefaultValuesForNonExistentPropertiesOrSections() - { - $config = new Config(array('a' => 'b')); + $config = Config::fromArray(array('a' => array('b' => 'c'), 'd' => array('e' => 'f'))); $this->assertEquals( - 'b', - $config->get('a'), - 'Config objects do not return the actual value of existing properties' - ); - $this->assertNull( - $config->get('b'), - 'Config objects do not return NULL as default for non-existent properties' - ); - $this->assertEquals( - 'test', - $config->get('test', 'test'), - 'Config objects do not allow to define the default value to return for non-existent properties' - ); - } - - public function testWhetherItIsPossibleToRetrieveAllPropertyAndSectionNames() - { - $config = new Config(array('a' => 'b', 'c' => array('d' => 'e'))); - - $this->assertEquals( - array('a', 'c'), + array('a', 'd'), $config->keys(), - 'Config objects do not list property and section names correctly' + 'Config::keys does not list section names correctly' ); } - public function testWhetherConfigObjectsCanBeConvertedToArrays() + public function testWhetherConfigCanBeConvertedToAnArray() { - $config = new Config(array('a' => 'b', 'c' => array('d' => 'e'))); + $config = Config::fromArray(array('a' => 'b', 'c' => array('d' => 'e'))); $this->assertEquals( array('a' => 'b', 'c' => array('d' => 'e')), $config->toArray(), - 'Config objects cannot be correctly converted to arrays' + 'Config::toArray does not return the correct array' ); } - /** - * @depends testWhetherConfigObjectsCanBeConvertedToArrays - */ - public function testWhetherItIsPossibleToMergeConfigObjects() - { - $config = new Config(array('a' => 'b')); - - $config->merge(array('a' => 'bb', 'c' => 'd', 'e' => array('f' => 'g'))); - $this->assertEquals( - array('a' => 'bb', 'c' => 'd', 'e' => array('f' => 'g')), - $config->toArray(), - 'Config objects cannot be extended with arrays' - ); - - $config->merge(new Config(array('c' => array('d' => 'ee'), 'e' => array('h' => 'i')))); - $this->assertEquals( - array('a' => 'bb', 'c' => array('d' => 'ee'), 'e' => array('f' => 'g', 'h' => 'i')), - $config->toArray(), - 'Config objects cannot be extended with other Config objects' - ); - } - - /** - * @depends testWhetherItIsPossibleToAccessProperties - */ public function testWhetherItIsPossibleToDirectlyRetrieveASectionProperty() { - $config = new Config(array('a' => array('b' => 'c'))); + $config = Config::fromArray(array('a' => array('b' => 'c'))); $this->assertEquals( 'c', - $config->fromSection('a', 'b'), - 'Config::fromSection does not return the actual value of a section\'s property' + $config->get('a', 'b'), + 'Config::get does not return the actual value of a section\'s property' ); $this->assertNull( - $config->fromSection('a', 'c'), - 'Config::fromSection does not return NULL as default for non-existent section properties' + $config->get('a', 'c'), + 'Config::get does not return NULL as default for non-existent section properties' ); $this->assertNull( - $config->fromSection('b', 'c'), - 'Config::fromSection does not return NULL as default for non-existent sections' + $config->get('b', 'c'), + 'Config::get does not return NULL as default for non-existent sections' ); $this->assertEquals( 'test', - $config->fromSection('a', 'c', 'test'), - 'Config::fromSection does not return the given default value for non-existent section properties' + $config->get('a', 'c', 'test'), + 'Config::get does not return the given default value for non-existent section properties' ); $this->assertEquals( 'c', - $config->fromSection('a', 'b', 'test'), - 'Config::fromSection does not return the actual value of a section\'s property in case a default is given' + $config->get('a', 'b', 'test'), + 'Config::get does not return the actual value of a section\'s property in case a default is given' + ); + } + + public function testWhetherConfigReturnsSingleSections() + { + $config = Config::fromArray(array('a' => array('b' => 'c'))); + + $this->assertInstanceOf( + 'Icinga\Data\ConfigObject', + $config->getSection('a'), + 'Config::getSection does not return a known section' + ); + } + + /** + * @depends testWhetherConfigReturnsSingleSections + */ + public function testWhetherConfigSetsSingleSections() + { + $config = new Config(); + $config->setSection('a', array('b' => 'c')); + + $this->assertInstanceOf( + 'Icinga\Data\ConfigObject', + $config->getSection('a'), + 'Config::setSection does not set a new section' + ); + + $config->setSection('a', array('bb' => 'cc')); + + $this->assertNull( + $config->getSection('a')->b, + 'Config::setSection does not overwrite existing sections' + ); + $this->assertEquals( + 'cc', + $config->getSection('a')->bb, + 'Config::setSection does not overwrite existing sections' + ); + } + + /** + * @depends testWhetherConfigIsCountable + */ + public function testWhetherConfigRemovesSingleSections() + { + $config = Config::fromArray(array('a' => array('b' => 'c'), 'd' => array('e' => 'f'))); + $config->removeSection('a'); + + $this->assertEquals( + 1, + $config->count(), + 'Config::removeSection does not remove a known section' + ); + } + + /** + * @depends testWhetherConfigSetsSingleSections + */ + public function testWhetherConfigKnowsWhichSectionsItHas() + { + $config = new Config(); + $config->setSection('a'); + + $this->assertTrue( + $config->hasSection('a'), + 'Config::hasSection does not know anything about its sections' + ); + $this->assertFalse( + $config->hasSection('b'), + 'Config::hasSection does not know anything about its sections' ); } /** * @expectedException UnexpectedValueException - * @depends testWhetherItIsPossibleToAccessProperties */ public function testWhetherAnExceptionIsThrownWhenTryingToAccessASectionPropertyOnANonSection() { - $config = new Config(array('a' => 'b')); - $config->fromSection('a', 'b'); + $config = Config::fromArray(array('a' => 'b')); + $config->get('a', 'b'); } public function testWhetherConfigResolvePathReturnsValidAbsolutePaths() @@ -293,10 +205,10 @@ class ConfigTest extends BaseTestCase } /** - * @depends testWhetherConfigObjectsCanBeConvertedToArrays + * @depends testWhetherConfigCanBeConvertedToAnArray * @depends testWhetherConfigResolvePathReturnsValidAbsolutePaths */ - public function testWhetherItIsPossibleToInitializeAConfigObjectFromAIniFile() + public function testWhetherItIsPossibleToInitializeAConfigFromAIniFile() { $config = Config::fromIni(Config::resolvePath('config.ini')); @@ -332,7 +244,7 @@ class ConfigTest extends BaseTestCase } /** - * @depends testWhetherItIsPossibleToInitializeAConfigObjectFromAIniFile + * @depends testWhetherItIsPossibleToInitializeAConfigFromAIniFile */ public function testWhetherItIsPossibleToRetrieveApplicationConfiguration() { @@ -356,7 +268,7 @@ class ConfigTest extends BaseTestCase } /** - * @depends testWhetherItIsPossibleToInitializeAConfigObjectFromAIniFile + * @depends testWhetherItIsPossibleToInitializeAConfigFromAIniFile */ public function testWhetherItIsPossibleToRetrieveModuleConfiguration() { diff --git a/test/php/library/Icinga/Data/ConfigObjectTest.php b/test/php/library/Icinga/Data/ConfigObjectTest.php new file mode 100644 index 000000000..c4b825e58 --- /dev/null +++ b/test/php/library/Icinga/Data/ConfigObjectTest.php @@ -0,0 +1,224 @@ + 'b', + 'c' => 'd', + 'e' => array( + 'f' => 'g', + 'h' => 'i', + 'j' => array( + 'k' => 'l', + 'm' => 'n' + ) + ) + )); + + $this->assertInstanceOf( + get_class($config), + $config->e, + 'ConfigObject::__construct() does not accept two dimensional arrays' + ); + $this->assertInstanceOf( + get_class($config), + $config->e->j, + 'ConfigObject::__construct() does not accept multi dimensional arrays' + ); + } + + /** + * @depends testWhetherInitializingAConfigWithAssociativeArraysCreatesHierarchicalConfigObjects + */ + public function testWhetherItIsPossibleToCloneConfigObjects() + { + $config = new ConfigObject(array( + 'a' => 'b', + 'c' => array( + 'd' => 'e' + ) + )); + $newConfig = clone $config; + + $this->assertNotSame( + $config, + $newConfig, + 'Shallow cloning objects of type ConfigObject does not seem to work properly' + ); + $this->assertNotSame( + $config->c, + $newConfig->c, + 'Deep cloning objects of type ConfigObject does not seem to work properly' + ); + } + + public function testWhetherConfigObjectsAreCountable() + { + $config = new ConfigObject(array('a' => 'b', 'c' => array('d' => 'e'))); + + $this->assertInstanceOf('Countable', $config, 'ConfigObject objects do not implement interface `Countable\''); + $this->assertEquals(2, count($config), 'ConfigObject objects do not count properties and sections correctly'); + } + + public function testWhetherConfigObjectsAreTraversable() + { + $config = new ConfigObject(array('a' => 'b', 'c' => 'd')); + $config->e = 'f'; + + $this->assertInstanceOf('Iterator', $config, 'ConfigObject objects do not implement interface `Iterator\''); + + $actual = array(); + foreach ($config as $key => $value) { + $actual[$key] = $value; + } + + $this->assertEquals( + array('a' => 'b', 'c' => 'd', 'e' => 'f'), + $actual, + 'ConfigObject objects do not iterate properly in the order their values were inserted' + ); + } + + public function testWhetherOneCanCheckWhetherConfigObjectsHaveACertainPropertyOrSection() + { + $config = new ConfigObject(array('a' => 'b', 'c' => array('d' => 'e'))); + + $this->assertTrue(isset($config->a), 'ConfigObjects do not seem to implement __isset() properly'); + $this->assertTrue(isset($config->c->d), 'ConfigObjects do not seem to implement __isset() properly'); + $this->assertFalse(isset($config->d), 'ConfigObjects do not seem to implement __isset() properly'); + $this->assertFalse(isset($config->c->e), 'ConfigObjects do not seem to implement __isset() properly'); + $this->assertTrue(isset($config['a']), 'ConfigObject do not seem to implement offsetExists() properly'); + $this->assertFalse(isset($config['d']), 'ConfigObject do not seem to implement offsetExists() properly'); + } + + public function testWhetherItIsPossibleToAccessProperties() + { + $config = new ConfigObject(array('a' => 'b', 'c' => null)); + + $this->assertEquals('b', $config->a, 'ConfigObjects do not allow property access'); + $this->assertNull($config['c'], 'ConfigObjects do not allow offset access'); + $this->assertNull($config->d, 'ConfigObjects do not return NULL as default'); + } + + public function testWhetherItIsPossibleToSetPropertiesAndSections() + { + $config = new ConfigObject(); + $config->a = 'b'; + $config['c'] = array('d' => 'e'); + + $this->assertTrue(isset($config->a), 'ConfigObjects do not allow to set properties'); + $this->assertTrue(isset($config->c), 'ConfigObjects do not allow to set offsets'); + $this->assertInstanceOf( + get_class($config), + $config->c, + 'ConfigObjects do not convert arrays to config objects when set' + ); + } + + /** + * @expectedException LogicException + */ + public function testWhetherItIsNotPossibleToAppendProperties() + { + $config = new ConfigObject(); + $config[] = 'test'; + } + + public function testWhetherItIsPossibleToUnsetPropertiesAndSections() + { + $config = new ConfigObject(array('a' => 'b', 'c' => array('d' => 'e'))); + unset($config->a); + unset($config['c']); + + $this->assertFalse(isset($config->a), 'ConfigObjects do not allow to unset properties'); + $this->assertFalse(isset($config->c), 'ConfigObjects do not allow to unset sections'); + } + + /** + * @depends testWhetherConfigObjectsAreCountable + */ + public function testWhetherOneCanCheckIfAConfigObjectHasAnyPropertiesOrSections() + { + $config = new ConfigObject(); + $this->assertTrue($config->isEmpty(), 'ConfigObjects do not report that they are empty'); + + $config->test = 'test'; + $this->assertFalse($config->isEmpty(), 'ConfigObjects do report that they are empty although they are not'); + } + + /** + * @depends testWhetherItIsPossibleToAccessProperties + */ + public function testWhetherItIsPossibleToRetrieveDefaultValuesForNonExistentPropertiesOrSections() + { + $config = new ConfigObject(array('a' => 'b')); + + $this->assertEquals( + 'b', + $config->get('a'), + 'ConfigObjects do not return the actual value of existing properties' + ); + $this->assertNull( + $config->get('b'), + 'ConfigObjects do not return NULL as default for non-existent properties' + ); + $this->assertEquals( + 'test', + $config->get('test', 'test'), + 'ConfigObjects do not allow to define the default value to return for non-existent properties' + ); + } + + public function testWhetherItIsPossibleToRetrieveAllPropertyAndSectionNames() + { + $config = new ConfigObject(array('a' => 'b', 'c' => array('d' => 'e'))); + + $this->assertEquals( + array('a', 'c'), + $config->keys(), + 'ConfigObjects do not list property and section names correctly' + ); + } + + public function testWhetherConfigObjectsCanBeConvertedToArrays() + { + $config = new ConfigObject(array('a' => 'b', 'c' => array('d' => 'e'))); + + $this->assertEquals( + array('a' => 'b', 'c' => array('d' => 'e')), + $config->toArray(), + 'ConfigObjects cannot be correctly converted to arrays' + ); + } + + /** + * @depends testWhetherConfigObjectsCanBeConvertedToArrays + */ + public function testWhetherItIsPossibleToMergeConfigObjects() + { + $config = new ConfigObject(array('a' => 'b')); + + $config->merge(array('a' => 'bb', 'c' => 'd', 'e' => array('f' => 'g'))); + $this->assertEquals( + array('a' => 'bb', 'c' => 'd', 'e' => array('f' => 'g')), + $config->toArray(), + 'ConfigObjects cannot be extended with arrays' + ); + + $config->merge(new ConfigObject(array('c' => array('d' => 'ee'), 'e' => array('h' => 'i')))); + $this->assertEquals( + array('a' => 'bb', 'c' => array('d' => 'ee'), 'e' => array('f' => 'g', 'h' => 'i')), + $config->toArray(), + 'ConfigObjects cannot be extended with other ConfigObjects' + ); + } +} From 7621f6642db38c0b610c0d40c041b4418aee8116 Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 18 Nov 2014 13:11:52 +0100 Subject: [PATCH 04/17] Adjust usages of Icinga\Application\Config refs #7147 --- application/controllers/ConfigController.php | 6 +- .../controllers/DashboardController.php | 4 +- application/controllers/ListController.php | 4 +- .../controllers/PreferenceController.php | 4 +- .../Config/Authentication/DbBackendForm.php | 4 +- .../Config/Authentication/LdapBackendForm.php | 4 +- .../AuthenticationBackendConfigForm.php | 33 +++++---- .../forms/Config/GeneralConfigForm.php | 2 +- .../forms/Config/Resource/DbResourceForm.php | 4 +- .../Config/Resource/LdapResourceForm.php | 4 +- .../Resource/LivestatusResourceForm.php | 4 +- .../forms/Config/ResourceConfigForm.php | 22 +++--- application/forms/LdapDiscoveryForm.php | 4 +- .../views/scripts/config/resource.phtml | 2 +- .../Application/ApplicationBootstrap.php | 9 +-- library/Icinga/Application/Cli.php | 4 +- library/Icinga/Application/Logger.php | 14 ++-- .../Icinga/Application/Logger/LogWriter.php | 6 +- .../Application/Logger/Writer/FileWriter.php | 6 +- .../Logger/Writer/SyslogWriter.php | 6 +- library/Icinga/Application/Modules/Module.php | 3 +- library/Icinga/Application/Web.php | 4 +- .../Icinga/Authentication/AdmissionLoader.php | 9 +-- library/Icinga/Authentication/AuthChain.php | 20 ++++-- .../Backend/AutoLoginBackend.php | 6 +- library/Icinga/Authentication/Manager.php | 3 +- library/Icinga/Authentication/UserBackend.php | 4 +- .../Authentication/UserGroupBackend.php | 8 +-- library/Icinga/Data/Db/DbConnection.php | 8 +-- library/Icinga/Data/ResourceFactory.php | 25 ++----- library/Icinga/Protocol/File/FileReader.php | 6 +- library/Icinga/Protocol/Ldap/Connection.php | 5 +- library/Icinga/Test/BaseTestCase.php | 6 +- .../User/Preferences/PreferencesStore.php | 23 ++++--- .../User/Preferences/Store/IniStore.php | 2 +- library/Icinga/Web/Menu.php | 17 ++--- library/Icinga/Web/Widget/Dashboard.php | 4 +- .../Icinga/Web/Widget/Dashboard/Component.php | 10 +-- library/Icinga/Web/Widget/Dashboard/Pane.php | 6 +- .../forms/Config/BackendConfigForm.php | 20 +++--- .../forms/Config/InstanceConfigForm.php | 20 +++--- .../forms/Config/SecurityConfigForm.php | 6 +- .../Monitoring/Backend/MonitoringBackend.php | 13 ++-- .../library/Monitoring/BackendStep.php | 4 +- .../Command/Transport/CommandTransport.php | 11 +-- .../library/Monitoring/InstanceStep.php | 2 +- .../Monitoring/Object/MonitoredObject.php | 5 +- .../library/Monitoring/SecurityStep.php | 2 +- .../test/php/regression/Bug7043Test.php | 3 +- .../application/forms/AdminAccountPage.php | 6 +- .../application/forms/AuthBackendPage.php | 6 +- .../forms/LdapDiscoveryConfirmPage.php | 6 +- .../Setup/Steps/AuthenticationStep.php | 7 +- .../library/Setup/Steps/GeneralConfigStep.php | 2 +- .../library/Setup/Steps/ResourceStep.php | 2 +- .../Authentication/DbBackendFormTest.php | 4 +- .../Authentication/LdapBackendFormTest.php | 4 +- .../AuthenticationBackendReorderFormTest.php | 2 +- .../Config/Resource/DbResourceFormTest.php | 2 +- .../Config/Resource/LdapResourceFormTest.php | 2 +- .../Resource/LivestatusResourceFormTest.php | 2 +- .../library/Icinga/File/Ini/IniWriterTest.php | 68 +++++++++---------- .../Icinga/Logger/Writer/StreamWriterTest.php | 6 +- .../Icinga/Protocol/Ldap/QueryTest.php | 4 +- .../library/Icinga/User/Store/DbStoreTest.php | 4 +- .../Icinga/User/Store/IniStoreTest.php | 4 +- test/php/library/Icinga/Web/MenuTest.php | 14 ++-- 67 files changed, 275 insertions(+), 271 deletions(-) diff --git a/application/controllers/ConfigController.php b/application/controllers/ConfigController.php index 11d011bc0..105338dfb 100644 --- a/application/controllers/ConfigController.php +++ b/application/controllers/ConfigController.php @@ -212,7 +212,7 @@ class ConfigController extends ActionController */ public function resourceAction() { - $this->view->resources = Config::app('resources', true)->toArray(); + $this->view->resources = Config::app('resources', true)->keys(); $this->view->tabs->activate('resources'); } @@ -274,9 +274,9 @@ class ConfigController extends ActionController // Check if selected resource is currently used for authentication $resource = $this->getRequest()->getQuery('resource'); - $authConfig = Config::app('authentication')->toArray(); + $authConfig = Config::app('authentication'); foreach ($authConfig as $backendName => $config) { - if (array_key_exists('resource', $config) && $config['resource'] === $resource) { + if ($config->get('resource') === $resource) { $form->addError(sprintf( $this->translate( 'The resource "%s" is currently in use by the authentication backend "%s". ' . diff --git a/application/controllers/DashboardController.php b/application/controllers/DashboardController.php index d357231ca..e1e9e14c2 100644 --- a/application/controllers/DashboardController.php +++ b/application/controllers/DashboardController.php @@ -37,7 +37,7 @@ class DashboardController extends ActionController $dashboard = new Dashboard(); try { $dashboardConfig = Config::app($config); - if (count($dashboardConfig) === 0) { + if ($dashboardConfig->isEmpty()) { return null; } $dashboard->readConfig($dashboardConfig); @@ -93,7 +93,7 @@ class DashboardController extends ActionController ); $configFile = Config::app('dashboard/dashboard')->getConfigFile(); - if ($this->writeConfiguration(new Config($dashboard->toArray()), $configFile)) { + if ($this->writeConfiguration(Config::fromArray($dashboard->toArray()), $configFile)) { $this->redirectNow(Url::fromPath('dashboard', array('pane' => $form->getValue('pane')))); } else { $this->render('showConfiguration'); diff --git a/application/controllers/ListController.php b/application/controllers/ListController.php index 8efc3fc11..f8b0ed1d6 100644 --- a/application/controllers/ListController.php +++ b/application/controllers/ListController.php @@ -5,7 +5,7 @@ use Icinga\Module\Monitoring\Controller; use Icinga\Web\Url; use Icinga\Application\Logger; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Protocol\File\FileReader; use \Zend_Controller_Action_Exception as ActionError; @@ -48,7 +48,7 @@ class ListController extends Controller . ' - (?.*)$/'; // message $loggerWriter = Logger::getInstance()->getWriter(); - $resource = new FileReader(new Config(array( + $resource = new FileReader(new ConfigObject(array( 'filename' => $loggerWriter->getPath(), 'fields' => $pattern ))); diff --git a/application/controllers/PreferenceController.php b/application/controllers/PreferenceController.php index 378a5aa34..7acab7c25 100644 --- a/application/controllers/PreferenceController.php +++ b/application/controllers/PreferenceController.php @@ -39,8 +39,8 @@ class PreferenceController extends BasePreferenceController */ public function indexAction() { - $storeConfig = Config::app()->preferences; - if ($storeConfig === null) { + $storeConfig = Config::app()->getSection('preferences'); + if ($storeConfig->isEmpty()) { throw new ConfigurationError(t('You need to configure how to store preferences first.')); } diff --git a/application/forms/Config/Authentication/DbBackendForm.php b/application/forms/Config/Authentication/DbBackendForm.php index 4cf015db8..31e6b2472 100644 --- a/application/forms/Config/Authentication/DbBackendForm.php +++ b/application/forms/Config/Authentication/DbBackendForm.php @@ -5,8 +5,8 @@ namespace Icinga\Forms\Config\Authentication; use Exception; -use Icinga\Application\Config; use Icinga\Web\Form; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Authentication\Backend\DbUserBackend; @@ -121,7 +121,7 @@ class DbBackendForm extends Form /** * Return the configuration for the chosen resource * - * @return Config + * @return ConfigObject */ public function getResourceConfig() { diff --git a/application/forms/Config/Authentication/LdapBackendForm.php b/application/forms/Config/Authentication/LdapBackendForm.php index 3e5c2b305..3be140fb8 100644 --- a/application/forms/Config/Authentication/LdapBackendForm.php +++ b/application/forms/Config/Authentication/LdapBackendForm.php @@ -5,8 +5,8 @@ namespace Icinga\Forms\Config\Authentication; use Exception; -use Icinga\Application\Config; use Icinga\Web\Form; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Exception\AuthenticationException; use Icinga\Authentication\Backend\LdapUserBackend; @@ -156,7 +156,7 @@ class LdapBackendForm extends Form /** * Return the configuration for the chosen resource * - * @return Config + * @return ConfigObject */ public function getResourceConfig() { diff --git a/application/forms/Config/AuthenticationBackendConfigForm.php b/application/forms/Config/AuthenticationBackendConfigForm.php index c21ccf8f2..12f407c69 100644 --- a/application/forms/Config/AuthenticationBackendConfigForm.php +++ b/application/forms/Config/AuthenticationBackendConfigForm.php @@ -9,6 +9,7 @@ use Icinga\Forms\ConfigForm; use Icinga\Web\Notification; use Icinga\Application\Config; use Icinga\Application\Platform; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Exception\ConfigurationError; use Icinga\Forms\Config\Authentication\DbBackendForm; @@ -91,12 +92,12 @@ class AuthenticationBackendConfigForm extends ConfigForm $name = isset($values['name']) ? $values['name'] : ''; if (! $name) { throw new InvalidArgumentException(t('Authentication backend name missing')); - } elseif ($this->config->get($name) !== null) { + } elseif ($this->config->hasSection($name)) { throw new InvalidArgumentException(t('Authentication backend already exists')); } unset($values['name']); - $this->config->{$name} = $values; + $this->config->setSection($name, $values); return $this; } @@ -116,18 +117,19 @@ class AuthenticationBackendConfigForm extends ConfigForm throw new InvalidArgumentException(t('Old authentication backend name missing')); } elseif (! ($newName = isset($values['name']) ? $values['name'] : '')) { throw new InvalidArgumentException(t('New authentication backend name missing')); - } elseif (($backendConfig = $this->config->get($name)) === null) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(t('Unknown authentication backend provided')); } + $backendConfig = $this->config->getSection($name); if ($newName !== $name) { // Only remove the old entry if it has changed as the order gets screwed when editing backend names - unset($this->config->{$name}); + $this->config->removeSection($name); } unset($values['name']); - $this->config->{$newName} = array_merge($backendConfig->toArray(), $values); - return $this->config->{$newName}; + $this->config->setSection($newName, $backendConfig->merge($values)); + return $backendConfig; } /** @@ -143,11 +145,12 @@ class AuthenticationBackendConfigForm extends ConfigForm { if (! $name) { throw new InvalidArgumentException(t('Authentication backend name missing')); - } elseif (($backendConfig = $this->config->get($name)) === null) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(t('Unknown authentication backend provided')); } - unset($this->config->{$name}); + $backendConfig = $this->config->getSection($name); + $this->config->removeSection($name); return $backendConfig; } @@ -165,7 +168,7 @@ class AuthenticationBackendConfigForm extends ConfigForm { if (! $name) { throw new InvalidArgumentException(t('Authentication backend name missing')); - } elseif ($this->config->get($name) === null) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(t('Unknown authentication backend provided')); } @@ -175,10 +178,10 @@ class AuthenticationBackendConfigForm extends ConfigForm $newConfig = array(); foreach ($backendOrder as $backendName) { - $newConfig[$backendName] = $this->config->get($backendName); + $newConfig[$backendName] = $this->config->getSection($backendName); } - $config = new Config($newConfig); + $config = Config::fromArray($newConfig); $this->config = $config->setConfigFile($this->config->getConfigFile()); return $this; } @@ -235,13 +238,13 @@ class AuthenticationBackendConfigForm extends ConfigForm if ($authBackend !== null) { if ($authBackend === '') { throw new ConfigurationError(t('Authentication backend name missing')); - } elseif (false === isset($this->config->{$authBackend})) { + } elseif (! $this->config->hasSection($authBackend)) { throw new ConfigurationError(t('Unknown authentication backend provided')); - } elseif (false === isset($this->config->{$authBackend}->backend)) { + } elseif ($this->config->getSection($authBackend)->backend === null) { throw new ConfigurationError(sprintf(t('Backend "%s" has no `backend\' setting'), $authBackend)); } - $configValues = $this->config->{$authBackend}->toArray(); + $configValues = $this->config->getSection($authBackend)->toArray(); $configValues['type'] = $configValues['backend']; $configValues['name'] = $authBackend; $this->populate($configValues); @@ -332,7 +335,7 @@ class AuthenticationBackendConfigForm extends ConfigForm /** * Return the configuration for the chosen resource * - * @return Config + * @return ConfigObject */ public function getResourceConfig() { diff --git a/application/forms/Config/GeneralConfigForm.php b/application/forms/Config/GeneralConfigForm.php index 69fd0fc19..0d81bb96b 100644 --- a/application/forms/Config/GeneralConfigForm.php +++ b/application/forms/Config/GeneralConfigForm.php @@ -48,7 +48,7 @@ class GeneralConfigForm extends ConfigForm $sections[$section][$property] = $value; } foreach ($sections as $section => $config) { - $this->config->{$section} = $config; + $this->config->setSection($section, $config); } if ($this->save()) { diff --git a/application/forms/Config/Resource/DbResourceForm.php b/application/forms/Config/Resource/DbResourceForm.php index b1d54c704..d5197c94e 100644 --- a/application/forms/Config/Resource/DbResourceForm.php +++ b/application/forms/Config/Resource/DbResourceForm.php @@ -5,8 +5,8 @@ namespace Icinga\Forms\Config\Resource; use Exception; -use Icinga\Application\Config; use Icinga\Web\Form; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Application\Platform; @@ -129,7 +129,7 @@ class DbResourceForm extends Form public static function isValidResource(Form $form) { try { - $resource = ResourceFactory::createResource(new Config($form->getValues())); + $resource = ResourceFactory::createResource(new ConfigObject($form->getValues())); $resource->getConnection()->getConnection(); } catch (Exception $e) { $form->addError(t('Connectivity validation failed, connection to the given resource not possible.')); diff --git a/application/forms/Config/Resource/LdapResourceForm.php b/application/forms/Config/Resource/LdapResourceForm.php index 6c29a09d6..6641b96bb 100644 --- a/application/forms/Config/Resource/LdapResourceForm.php +++ b/application/forms/Config/Resource/LdapResourceForm.php @@ -5,8 +5,8 @@ namespace Icinga\Forms\Config\Resource; use Exception; -use Icinga\Application\Config; use Icinga\Web\Form; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; /** @@ -110,7 +110,7 @@ class LdapResourceForm extends Form public static function isValidResource(Form $form) { try { - $resource = ResourceFactory::createResource(new Config($form->getValues())); + $resource = ResourceFactory::createResource(new ConfigObject($form->getValues())); if (false === $resource->testCredentials( $form->getElement('bind_dn')->getValue(), $form->getElement('bind_pw')->getValue() diff --git a/application/forms/Config/Resource/LivestatusResourceForm.php b/application/forms/Config/Resource/LivestatusResourceForm.php index e4dae844b..d90600370 100644 --- a/application/forms/Config/Resource/LivestatusResourceForm.php +++ b/application/forms/Config/Resource/LivestatusResourceForm.php @@ -5,9 +5,9 @@ namespace Icinga\Forms\Config\Resource; use Exception; -use Icinga\Application\Config; use Icinga\Web\Form; use Icinga\Application\Icinga; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; /** @@ -73,7 +73,7 @@ class LivestatusResourceForm extends Form public static function isValidResource(Form $form) { try { - $resource = ResourceFactory::createResource(new Config($form->getValues())); + $resource = ResourceFactory::createResource(new ConfigObject($form->getValues())); $resource->connect()->disconnect(); } catch (Exception $e) { $form->addError(t('Connectivity validation failed, connection to the given resource not possible.')); diff --git a/application/forms/Config/ResourceConfigForm.php b/application/forms/Config/ResourceConfigForm.php index d5faca1cd..fe3b9957d 100644 --- a/application/forms/Config/ResourceConfigForm.php +++ b/application/forms/Config/ResourceConfigForm.php @@ -63,12 +63,12 @@ class ResourceConfigForm extends ConfigForm $name = isset($values['name']) ? $values['name'] : ''; if (! $name) { throw new InvalidArgumentException(t('Resource name missing')); - } elseif ($this->config->{$name} !== null) { + } elseif ($this->config->hasSection($name)) { throw new InvalidArgumentException(t('Resource already exists')); } unset($values['name']); - $this->config->{$name} = $values; + $this->config->setSection($name, $values); return $this; } @@ -88,14 +88,15 @@ class ResourceConfigForm extends ConfigForm throw new InvalidArgumentException(t('Old resource name missing')); } elseif (! ($newName = isset($values['name']) ? $values['name'] : '')) { throw new InvalidArgumentException(t('New resource name missing')); - } elseif (($resourceConfig = $this->config->get($name)) === null) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(t('Unknown resource provided')); } + $resourceConfig = $this->config->getSection($name); + $this->config->removeSection($name); unset($values['name']); - unset($this->config->{$name}); - $this->config->{$newName} = array_merge($resourceConfig->toArray(), $values); - return $this->config->{$newName}; + $this->config->setSection($newName, $resourceConfig->merge($values)); + return $resourceConfig; } /** @@ -111,11 +112,12 @@ class ResourceConfigForm extends ConfigForm { if (! $name) { throw new InvalidArgumentException(t('Resource name missing')); - } elseif (($resourceConfig = $this->config->get($name)) === null) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(t('Unknown resource provided')); } - unset($this->config->{$name}); + $resourceConfig = $this->config->getSection($name); + $this->config->removeSection($name); return $resourceConfig; } @@ -171,11 +173,11 @@ class ResourceConfigForm extends ConfigForm if ($resource !== null) { if ($resource === '') { throw new ConfigurationError(t('Resource name missing')); - } elseif (false === isset($this->config->{$resource})) { + } elseif (! $this->config->hasSection($resource)) { throw new ConfigurationError(t('Unknown resource provided')); } - $configValues = $this->config->{$resource}->toArray(); + $configValues = $this->config->getSection($resource)->toArray(); $configValues['name'] = $resource; $this->populate($configValues); } diff --git a/application/forms/LdapDiscoveryForm.php b/application/forms/LdapDiscoveryForm.php index 9e5af79ac..36f11deae 100644 --- a/application/forms/LdapDiscoveryForm.php +++ b/application/forms/LdapDiscoveryForm.php @@ -2,8 +2,8 @@ namespace Icinga\Forms; -use Icinga\Application\Config; use Icinga\Application\Logger; +use Icinga\Data\ConfigObject; use Icinga\Protocol\Ldap\Exception as LdapException; use Icinga\Protocol\Ldap\Connection; use Icinga\Protocol\Dns; @@ -143,7 +143,7 @@ class LdapDiscoveryForm extends Form private function discoverCapabilities($config) { - $conn = new Connection(new Config($config)); + $conn = new Connection(new ConfigObject($config)); try { $conn->connect(); $this->capabilities = $conn->getCapabilities(); diff --git a/application/views/scripts/config/resource.phtml b/application/views/scripts/config/resource.phtml index 73ce6dae3..a2368fb9c 100644 --- a/application/views/scripts/config/resource.phtml +++ b/application/views/scripts/config/resource.phtml @@ -13,7 +13,7 @@ translate('Remove'); ?> -resources as $name => $resource): ?> +resources as $name): ?> diff --git a/library/Icinga/Application/ApplicationBootstrap.php b/library/Icinga/Application/ApplicationBootstrap.php index 5e10072cf..7f1667e5b 100644 --- a/library/Icinga/Application/ApplicationBootstrap.php +++ b/library/Icinga/Application/ApplicationBootstrap.php @@ -8,6 +8,7 @@ use ErrorException; use Exception; use LogicException; use Icinga\Application\Modules\Manager as ModuleManager; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Exception\ConfigurationError; use Icinga\Exception\NotReadableError; @@ -372,7 +373,7 @@ abstract class ApplicationBootstrap $this->moduleManager = new ModuleManager( $this, $this->configDir . '/enabledModules', - explode(':', $this->config->fromSection('global', 'module_path', $this->baseDir . '/modules')) + explode(':', $this->config->get('global', 'module_path', $this->baseDir . '/modules')) ); return $this; } @@ -415,7 +416,7 @@ abstract class ApplicationBootstrap protected function setupLogging() { Logger::create( - new Config( + new ConfigObject( array( 'log' => 'syslog' ) @@ -476,9 +477,9 @@ abstract class ApplicationBootstrap */ protected function setupLogger() { - if (($loggingConfig = $this->config->logging) !== null) { + if ($this->config->hasSection('logging')) { try { - Logger::create($loggingConfig); + Logger::create($this->config->getSection('logging')); } catch (ConfigurationError $e) { Logger::error($e); } diff --git a/library/Icinga/Application/Cli.php b/library/Icinga/Application/Cli.php index 9f14b6c20..abf46262f 100644 --- a/library/Icinga/Application/Cli.php +++ b/library/Icinga/Application/Cli.php @@ -4,7 +4,6 @@ namespace Icinga\Application; -use Icinga\Application\Config; use Icinga\Application\Platform; use Icinga\Application\ApplicationBootstrap; use Icinga\Cli\Params; @@ -12,6 +11,7 @@ use Icinga\Cli\Loader; use Icinga\Cli\Screen; use Icinga\Application\Logger; use Icinga\Application\Benchmark; +use Icinga\Data\ConfigObject; use Icinga\Exception\ProgrammingError; require_once __DIR__ . '/ApplicationBootstrap.php'; @@ -50,7 +50,7 @@ class Cli extends ApplicationBootstrap protected function setupLogging() { Logger::create( - new Config( + new ConfigObject( array( 'level' => Logger::INFO, 'log' => 'stdout', diff --git a/library/Icinga/Application/Logger.php b/library/Icinga/Application/Logger.php index f74c6d021..70eaa774b 100644 --- a/library/Icinga/Application/Logger.php +++ b/library/Icinga/Application/Logger.php @@ -5,7 +5,7 @@ namespace Icinga\Application; use Exception; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Application\Logger\Writer\FileWriter; use Icinga\Application\Logger\Writer\SyslogWriter; use Icinga\Exception\ConfigurationError; @@ -71,12 +71,12 @@ class Logger /** * Create a new logger object * - * @param Config $config + * @param ConfigObject $config * * @throws ConfigurationError If the logging configuration directive 'log' is missing or if the logging level is * not defined */ - public function __construct(Config $config) + public function __construct(ConfigObject $config) { if ($config->log === null) { throw new ConfigurationError('Required logging configuration directive \'log\' missing'); @@ -118,11 +118,11 @@ class Logger /** * Create a new logger object * - * @param Config $config + * @param ConfigObject $config * * @return static */ - public static function create(Config $config) + public static function create(ConfigObject $config) { static::$instance = new static($config); return static::$instance; @@ -131,12 +131,12 @@ class Logger /** * Create a log writer * - * @param Config $config The configuration to initialize the writer with + * @param ConfigObject $config The configuration to initialize the writer with * * @return \Icinga\Application\Logger\LogWriter The requested log writer * @throws ConfigurationError If the requested writer cannot be found */ - protected function createWriter(Config $config) + protected function createWriter(ConfigObject $config) { $class = 'Icinga\\Application\\Logger\\Writer\\' . ucfirst(strtolower($config->log)) . 'Writer'; if (! class_exists($class)) { diff --git a/library/Icinga/Application/Logger/LogWriter.php b/library/Icinga/Application/Logger/LogWriter.php index 831c96fe8..b89fec62f 100644 --- a/library/Icinga/Application/Logger/LogWriter.php +++ b/library/Icinga/Application/Logger/LogWriter.php @@ -4,7 +4,7 @@ namespace Icinga\Application\Logger; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; /** * Abstract class for writers that write messages to a log @@ -12,14 +12,14 @@ use Icinga\Application\Config; abstract class LogWriter { /** - * @var Zend_Config + * @var ConfigObject */ protected $config; /** * Create a new log writer initialized with the given configuration */ - public function __construct(Config $config) + public function __construct(ConfigObject $config) { $this->config = $config; } diff --git a/library/Icinga/Application/Logger/Writer/FileWriter.php b/library/Icinga/Application/Logger/Writer/FileWriter.php index eec3b038f..2f5a292ec 100644 --- a/library/Icinga/Application/Logger/Writer/FileWriter.php +++ b/library/Icinga/Application/Logger/Writer/FileWriter.php @@ -5,7 +5,7 @@ namespace Icinga\Application\Logger\Writer; use Exception; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Application\Logger; use Icinga\Application\Logger\LogWriter; use Icinga\Exception\ConfigurationError; @@ -26,12 +26,12 @@ class FileWriter extends LogWriter /** * Create a new file log writer * - * @param Config $config + * @param ConfigObject $config * * @throws ConfigurationError If the configuration directive 'file' is missing or if the path to 'file' does * not exist or if writing to 'file' is not possible */ - public function __construct(Config $config) + public function __construct(ConfigObject $config) { if ($config->file === null) { throw new ConfigurationError('Required logging configuration directive \'file\' missing'); diff --git a/library/Icinga/Application/Logger/Writer/SyslogWriter.php b/library/Icinga/Application/Logger/Writer/SyslogWriter.php index 6c39eee28..7a69e4cba 100644 --- a/library/Icinga/Application/Logger/Writer/SyslogWriter.php +++ b/library/Icinga/Application/Logger/Writer/SyslogWriter.php @@ -4,7 +4,7 @@ namespace Icinga\Application\Logger\Writer; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Application\Logger; use Icinga\Application\Logger\LogWriter; @@ -51,9 +51,9 @@ class SyslogWriter extends LogWriter /** * Create a new syslog log writer * - * @param Config $config + * @param ConfigObject $config */ - public function __construct(Config $config) + public function __construct(ConfigObject $config) { $this->ident = $config->get('application', 'icingaweb'); $this->facility = static::$facilities['user']; diff --git a/library/Icinga/Application/Modules/Module.php b/library/Icinga/Application/Modules/Module.php index 443a39e32..8c01eb05e 100644 --- a/library/Icinga/Application/Modules/Module.php +++ b/library/Icinga/Application/Modules/Module.php @@ -12,6 +12,7 @@ use Icinga\Application\ApplicationBootstrap; use Icinga\Application\Config; use Icinga\Application\Icinga; use Icinga\Application\Logger; +use Icinga\Data\ConfigObject; use Icinga\Util\Translator; use Icinga\Web\Hook; use Icinga\Web\Menu; @@ -242,7 +243,7 @@ class Module if (array_key_exists($name, $this->menuItems)) { $this->menuItems[$name]->setProperties($properties); } else { - $this->menuItems[$name] = new Menu($name, new Config($properties)); + $this->menuItems[$name] = new Menu($name, new ConfigObject($properties)); } return $this->menuItems[$name]; diff --git a/library/Icinga/Application/Web.php b/library/Icinga/Application/Web.php index f227df247..37ec5138a 100644 --- a/library/Icinga/Application/Web.php +++ b/library/Icinga/Application/Web.php @@ -259,9 +259,7 @@ class Web extends ApplicationBootstrap $view->view->addHelperPath($this->getApplicationDir('/views/helpers')); $view->view->setEncoding('UTF-8'); - $view->view->headTitle()->prepend( - $this->config->global !== null ? $this->config->global->get('project', 'Icinga') : 'Icinga' - ); + $view->view->headTitle()->prepend($this->config->get('global', 'project', 'Icinga')); $view->view->headTitle()->setSeparator(' :: '); diff --git a/library/Icinga/Authentication/AdmissionLoader.php b/library/Icinga/Authentication/AdmissionLoader.php index 50624003c..65d99f427 100644 --- a/library/Icinga/Authentication/AdmissionLoader.php +++ b/library/Icinga/Authentication/AdmissionLoader.php @@ -6,6 +6,7 @@ namespace Icinga\Authentication; use Icinga\Application\Config; use Icinga\Exception\NotReadableError; +use Icinga\Data\ConfigObject; use Icinga\User; use Icinga\Util\String; @@ -15,13 +16,13 @@ use Icinga\Util\String; class AdmissionLoader { /** - * @param string $username - * @param array $userGroups - * @param mixed $section + * @param string $username + * @param array $userGroups + * @param ConfigObject $section * * @return bool */ - protected function match($username, $userGroups, $section) + protected function match($username, $userGroups, ConfigObject $section) { $username = strtolower($username); if (! empty($section->users)) { diff --git a/library/Icinga/Authentication/AuthChain.php b/library/Icinga/Authentication/AuthChain.php index d704f2932..24c12c9de 100644 --- a/library/Icinga/Authentication/AuthChain.php +++ b/library/Icinga/Authentication/AuthChain.php @@ -5,6 +5,7 @@ namespace Icinga\Authentication; use Iterator; +use Icinga\Data\ConfigObject; use Icinga\Application\Config; use Icinga\Application\Logger; use Icinga\Exception\ConfigurationError; @@ -40,11 +41,13 @@ class AuthChain implements Iterator /** * Rewind the chain + * + * @return ConfigObject */ public function rewind() { - $this->config->rewind(); $this->currentBackend = null; + return $this->config->rewind(); } /** @@ -60,7 +63,7 @@ class AuthChain implements Iterator /** * Return the key of the current user backend config * - * @return string + * @return string */ public function key() { @@ -69,16 +72,18 @@ class AuthChain implements Iterator /** * Move forward to the next user backend config + * + * @return ConfigObject */ public function next() { - $this->config->next(); + return $this->config->next(); } /** - * Check if the current user backend is valid, i.e. it's enabled and the config's valid + * Check if the current user backend is valid, i.e. it's enabled and the config is valid * - * @return bool + * @return bool */ public function valid() { @@ -86,13 +91,15 @@ class AuthChain implements Iterator // Stop when there are no more backends to check return false; } + $backendConfig = $this->config->current(); if ((bool) $backendConfig->get('disabled', false) === true) { $this->next(); return $this->valid(); } + + $name = $this->key(); try { - $name = $this->key(); $backend = UserBackend::create($name, $backendConfig); } catch (ConfigurationError $e) { Logger::error( @@ -105,6 +112,7 @@ class AuthChain implements Iterator $this->next(); return $this->valid(); } + $this->currentBackend = $backend; return true; } diff --git a/library/Icinga/Authentication/Backend/AutoLoginBackend.php b/library/Icinga/Authentication/Backend/AutoLoginBackend.php index 990797088..b4a70bd4f 100644 --- a/library/Icinga/Authentication/Backend/AutoLoginBackend.php +++ b/library/Icinga/Authentication/Backend/AutoLoginBackend.php @@ -4,8 +4,8 @@ namespace Icinga\Authentication\Backend; -use Icinga\Application\Config; use Icinga\Authentication\UserBackend; +use Icinga\Data\ConfigObject; use Icinga\User; /** @@ -23,9 +23,9 @@ class AutoLoginBackend extends UserBackend /** * Create new autologin backend * - * @param Config $config + * @param ConfigObject $config */ - public function __construct(Config $config) + public function __construct(ConfigObject $config) { $this->stripUsernameRegexp = $config->get('strip_username_regexp'); } diff --git a/library/Icinga/Authentication/Manager.php b/library/Icinga/Authentication/Manager.php index 64d5f5336..88258351e 100644 --- a/library/Icinga/Authentication/Manager.php +++ b/library/Icinga/Authentication/Manager.php @@ -63,7 +63,8 @@ class Manager ); $config = new Config(); } - if (($preferencesConfig = $config->preferences) !== null) { + if ($config->hasSection('preferences')) { + $preferencesConfig = $config->getSection('preferences'); try { $preferencesStore = PreferencesStore::create( $preferencesConfig, diff --git a/library/Icinga/Authentication/UserBackend.php b/library/Icinga/Authentication/UserBackend.php index 494ada4aa..eaf39e49d 100644 --- a/library/Icinga/Authentication/UserBackend.php +++ b/library/Icinga/Authentication/UserBackend.php @@ -6,9 +6,9 @@ namespace Icinga\Authentication; use Countable; use Icinga\Authentication\Backend\AutoLoginBackend; -use Icinga\Application\Config; use Icinga\Authentication\Backend\DbUserBackend; use Icinga\Authentication\Backend\LdapUserBackend; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Exception\ConfigurationError; use Icinga\User; @@ -45,7 +45,7 @@ abstract class UserBackend implements Countable return $this->name; } - public static function create($name, Config $backendConfig) + public static function create($name, ConfigObject $backendConfig) { if ($backendConfig->name !== null) { $name = $backendConfig->name; diff --git a/library/Icinga/Authentication/UserGroupBackend.php b/library/Icinga/Authentication/UserGroupBackend.php index b41ef3f13..f1a41adcb 100644 --- a/library/Icinga/Authentication/UserGroupBackend.php +++ b/library/Icinga/Authentication/UserGroupBackend.php @@ -4,9 +4,9 @@ namespace Icinga\Authentication; -use Icinga\Application\Config; use Icinga\Authentication\Backend\DbUserGroupBackend; use Icinga\Authentication\Backend\IniUserGroupBackend; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Exception\ConfigurationError; use Icinga\Exception\IcingaException; @@ -50,13 +50,13 @@ abstract class UserGroupBackend /** * Create a user group backend * - * @param string $name - * @param Config $backendConfig + * @param string $name + * @param ConfigObject $backendConfig * * @return DbUserGroupBackend|IniUserGroupBackend * @throws ConfigurationError If the backend configuration is invalid */ - public static function create($name, Config $backendConfig) + public static function create($name, ConfigObject $backendConfig) { if ($backendConfig->name !== null) { $name = $backendConfig->name; diff --git a/library/Icinga/Data/Db/DbConnection.php b/library/Icinga/Data/Db/DbConnection.php index 82686893d..38153a1cf 100644 --- a/library/Icinga/Data/Db/DbConnection.php +++ b/library/Icinga/Data/Db/DbConnection.php @@ -6,8 +6,8 @@ namespace Icinga\Data\Db; use PDO; use Zend_Db; -use Icinga\Application\Config; use Icinga\Application\Benchmark; +use Icinga\Data\ConfigObject; use Icinga\Data\Db\DbQuery; use Icinga\Data\ResourceFactory; use Icinga\Data\Selectable; @@ -21,7 +21,7 @@ class DbConnection implements Selectable /** * Connection config * - * @var Config + * @var ConfigObject */ private $config; @@ -59,9 +59,9 @@ class DbConnection implements Selectable /** * Create a new connection object * - * @param Config $config + * @param ConfigObject $config */ - public function __construct(Config $config = null) + public function __construct(ConfigObject $config = null) { $this->config = $config; if (isset($config->prefix)) { diff --git a/library/Icinga/Data/ResourceFactory.php b/library/Icinga/Data/ResourceFactory.php index f938ea9a5..754360740 100644 --- a/library/Icinga/Data/ResourceFactory.php +++ b/library/Icinga/Data/ResourceFactory.php @@ -40,14 +40,15 @@ class ResourceFactory implements ConfigAwareFactory * * @param $resourceName String The resource's name * - * @return Config The configuration of the resource + * @return ConfigObject The configuration of the resource * * @throws ConfigurationError */ public static function getResourceConfig($resourceName) { self::assertResourcesExist(); - if (($resourceConfig = self::$resources->get($resourceName)) === null) { + $resourceConfig = self::$resources->getSection($resourceName); + if ($resourceConfig->isEmpty()) { throw new ConfigurationError( 'Cannot load resource config "%s". Resource does not exist', $resourceName @@ -59,24 +60,12 @@ class ResourceFactory implements ConfigAwareFactory /** * Return the configuration of all existing resources, or get all resources of a given type. * - * @param String|null $type Fetch only resources that have the given type. - * * @return Config The configuration containing all resources */ - public static function getResourceConfigs($type = null) + public static function getResourceConfigs() { self::assertResourcesExist(); - if (!isset($type)) { - return self::$resources; - } else { - $resources = array(); - foreach (self::$resources as $name => $resource) { - if (strtolower($resource->type) === $type) { - $resources[$name] = $resource; - } - } - return new Config($resources); - } + return self::$resources; } /** @@ -99,13 +88,13 @@ class ResourceFactory implements ConfigAwareFactory * NOTE: The factory does not test if the given configuration is valid and the resource is accessible, this * depends entirely on the implementation of the returned resource. * - * @param Config $config The configuration for the created resource. + * @param ConfigObject $config The configuration for the created resource. * * @return DbConnection|LdapConnection|LivestatusConnection An object that can be used to access * the given resource. The returned class depends on the configuration property 'type'. * @throws ConfigurationError When an unsupported type is given */ - public static function createResource(Config $config) + public static function createResource(ConfigObject $config) { switch (strtolower($config->type)) { case 'db': diff --git a/library/Icinga/Protocol/File/FileReader.php b/library/Icinga/Protocol/File/FileReader.php index 26445de8a..363f8e173 100644 --- a/library/Icinga/Protocol/File/FileReader.php +++ b/library/Icinga/Protocol/File/FileReader.php @@ -5,8 +5,8 @@ namespace Icinga\Protocol\File; use Countable; -use Icinga\Application\Config; use Icinga\Data\Selectable; +use Icinga\Data\ConfigObject; /** * Read file line by line @@ -30,11 +30,11 @@ class FileReader implements Selectable, Countable /** * Create a new reader * - * @param Config $config + * @param ConfigObject $config * * @throws FileReaderException If a required $config directive (filename or fields) is missing */ - public function __construct(Config $config) + public function __construct(ConfigObject $config) { foreach (array('filename', 'fields') as $key) { if (isset($config->{$key})) { diff --git a/library/Icinga/Protocol/Ldap/Connection.php b/library/Icinga/Protocol/Ldap/Connection.php index 1cd66c70a..b0fd2a6bd 100644 --- a/library/Icinga/Protocol/Ldap/Connection.php +++ b/library/Icinga/Protocol/Ldap/Connection.php @@ -8,6 +8,7 @@ use Icinga\Protocol\Ldap\Exception as LdapException; use Icinga\Application\Platform; use Icinga\Application\Config; use Icinga\Application\Logger; +use Icinga\Data\ConfigObject; /** * Backend class managing all the LDAP stuff for you. @@ -100,9 +101,9 @@ class Connection * * TODO: Allow to pass port and SSL options * - * @param Config $config + * @param ConfigObject $config */ - public function __construct(Config $config) + public function __construct(ConfigObject $config) { $this->hostname = $config->hostname; $this->bind_dn = $config->bind_dn; diff --git a/library/Icinga/Test/BaseTestCase.php b/library/Icinga/Test/BaseTestCase.php index ade096547..41cd1099c 100644 --- a/library/Icinga/Test/BaseTestCase.php +++ b/library/Icinga/Test/BaseTestCase.php @@ -26,8 +26,8 @@ namespace Icinga\Test { use Mockery; use PHPUnit_Framework_TestCase; use Icinga\Application\Icinga; - use Icinga\Application\Config; use Icinga\Util\DateTimeFactory; + use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Data\Db\DbConnection; @@ -195,13 +195,13 @@ namespace Icinga\Test { * * @param string $name * - * @return Config + * @return ConfigObject * @throws RuntimeException */ protected function createDbConfigFor($name) { if (array_key_exists($name, self::$dbConfiguration)) { - return new Config(self::$dbConfiguration[$name]); + return new ConfigObject(self::$dbConfiguration[$name]); } throw new RuntimeException('Configuration for database type not available: ' . $name); diff --git a/library/Icinga/User/Preferences/PreferencesStore.php b/library/Icinga/User/Preferences/PreferencesStore.php index 79bea2e40..c2cba0c41 100644 --- a/library/Icinga/User/Preferences/PreferencesStore.php +++ b/library/Icinga/User/Preferences/PreferencesStore.php @@ -7,6 +7,7 @@ namespace Icinga\User\Preferences; use Icinga\Application\Config; use Icinga\User; use Icinga\User\Preferences; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Exception\ConfigurationError; use Icinga\Data\Db\DbConnection; @@ -18,14 +19,14 @@ use Icinga\Data\Db\DbConnection; * * 'ini', + * new ConfigObject( + * 'type' => 'ini', * 'config_path' => '/path/to/preferences' * ), * $user // Instance of \Icinga\User @@ -41,7 +42,7 @@ abstract class PreferencesStore /** * Store config * - * @var Config + * @var ConfigObject */ protected $config; @@ -55,10 +56,10 @@ abstract class PreferencesStore /** * Create a new store * - * @param Config $config The config for this adapter - * @param User $user The user to which these preferences belong + * @param ConfigObject $config The config for this adapter + * @param User $user The user to which these preferences belong */ - public function __construct(Config $config, User $user) + public function __construct(ConfigObject $config, User $user) { $this->config = $config; $this->user = $user; @@ -68,7 +69,7 @@ abstract class PreferencesStore /** * Getter for the store config * - * @return Config + * @return ConfigObject */ public function getStoreConfig() { @@ -107,14 +108,14 @@ abstract class PreferencesStore /** * Create preferences storage adapter from config * - * @param Config $config The config for the adapter - * @param User $user The user to which these preferences belong + * @param ConfigObject $config The config for the adapter + * @param User $user The user to which these preferences belong * * @return self * * @throws ConfigurationError When the configuration defines an invalid storage type */ - public static function create(Config $config, User $user) + public static function create(ConfigObject $config, User $user) { if (($type = $config->type) === null) { throw new ConfigurationError( diff --git a/library/Icinga/User/Preferences/Store/IniStore.php b/library/Icinga/User/Preferences/Store/IniStore.php index b765efe52..1a7efe760 100644 --- a/library/Icinga/User/Preferences/Store/IniStore.php +++ b/library/Icinga/User/Preferences/Store/IniStore.php @@ -120,7 +120,7 @@ class IniStore extends PreferencesStore $this->writer = new IniWriter( array( - 'config' => new Config($this->preferences), + 'config' => Config::fromArray($this->preferences), 'filename' => $this->preferencesFile ) ); diff --git a/library/Icinga/Web/Menu.php b/library/Icinga/Web/Menu.php index 4eae7525b..a2711f1b2 100644 --- a/library/Icinga/Web/Menu.php +++ b/library/Icinga/Web/Menu.php @@ -10,6 +10,7 @@ use RecursiveIterator; use Icinga\Application\Config; use Icinga\Application\Icinga; use Icinga\Application\Logger; +use Icinga\Data\ConfigObject; use Icinga\Exception\ConfigurationError; use Icinga\Exception\ProgrammingError; use Icinga\Web\Url; @@ -79,10 +80,10 @@ class Menu implements RecursiveIterator /** * Create a new menu * - * @param int $id The id of this menu - * @param Config $config The configuration for this menu + * @param int $id The id of this menu + * @param ConfigObject $config The configuration for this menu */ - public function __construct($id, Config $config = null, Menu $parent = null) + public function __construct($id, ConfigObject $config = null, Menu $parent = null) { $this->id = $id; if ($parent !== null) { @@ -94,7 +95,7 @@ class Menu implements RecursiveIterator /** * Set all given properties * - * @param array|Config $props Property list + * @param array|ConfigObject $props Property list */ public function setProperties($props = null) { @@ -170,7 +171,7 @@ class Menu implements RecursiveIterator foreach ($modules as $moduleName) { $moduleMenuConfig = Config::module($moduleName, 'menu'); - if (false === empty($moduleMenuConfig)) { + if (! $moduleMenuConfig->isEmpty()) { $menuConfigs[] = $moduleMenuConfig; } } @@ -424,11 +425,11 @@ class Menu implements RecursiveIterator * Add a sub menu to this menu * * @param string $id The id of the menu to add - * @param Config $itemConfig The config with which to initialize the menu + * @param ConfigObject $itemConfig The config with which to initialize the menu * * @return self */ - public function addSubMenu($id, Config $menuConfig = null) + public function addSubMenu($id, ConfigObject $menuConfig = null) { if (false === ($pos = strpos($id, '.'))) { $subMenu = new self($id, $menuConfig, $this); @@ -518,7 +519,7 @@ class Menu implements RecursiveIterator */ public function add($name, $config = array()) { - return $this->addSubMenu($name, new Config($config)); + return $this->addSubMenu($name, new ConfigObject($config)); } /** diff --git a/library/Icinga/Web/Widget/Dashboard.php b/library/Icinga/Web/Widget/Dashboard.php index 0221e4744..f7daa5d02 100644 --- a/library/Icinga/Web/Widget/Dashboard.php +++ b/library/Icinga/Web/Widget/Dashboard.php @@ -366,9 +366,7 @@ class Dashboard extends AbstractWidget */ private function loadConfigPanes() { - $items = $this->config; - foreach ($items->keys() as $key) { - $item = $this->config->get($key, false); + foreach ($this->config as $key => $item) { if (false === strstr($key, '.')) { $this->addPane(Pane::fromIni($key, $item)); } else { diff --git a/library/Icinga/Web/Widget/Dashboard/Component.php b/library/Icinga/Web/Widget/Dashboard/Component.php index 6edf140f5..e0ac4b3d7 100644 --- a/library/Icinga/Web/Widget/Dashboard/Component.php +++ b/library/Icinga/Web/Widget/Dashboard/Component.php @@ -5,10 +5,10 @@ namespace Icinga\Web\Widget\Dashboard; use Zend_Form_Element_Button; -use Icinga\Application\Config; use Icinga\Web\Form; use Icinga\Web\Url; use Icinga\Web\Widget\AbstractWidget; +use Icinga\Data\ConfigObject; use Icinga\Exception\IcingaException; /** @@ -214,13 +214,13 @@ EOD; /** * Create a @see Component instance from the given Zend config, using the provided title * - * @param $title The title for this component - * @param Config $config The configuration defining url, parameters, height, width, etc. - * @param Pane $pane The pane this component belongs to + * @param $title The title for this component + * @param ConfigObject $config The configuration defining url, parameters, height, width, etc. + * @param Pane $pane The pane this component belongs to * * @return Component A newly created Component for use in the Dashboard */ - public static function fromIni($title, Config $config, Pane $pane) + public static function fromIni($title, ConfigObject $config, Pane $pane) { $height = null; $width = null; diff --git a/library/Icinga/Web/Widget/Dashboard/Pane.php b/library/Icinga/Web/Widget/Dashboard/Pane.php index 3b0e97c73..92523578f 100644 --- a/library/Icinga/Web/Widget/Dashboard/Pane.php +++ b/library/Icinga/Web/Widget/Dashboard/Pane.php @@ -4,7 +4,7 @@ namespace Icinga\Web\Widget\Dashboard; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Web\Widget\AbstractWidget; use Icinga\Exception\ProgrammingError; use Icinga\Exception\ConfigurationError; @@ -253,11 +253,11 @@ class Pane extends AbstractWidget * Create a new pane with the title $title from the given configuration * * @param $title The title for this pane - * @param Config $config The configuration to use for setup + * @param ConfigObject $config The configuration to use for setup * * @return Pane */ - public static function fromIni($title, Config $config) + public static function fromIni($title, ConfigObject $config) { $pane = new Pane($title); if ($config->get('title', false)) { diff --git a/modules/monitoring/application/forms/Config/BackendConfigForm.php b/modules/monitoring/application/forms/Config/BackendConfigForm.php index 1f31990cb..f467b8f59 100644 --- a/modules/monitoring/application/forms/Config/BackendConfigForm.php +++ b/modules/monitoring/application/forms/Config/BackendConfigForm.php @@ -73,12 +73,12 @@ class BackendConfigForm extends ConfigForm $name = isset($values['name']) ? $values['name'] : ''; if (! $name) { throw new InvalidArgumentException(mt('monitoring', 'Monitoring backend name missing')); - } elseif ($this->config->get($name) !== null) { + } elseif ($this->config->hasSection($name)) { throw new InvalidArgumentException(mt('monitoring', 'Monitoring backend already exists')); } unset($values['name']); - $this->config->{$name} = $values; + $this->config->setSection($name, $values); return $this; } @@ -98,14 +98,13 @@ class BackendConfigForm extends ConfigForm throw new InvalidArgumentException(mt('monitoring', 'Old monitoring backend name missing')); } elseif (! ($newName = isset($values['name']) ? $values['name'] : '')) { throw new InvalidArgumentException(mt('monitoring', 'New monitoring backend name missing')); - } elseif (($backendConfig = $this->config->get($name)) === null) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(mt('monitoring', 'Unknown monitoring backend provided')); } unset($values['name']); - unset($this->config->{$name}); - $this->config->{$newName} = $values; - return $this->config->{$newName}; + $this->config->setSection($name, $values); + return $this->config->getSection($name); } /** @@ -121,11 +120,12 @@ class BackendConfigForm extends ConfigForm { if (! $name) { throw new InvalidArgumentException(mt('monitoring', 'Monitoring backend name missing')); - } elseif (($backendConfig = $this->config->get($name)) === null) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(mt('monitoring', 'Unknown monitoring backend provided')); } - unset($this->config->{$name}); + $backendConfig = $this->config->getSection($name); + $this->config->removeSection($name); return $backendConfig; } @@ -170,11 +170,11 @@ class BackendConfigForm extends ConfigForm if ($monitoringBackend !== null) { if ($monitoringBackend === '') { throw new ConfigurationError(mt('monitoring', 'Monitoring backend name missing')); - } elseif (false === isset($this->config->{$monitoringBackend})) { + } elseif (! $this->config->hasSection($monitoringBackend)) { throw new ConfigurationError(mt('monitoring', 'Unknown monitoring backend provided')); } - $backendConfig = $this->config->{$monitoringBackend}->toArray(); + $backendConfig = $this->config->getSection($monitoringBackend)->toArray(); $backendConfig['name'] = $monitoringBackend; $this->populate($backendConfig); } diff --git a/modules/monitoring/application/forms/Config/InstanceConfigForm.php b/modules/monitoring/application/forms/Config/InstanceConfigForm.php index 302c0dec3..b89e48c0a 100644 --- a/modules/monitoring/application/forms/Config/InstanceConfigForm.php +++ b/modules/monitoring/application/forms/Config/InstanceConfigForm.php @@ -71,12 +71,12 @@ class InstanceConfigForm extends ConfigForm if (! $name) { throw new InvalidArgumentException(mt('monitoring', 'Instance name missing')); } - if (isset($this->config->{$name})) { + if ($this->config->hasSection($name)) { throw new InvalidArgumentException(mt('monitoring', 'Instance already exists')); } unset($values['name']); - $this->config->{$name} = $values; + $this->config->setSection($name, $values); return $this; } @@ -96,14 +96,13 @@ class InstanceConfigForm extends ConfigForm throw new InvalidArgumentException(mt('monitoring', 'Old instance name missing')); } elseif (! ($newName = isset($values['name']) ? $values['name'] : '')) { throw new InvalidArgumentException(mt('monitoring', 'New instance name missing')); - } elseif (! ($instanceConfig = $this->config->get($name))) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(mt('monitoring', 'Unknown instance name provided')); } unset($values['name']); - unset($this->config->{$name}); - $this->config->{$newName} = $values; - return $this->config->{$newName}; + $this->config->setSection($name, $values); + return $this->config->getSection($name); } /** @@ -119,11 +118,12 @@ class InstanceConfigForm extends ConfigForm { if (! $name) { throw new InvalidArgumentException(mt('monitoring', 'Instance name missing')); - } elseif (! ($instanceConfig = $this->config->get($name))) { + } elseif (! $this->config->hasSection($name)) { throw new InvalidArgumentException(mt('monitoring', 'Unknown instance name provided')); } - unset($this->config->{$name}); + $instanceConfig = $this->config->getSection($name); + $this->config->removeSection($name); return $instanceConfig; } @@ -138,11 +138,11 @@ class InstanceConfigForm extends ConfigForm if (! $instanceName) { throw new ConfigurationError(mt('monitoring', 'Instance name missing')); } - if (! isset($this->config->{$instanceName})) { + if (! $this->config->hasSection($instanceName)) { throw new ConfigurationError(mt('monitoring', 'Unknown instance name given')); } - $instanceConfig = $this->config->{$instanceName}->toArray(); + $instanceConfig = $this->config->getSection($instanceName)->toArray(); $instanceConfig['name'] = $instanceName; $this->populate($instanceConfig); } diff --git a/modules/monitoring/application/forms/Config/SecurityConfigForm.php b/modules/monitoring/application/forms/Config/SecurityConfigForm.php index de4055802..40c0b7b8c 100644 --- a/modules/monitoring/application/forms/Config/SecurityConfigForm.php +++ b/modules/monitoring/application/forms/Config/SecurityConfigForm.php @@ -26,7 +26,7 @@ class SecurityConfigForm extends ConfigForm */ public function onSuccess() { - $this->config->security = $this->getValues(); + $this->config->setSection('security', $this->getValues()); if ($this->save()) { Notification::success(mt('monitoring', 'New security configuration has successfully been stored')); @@ -40,9 +40,7 @@ class SecurityConfigForm extends ConfigForm */ public function onRequest() { - if (isset($this->config->security)) { - $this->populate($this->config->security->toArray()); - } + $this->populate($this->config->getSection('security')->toArray()); } /** diff --git a/modules/monitoring/library/Monitoring/Backend/MonitoringBackend.php b/modules/monitoring/library/Monitoring/Backend/MonitoringBackend.php index 11a8fb699..c8f75f540 100644 --- a/modules/monitoring/library/Monitoring/Backend/MonitoringBackend.php +++ b/modules/monitoring/library/Monitoring/Backend/MonitoringBackend.php @@ -3,6 +3,7 @@ namespace Icinga\Module\Monitoring\Backend; use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Data\ConnectionInterface; use Icinga\Data\Queryable; @@ -16,7 +17,7 @@ class MonitoringBackend implements Selectable, Queryable, ConnectionInterface /** * Backend configuration * - * @var Config + * @var ConfigObject */ protected $config; @@ -51,10 +52,10 @@ class MonitoringBackend implements Selectable, Queryable, ConnectionInterface /** * Create a new backend * - * @param string $name - * @param mixed $config + * @param string $name + * @param ConfigObject $config */ - protected function __construct($name, $config) + protected function __construct($name, ConfigObject $config) { $this->name = $name; $this->config = $config; @@ -180,9 +181,9 @@ class MonitoringBackend implements Selectable, Queryable, ConnectionInterface } else { - $config = $backends->get($name); + $config = $backends->getSection($name); - if ($config === null) { + if ($config->isEmpty()) { throw new ConfigurationError( mt('monitoring', 'No configuration for backend %s'), $name diff --git a/modules/monitoring/library/Monitoring/BackendStep.php b/modules/monitoring/library/Monitoring/BackendStep.php index 4eac949ba..c0dc3d4ea 100644 --- a/modules/monitoring/library/Monitoring/BackendStep.php +++ b/modules/monitoring/library/Monitoring/BackendStep.php @@ -39,7 +39,7 @@ class BackendStep extends Step try { $writer = new IniWriter(array( - 'config' => new Config($config), + 'config' => Config::fromArray($config), 'filename' => Config::resolvePath('modules/monitoring/backends.ini') )); $writer->write(); @@ -60,7 +60,7 @@ class BackendStep extends Step try { $config = Config::app('resources', true); - $config->merge(new Config(array($resourceName => $resourceConfig))); + $config->setSection($resourceName, $resourceConfig); $writer = new IniWriter(array( 'config' => $config, diff --git a/modules/monitoring/library/Monitoring/Command/Transport/CommandTransport.php b/modules/monitoring/library/Monitoring/Command/Transport/CommandTransport.php index 166bbb6a3..8ed7d45eb 100644 --- a/modules/monitoring/library/Monitoring/Command/Transport/CommandTransport.php +++ b/modules/monitoring/library/Monitoring/Command/Transport/CommandTransport.php @@ -5,6 +5,7 @@ namespace Icinga\Module\Monitoring\Command\Transport; use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Exception\ConfigurationError; /** @@ -31,7 +32,7 @@ abstract class CommandTransport { if (! isset(self::$config)) { self::$config = Config::module('monitoring', 'instances'); - if (self::$config->count() === 0) { + if (self::$config->isEmpty()) { throw new ConfigurationError( 'No instances have been configured in \'%s\'.', self::$config->getConfigFile() @@ -44,12 +45,12 @@ abstract class CommandTransport /** * Create a transport from config * - * @param Config $config + * @param ConfigObject $config * * @return LocalCommandFile|RemoteCommandFile * @throws ConfigurationError */ - public static function fromConfig(Config $config) + public static function fromConfig(ConfigObject $config) { switch (strtolower($config->transport)) { case RemoteCommandFile::TRANSPORT: @@ -90,8 +91,8 @@ abstract class CommandTransport */ public static function create($name) { - $config = self::getConfig()->get($name); - if ($config === null) { + $config = self::getConfig()->getSection($name); + if ($config->isEmpty()) { throw new ConfigurationError(); } return self::fromConfig($config); diff --git a/modules/monitoring/library/Monitoring/InstanceStep.php b/modules/monitoring/library/Monitoring/InstanceStep.php index 9a5ce4f1b..2cb8d7d8d 100644 --- a/modules/monitoring/library/Monitoring/InstanceStep.php +++ b/modules/monitoring/library/Monitoring/InstanceStep.php @@ -28,7 +28,7 @@ class InstanceStep extends Step try { $writer = new IniWriter(array( - 'config' => new Config(array($instanceName => $instanceConfig)), + 'config' => Config::fromArray(array($instanceName => $instanceConfig)), 'filename' => Config::resolvePath('modules/monitoring/instances.ini') )); $writer->write(); diff --git a/modules/monitoring/library/Monitoring/Object/MonitoredObject.php b/modules/monitoring/library/Monitoring/Object/MonitoredObject.php index fefcba929..4be004d99 100644 --- a/modules/monitoring/library/Monitoring/Object/MonitoredObject.php +++ b/modules/monitoring/library/Monitoring/Object/MonitoredObject.php @@ -290,10 +290,7 @@ abstract class MonitoredObject $blacklist = array(); $blacklistPattern = '/^(.*pw.*|.*pass.*|community)$/i'; - if ($security = Config::module('monitoring')->get('security')) { - - $blacklistConfig = $security->get('protected_customvars', ''); - + if (($blacklistConfig = Config::module('monitoring')->get('security', 'protected_customvars', '')) !== '') { foreach (explode(',', $blacklistConfig) as $customvar) { $nonWildcards = array(); foreach (explode('*', $customvar) as $nonWildcard) { diff --git a/modules/monitoring/library/Monitoring/SecurityStep.php b/modules/monitoring/library/Monitoring/SecurityStep.php index 636f5826e..4a2c0f846 100644 --- a/modules/monitoring/library/Monitoring/SecurityStep.php +++ b/modules/monitoring/library/Monitoring/SecurityStep.php @@ -27,7 +27,7 @@ class SecurityStep extends Step try { $writer = new IniWriter(array( - 'config' => new Config($config), + 'config' => Config::fromArray($config), 'filename' => Config::resolvePath('modules/monitoring/config.ini') )); $writer->write(); diff --git a/modules/monitoring/test/php/regression/Bug7043Test.php b/modules/monitoring/test/php/regression/Bug7043Test.php index ea216d6fa..94a60a5b6 100644 --- a/modules/monitoring/test/php/regression/Bug7043Test.php +++ b/modules/monitoring/test/php/regression/Bug7043Test.php @@ -7,6 +7,7 @@ namespace Tests\Icinga\Module\Monitoring\Regression; require_once realpath(dirname(__FILE__) . '/../../../../../test/php/bootstrap.php'); use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Module\Monitoring\Backend; use Icinga\Test\BaseTestCase; use Mockery; @@ -45,7 +46,7 @@ class Bug7043Test extends BaseTestCase ->getMock() ); - ConfigWithSetModuleConfig::setModuleConfig('monitoring', 'backends', new Config(array( + ConfigWithSetModuleConfig::setModuleConfig('monitoring', 'backends', new ConfigObject(array( 'backendName' => array( 'type' => 'ido', 'resource' => 'ido' diff --git a/modules/setup/application/forms/AdminAccountPage.php b/modules/setup/application/forms/AdminAccountPage.php index f338d9449..6ef791d4e 100644 --- a/modules/setup/application/forms/AdminAccountPage.php +++ b/modules/setup/application/forms/AdminAccountPage.php @@ -6,8 +6,8 @@ namespace Icinga\Module\Setup\Forms; use Exception; use LogicException; -use Icinga\Application\Config; use Icinga\Web\Form; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Authentication\Backend\DbUserBackend; use Icinga\Authentication\Backend\LdapUserBackend; @@ -253,10 +253,10 @@ class AdminAccountPage extends Form protected function fetchUsers() { if ($this->backendConfig['backend'] === 'db') { - $backend = new DbUserBackend(ResourceFactory::createResource(new Config($this->resourceConfig))); + $backend = new DbUserBackend(ResourceFactory::createResource(new ConfigObject($this->resourceConfig))); } elseif ($this->backendConfig['backend'] === 'ldap') { $backend = new LdapUserBackend( - ResourceFactory::createResource(new Config($this->resourceConfig)), + ResourceFactory::createResource(new ConfigObject($this->resourceConfig)), $this->backendConfig['user_class'], $this->backendConfig['user_name_attribute'], $this->backendConfig['base_dn'] diff --git a/modules/setup/application/forms/AuthBackendPage.php b/modules/setup/application/forms/AuthBackendPage.php index 0c58906be..fac2a7bbd 100644 --- a/modules/setup/application/forms/AuthBackendPage.php +++ b/modules/setup/application/forms/AuthBackendPage.php @@ -4,11 +4,11 @@ namespace Icinga\Module\Setup\Forms; -use Icinga\Application\Config; use Icinga\Web\Form; use Icinga\Forms\Config\Authentication\DbBackendForm; use Icinga\Forms\Config\Authentication\LdapBackendForm; use Icinga\Forms\Config\Authentication\AutologinBackendForm; +use Icinga\Data\ConfigObject; /** * Wizard page to define authentication backend specific details @@ -46,11 +46,11 @@ class AuthBackendPage extends Form /** * Return the resource configuration as Config object * - * @return Config + * @return ConfigObject */ public function getResourceConfig() { - return new Config($this->config); + return new ConfigObject($this->config); } /** diff --git a/modules/setup/application/forms/LdapDiscoveryConfirmPage.php b/modules/setup/application/forms/LdapDiscoveryConfirmPage.php index a192fac72..f76cbee07 100644 --- a/modules/setup/application/forms/LdapDiscoveryConfirmPage.php +++ b/modules/setup/application/forms/LdapDiscoveryConfirmPage.php @@ -4,7 +4,7 @@ namespace Icinga\Module\Setup\Forms; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Web\Form; /** @@ -56,11 +56,11 @@ EOT; /** * Return the resource configuration as Config object * - * @return Config + * @return ConfigObject */ public function getResourceConfig() { - return new Config($this->config); + return new ConfigObject($this->config); } /** diff --git a/modules/setup/library/Setup/Steps/AuthenticationStep.php b/modules/setup/library/Setup/Steps/AuthenticationStep.php index 327bdad2c..a15198c57 100644 --- a/modules/setup/library/Setup/Steps/AuthenticationStep.php +++ b/modules/setup/library/Setup/Steps/AuthenticationStep.php @@ -7,6 +7,7 @@ namespace Icinga\Module\Setup\Steps; use Exception; use Icinga\Application\Config; use Icinga\File\Ini\IniWriter; +use Icinga\Data\ConfigObject; use Icinga\Data\ResourceFactory; use Icinga\Authentication\Backend\DbUserBackend; use Icinga\Module\Setup\Step; @@ -50,7 +51,7 @@ class AuthenticationStep extends Step try { $writer = new IniWriter(array( - 'config' => new Config($config), + 'config' => Config::fromArray($config), 'filename' => Config::resolvePath('authentication.ini') )); $writer->write(); @@ -73,7 +74,7 @@ class AuthenticationStep extends Step try { $writer = new IniWriter(array( - 'config' => new Config($config), + 'config' => Config::fromArray($config), 'filename' => Config::resolvePath('permissions.ini') )); $writer->write(); @@ -90,7 +91,7 @@ class AuthenticationStep extends Step { try { $backend = new DbUserBackend( - ResourceFactory::createResource(new Config($this->data['adminAccountData']['resourceConfig'])) + ResourceFactory::createResource(new ConfigObject($this->data['adminAccountData']['resourceConfig'])) ); if (array_search($this->data['adminAccountData']['username'], $backend->listUsers()) === false) { diff --git a/modules/setup/library/Setup/Steps/GeneralConfigStep.php b/modules/setup/library/Setup/Steps/GeneralConfigStep.php index 6a3f12897..ee9e2c581 100644 --- a/modules/setup/library/Setup/Steps/GeneralConfigStep.php +++ b/modules/setup/library/Setup/Steps/GeneralConfigStep.php @@ -36,7 +36,7 @@ class GeneralConfigStep extends Step try { $writer = new IniWriter(array( - 'config' => new Config($config), + 'config' => Config::fromArray($config), 'filename' => Config::resolvePath('config.ini') )); $writer->write(); diff --git a/modules/setup/library/Setup/Steps/ResourceStep.php b/modules/setup/library/Setup/Steps/ResourceStep.php index 75e79a8fa..c04cdbc79 100644 --- a/modules/setup/library/Setup/Steps/ResourceStep.php +++ b/modules/setup/library/Setup/Steps/ResourceStep.php @@ -39,7 +39,7 @@ class ResourceStep extends Step try { $writer = new IniWriter(array( - 'config' => new Config($resourceConfig), + 'config' => Config::fromArray($resourceConfig), 'filename' => Config::resolvePath('resources.ini'), 'filemode' => 0660 )); diff --git a/test/php/application/forms/Config/Authentication/DbBackendFormTest.php b/test/php/application/forms/Config/Authentication/DbBackendFormTest.php index 3157f4e0e..6af628b06 100644 --- a/test/php/application/forms/Config/Authentication/DbBackendFormTest.php +++ b/test/php/application/forms/Config/Authentication/DbBackendFormTest.php @@ -9,7 +9,7 @@ namespace Tests\Icinga\Forms\Config\Authentication; require_once realpath(dirname(__FILE__) . '/../../../../bootstrap.php'); use Mockery; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Test\BaseTestCase; use Icinga\Forms\Config\Authentication\DbBackendForm; @@ -71,6 +71,6 @@ class DbBackendFormTest extends BaseTestCase ->shouldReceive('createResource') ->andReturn(Mockery::mock('Icinga\Data\Db\DbConnection')) ->shouldReceive('getResourceConfig') - ->andReturn(new Config()); + ->andReturn(new ConfigObject()); } } diff --git a/test/php/application/forms/Config/Authentication/LdapBackendFormTest.php b/test/php/application/forms/Config/Authentication/LdapBackendFormTest.php index 6126cbb9c..046730f57 100644 --- a/test/php/application/forms/Config/Authentication/LdapBackendFormTest.php +++ b/test/php/application/forms/Config/Authentication/LdapBackendFormTest.php @@ -9,8 +9,8 @@ namespace Tests\Icinga\Forms\Config\Authentication; require_once realpath(dirname(__FILE__) . '/../../../../bootstrap.php'); use Mockery; +use Icinga\Data\ConfigObject; use Icinga\Test\BaseTestCase; -use Icinga\Application\Config; use Icinga\Forms\Config\Authentication\LdapBackendForm; use Icinga\Exception\AuthenticationException; @@ -70,6 +70,6 @@ class LdapBackendFormTest extends BaseTestCase ->shouldReceive('createResource') ->andReturn(Mockery::mock('Icinga\Protocol\Ldap\Connection')) ->shouldReceive('getResourceConfig') - ->andReturn(new Config()); + ->andReturn(new ConfigObject()); } } diff --git a/test/php/application/forms/Config/AuthenticationBackendReorderFormTest.php b/test/php/application/forms/Config/AuthenticationBackendReorderFormTest.php index 936bf9366..88de869a1 100644 --- a/test/php/application/forms/Config/AuthenticationBackendReorderFormTest.php +++ b/test/php/application/forms/Config/AuthenticationBackendReorderFormTest.php @@ -34,7 +34,7 @@ class AuthenticationBackendReorderFormTest extends BaseTestCase { public function testMoveBackend() { - $config = new Config( + $config = Config::fromArray( array( 'test1' => '', 'test2' => '', diff --git a/test/php/application/forms/Config/Resource/DbResourceFormTest.php b/test/php/application/forms/Config/Resource/DbResourceFormTest.php index d6e7fc447..53dd6bf56 100644 --- a/test/php/application/forms/Config/Resource/DbResourceFormTest.php +++ b/test/php/application/forms/Config/Resource/DbResourceFormTest.php @@ -56,7 +56,7 @@ class DbResourceFormTest extends BaseTestCase { Mockery::mock('alias:Icinga\Data\ResourceFactory') ->shouldReceive('createResource') - ->with(Mockery::type('Icinga\Application\Config')) + ->with(Mockery::type('Icinga\Data\ConfigObject')) ->andReturn($resourceMock); } } diff --git a/test/php/application/forms/Config/Resource/LdapResourceFormTest.php b/test/php/application/forms/Config/Resource/LdapResourceFormTest.php index 211b9bb02..9ef8880e7 100644 --- a/test/php/application/forms/Config/Resource/LdapResourceFormTest.php +++ b/test/php/application/forms/Config/Resource/LdapResourceFormTest.php @@ -62,7 +62,7 @@ class LdapResourceFormTest extends BaseTestCase { Mockery::mock('alias:Icinga\Data\ResourceFactory') ->shouldReceive('createResource') - ->with(Mockery::type('Icinga\Application\Config')) + ->with(Mockery::type('Icinga\Data\ConfigObject')) ->andReturn($resourceMock); } } diff --git a/test/php/application/forms/Config/Resource/LivestatusResourceFormTest.php b/test/php/application/forms/Config/Resource/LivestatusResourceFormTest.php index f6fae6b08..3f5de5844 100644 --- a/test/php/application/forms/Config/Resource/LivestatusResourceFormTest.php +++ b/test/php/application/forms/Config/Resource/LivestatusResourceFormTest.php @@ -57,7 +57,7 @@ class LivestatusResourceFormTest extends BaseTestCase { Mockery::mock('alias:Icinga\Data\ResourceFactory') ->shouldReceive('createResource') - ->with(Mockery::type('Icinga\Application\Config')) + ->with(Mockery::type('Icinga\Data\ConfigObject')) ->andReturn($resourceMock); } } diff --git a/test/php/library/Icinga/File/Ini/IniWriterTest.php b/test/php/library/Icinga/File/Ini/IniWriterTest.php index 1b9580fb3..63cb0e517 100644 --- a/test/php/library/Icinga/File/Ini/IniWriterTest.php +++ b/test/php/library/Icinga/File/Ini/IniWriterTest.php @@ -33,7 +33,7 @@ class IniWriterTest extends BaseTestCase { $writer = new IniWriter( array( - 'config' => new Config( + 'config' => Config::fromArray( array( 'section' => array( 'foo.bar' => 1337 @@ -57,7 +57,7 @@ class IniWriterTest extends BaseTestCase { $this->markTestSkipped('Implementation has changed. Section-less properties are not supported anymore'); $target = $this->writeConfigToTemporaryFile(''); - $config = new Config(array('key' => 'value')); + $config = Config::fromArray(array('key' => 'value')); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -69,7 +69,7 @@ class IniWriterTest extends BaseTestCase { $this->markTestSkipped('Implementation has changed. Section-less properties are not supported anymore'); $target = $this->writeConfigToTemporaryFile('key1 = "1"'); - $config = new Config(array('key2' => '2')); + $config = Config::fromArray(array('key2' => '2')); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -84,7 +84,7 @@ class IniWriterTest extends BaseTestCase { $this->markTestSkipped('Implementation has changed. Section-less properties are not supported anymore'); $target = $this->writeConfigToTemporaryFile('key = "value"'); - $config = new Config(array('key' => 'eulav')); + $config = Config::fromArray(array('key' => 'eulav')); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -99,7 +99,7 @@ class IniWriterTest extends BaseTestCase { $this->markTestSkipped('Implementation has changed. Section-less properties are not supported anymore'); $target = $this->writeConfigToTemporaryFile('key = "value"'); - $config = new Config(array()); + $config = new Config(); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -110,19 +110,19 @@ class IniWriterTest extends BaseTestCase public function testWhetherNestedPropertiesAreInserted() { $target = $this->writeConfigToTemporaryFile(''); - $config = new Config(array('a' => array('b' => 'c'))); + $config = Config::fromArray(array('a' => array('b' => 'c'))); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); $newConfig = Config::fromIni($target); $this->assertInstanceOf( - get_class($newConfig), - $newConfig->get('a'), + 'Icinga\Data\ConfigObject', + $newConfig->getSection('a'), 'IniWriter does not insert nested properties' ); $this->assertEquals( 'c', - $newConfig->get('a')->get('b'), + $newConfig->getSection('a')->get('b'), 'IniWriter does not insert nested properties' ); } @@ -134,7 +134,7 @@ class IniWriterTest extends BaseTestCase { $this->markTestSkipped('Implementation has changed. Section-less properties are not supported anymore'); $target = $this->writeConfigToTemporaryFile('a.b = "c"'); - $config = new Config(array('a' => array('b' => 'cc'))); + $config = Config::fromArray(array('a' => array('b' => 'cc'))); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -158,7 +158,7 @@ class IniWriterTest extends BaseTestCase { $this->markTestSkipped('Implementation has changed. Section-less properties are not supported anymore'); $target = $this->writeConfigToTemporaryFile('a.b = "c"'); - $config = new Config(array()); + $config = new Config(); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -172,19 +172,19 @@ class IniWriterTest extends BaseTestCase public function testWhetherSimpleSectionPropertiesAreInserted() { $target = $this->writeConfigToTemporaryFile(''); - $config = new Config(array('section' => array('key' => 'value'))); + $config = Config::fromArray(array('section' => array('key' => 'value'))); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); $newConfig = Config::fromIni($target); $this->assertInstanceOf( - get_class($newConfig), - $newConfig->get('section'), + 'Icinga\Data\ConfigObject', + $newConfig->getSection('section'), 'IniWriter does not insert sections' ); $this->assertEquals( 'value', - $newConfig->get('section')->get('key'), + $newConfig->getSection('section')->get('key'), 'IniWriter does not insert simple section properties' ); } @@ -199,14 +199,14 @@ class IniWriterTest extends BaseTestCase key = "value" EOD ); - $config = new Config(array('section' => array('key' => 'eulav'))); + $config = Config::fromArray(array('section' => array('key' => 'eulav'))); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); $newConfig = Config::fromIni($target); $this->assertEquals( 'eulav', - $newConfig->get('section')->get('key'), + $newConfig->getSection('section')->get('key'), 'IniWriter does not update simple section properties' ); } @@ -221,13 +221,13 @@ EOD key = "value" EOD ); - $config = new Config(array('section' => array())); + $config = Config::fromArray(array('section' => array())); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); $newConfig = Config::fromIni($target); $this->assertNull( - $newConfig->get('section')->get('key'), + $newConfig->getSection('section')->get('key'), 'IniWriter does not delete simple section properties' ); } @@ -236,7 +236,7 @@ EOD { $this->markTestSkipped('Implementation has changed. Config::fromIni cannot handle nested properties anymore'); $target = $this->writeConfigToTemporaryFile(''); - $config = new Config(array('section' => array('a' => array('b' => 'c')))); + $config = Config::fromArray(array('section' => array('a' => array('b' => 'c')))); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -268,7 +268,7 @@ EOD a.b = "c" EOD ); - $config = new Config(array('section' => array('a' => array('b' => 'cc')))); + $config = Config::fromArray(array('section' => array('a' => array('b' => 'cc')))); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -290,7 +290,7 @@ EOD a.b = "c" EOD ); - $config = new Config(array('section' => array())); + $config = Config::fromArray(array('section' => array())); $writer = new IniWriter(array('config' => $config, 'filename' => $target)); $writer->write(); @@ -307,7 +307,7 @@ EOD 'Implementation has changed. There is no "Extend" functionality anymore in our Config object' ); $target = $this->writeConfigToTemporaryFile(''); - $config = new Config( + $config = Config::fromArray( array( 'foo' => array('key1' => '1'), 'bar' => array('key2' => '2') @@ -356,7 +356,7 @@ key1 = "1" key2 = "2" EOD ); - $config = new Config( + $config = Config::fromArray( array( 'foo' => array('key1' => '1'), 'bar' => array('key2' => '22') @@ -390,7 +390,7 @@ key1 = "1" key2 = "2" EOD ); - $config = new Config( + $config = Config::fromArray( array( 'foo' => array('key1' => '1'), 'bar' => array() @@ -413,7 +413,7 @@ EOD 'Implementation has changed. There is no "Extend" functionality anymore in our Config object' ); $target = $this->writeConfigToTemporaryFile(''); - $config = new Config( + $config = Config::fromArray( array( 'foo' => array('a' => array('b' => 'c')), 'bar' => array('d' => array('e' => 'f')) @@ -464,7 +464,7 @@ a.b = "c" d.e = "f" EOD ); - $config = new Config( + $config = Config::fromArray( array( 'foo' => array('a' => array('b' => 'c')), 'bar' => array('d' => array('e' => 'ff')) @@ -498,7 +498,7 @@ a.b = "c" d.e = "f" EOD ); - $config = new Config( + $config = Config::fromArray( array( 'foo' => array('a' => array('b' => 'c')), 'bar' => array() @@ -551,7 +551,7 @@ EOD; $target = $this->writeConfigToTemporaryFile($config); $writer = new IniWriter( array( - 'config' => new Config( + 'config' => Config::fromArray( array( 'three' => array( 'foo' => array( @@ -606,7 +606,7 @@ EOD; $target = $this->writeConfigToTemporaryFile($config); $writer = new IniWriter( array( - 'config' => new Config( + 'config' => Config::fromArray( array( 'two' => array(), 'one' => array() @@ -634,7 +634,7 @@ key = "value" EOD; $target = $this->writeConfigToTemporaryFile($config); $writer = new IniWriter( - array('config' => new Config(array('key' => 'value')), 'filename' => $target) + array('config' => Config::fromArray(array('key' => 'value')), 'filename' => $target) ); $this->assertEquals( @@ -655,7 +655,7 @@ EOD; $target = $this->writeConfigToTemporaryFile($config); $writer = new IniWriter( array( - 'config' => new Config( + 'config' => Config::fromArray( array( 'foo' => 1337, 'bar' => 7331, @@ -683,7 +683,7 @@ key = "value" EOD; $target = $this->writeConfigToTemporaryFile($config); $writer = new IniWriter( - array('config' => new Config(array('section' => array('key' => 'value'))), 'filename' => $target) + array('config' => Config::fromArray(array('section' => array('key' => 'value'))), 'filename' => $target) ); $this->assertEquals( @@ -705,7 +705,7 @@ EOD; $target = $this->writeConfigToTemporaryFile($config); $writer = new IniWriter( array( - 'config' => new Config( + 'config' => Config::fromArray( array( 'section' => array( 'foo' => 1337, diff --git a/test/php/library/Icinga/Logger/Writer/StreamWriterTest.php b/test/php/library/Icinga/Logger/Writer/StreamWriterTest.php index 44831a5e7..0c0d55498 100644 --- a/test/php/library/Icinga/Logger/Writer/StreamWriterTest.php +++ b/test/php/library/Icinga/Logger/Writer/StreamWriterTest.php @@ -4,7 +4,7 @@ namespace Tests\Icinga\Logger\Writer; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Application\Logger; use Icinga\Application\Logger\Writer\FileWriter; use Icinga\Test\BaseTestCase; @@ -27,7 +27,7 @@ class StreamWriterTest extends BaseTestCase public function testWhetherStreamWriterCreatesMissingFiles() { - new FileWriter(new Config(array('file' => $this->target))); + new FileWriter(new ConfigObject(array('file' => $this->target))); $this->assertFileExists($this->target, 'StreamWriter does not create missing files on initialization'); } @@ -36,7 +36,7 @@ class StreamWriterTest extends BaseTestCase */ public function testWhetherStreamWriterWritesMessages() { - $writer = new FileWriter(new Config(array('file' => $this->target))); + $writer = new FileWriter(new ConfigObject(array('file' => $this->target))); $writer->log(Logger::ERROR, 'This is a test error'); $log = file_get_contents($this->target); $this->assertContains('This is a test error', $log, 'StreamWriter does not write log messages'); diff --git a/test/php/library/Icinga/Protocol/Ldap/QueryTest.php b/test/php/library/Icinga/Protocol/Ldap/QueryTest.php index 4871abaa0..f6387709f 100644 --- a/test/php/library/Icinga/Protocol/Ldap/QueryTest.php +++ b/test/php/library/Icinga/Protocol/Ldap/QueryTest.php @@ -4,15 +4,15 @@ namespace Tests\Icinga\Protocol\Ldap; +use Icinga\Data\ConfigObject; use Icinga\Test\BaseTestCase; -use Icinga\Application\Config; use Icinga\Protocol\Ldap\Connection; class QueryTest extends BaseTestCase { private function emptySelect() { - $config = new Config( + $config = new ConfigObject( array( 'hostname' => 'localhost', 'root_dn' => 'dc=example,dc=com', diff --git a/test/php/library/Icinga/User/Store/DbStoreTest.php b/test/php/library/Icinga/User/Store/DbStoreTest.php index 30e2e1986..dfb70c66b 100644 --- a/test/php/library/Icinga/User/Store/DbStoreTest.php +++ b/test/php/library/Icinga/User/Store/DbStoreTest.php @@ -5,7 +5,7 @@ namespace Tests\Icinga\User\Preferences\Store; use Mockery; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; use Icinga\Exception\NotWritableError; use Icinga\Test\BaseTestCase; use Icinga\User\Preferences\Store\DbStore; @@ -165,7 +165,7 @@ class DbStoreTest extends BaseTestCase protected function getStore($dbMock) { return new DbStoreWithSetPreferences( - new Config( + new ConfigObject( array( 'connection' => Mockery::mock(array('getDbAdapter' => $dbMock)) ) diff --git a/test/php/library/Icinga/User/Store/IniStoreTest.php b/test/php/library/Icinga/User/Store/IniStoreTest.php index f6adc0d41..51de87840 100644 --- a/test/php/library/Icinga/User/Store/IniStoreTest.php +++ b/test/php/library/Icinga/User/Store/IniStoreTest.php @@ -5,8 +5,8 @@ namespace Tests\Icinga\User\Preferences\Store; use Mockery; +use Icinga\Data\ConfigObject; use Icinga\Test\BaseTestCase; -use Icinga\Application\Config; use Icinga\User\Preferences\Store\IniStore; class IniStoreWithSetGetPreferencesAndEmptyWrite extends IniStore @@ -61,7 +61,7 @@ class IniStoreTest extends BaseTestCase protected function getStore() { return new IniStoreWithSetGetPreferencesAndEmptyWrite( - new Config( + new ConfigObject( array( 'location' => 'some/Path/To/Some/Directory' ) diff --git a/test/php/library/Icinga/Web/MenuTest.php b/test/php/library/Icinga/Web/MenuTest.php index b0727111b..b7370d65b 100644 --- a/test/php/library/Icinga/Web/MenuTest.php +++ b/test/php/library/Icinga/Web/MenuTest.php @@ -6,19 +6,19 @@ namespace Tests\Icinga\Web; use Icinga\Web\Menu; use Icinga\Test\BaseTestCase; -use Icinga\Application\Config; +use Icinga\Data\ConfigObject; class MenuTest extends BaseTestCase { public function testWhetherMenusAreNaturallySorted() { $menu = new Menu('test'); - $menu->addSubMenu(5, new Config(array('title' => 'ccc5'))); - $menu->addSubMenu(0, new Config(array('title' => 'aaa'))); - $menu->addSubMenu(3, new Config(array('title' => 'ccc'))); - $menu->addSubMenu(2, new Config(array('title' => 'bbb'))); - $menu->addSubMenu(4, new Config(array('title' => 'ccc2'))); - $menu->addSubMenu(1, new Config(array('title' => 'bb'))); + $menu->addSubMenu(5, new ConfigObject(array('title' => 'ccc5'))); + $menu->addSubMenu(0, new ConfigObject(array('title' => 'aaa'))); + $menu->addSubMenu(3, new ConfigObject(array('title' => 'ccc'))); + $menu->addSubMenu(2, new ConfigObject(array('title' => 'bbb'))); + $menu->addSubMenu(4, new ConfigObject(array('title' => 'ccc2'))); + $menu->addSubMenu(1, new ConfigObject(array('title' => 'bb'))); $this->assertEquals( array('aaa', 'bb', 'bbb', 'ccc', 'ccc2', 'ccc5'), From 4ab5b2abf3cdb69e2734cb3bc694211171019b49 Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 18 Nov 2014 13:12:30 +0100 Subject: [PATCH 05/17] Fix anonymous onSuccess callbacks --- application/controllers/ConfigController.php | 8 ++++---- .../application/controllers/ConfigController.php | 8 ++++---- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/application/controllers/ConfigController.php b/application/controllers/ConfigController.php index 105338dfb..8f5f9eb42 100644 --- a/application/controllers/ConfigController.php +++ b/application/controllers/ConfigController.php @@ -177,10 +177,10 @@ class ConfigController extends ActionController public function removeauthenticationbackendAction() { $form = new ConfirmRemovalForm(array( - 'onSuccess' => function ($request) { + 'onSuccess' => function ($form) { $configForm = new AuthenticationBackendConfigForm(); $configForm->setIniConfig(Config::app('authentication')); - $authBackend = $request->getQuery('auth_backend'); + $authBackend = $form->getRequest()->getQuery('auth_backend'); try { $configForm->remove($authBackend); @@ -250,10 +250,10 @@ class ConfigController extends ActionController public function removeresourceAction() { $form = new ConfirmRemovalForm(array( - 'onSuccess' => function ($request) { + 'onSuccess' => function ($form) { $configForm = new ResourceConfigForm(); $configForm->setIniConfig(Config::app('resources')); - $resource = $request->getQuery('resource'); + $resource = $form->getRequest()->getQuery('resource'); try { $configForm->remove($resource); diff --git a/modules/monitoring/application/controllers/ConfigController.php b/modules/monitoring/application/controllers/ConfigController.php index 1e961d26e..ed5d57570 100644 --- a/modules/monitoring/application/controllers/ConfigController.php +++ b/modules/monitoring/application/controllers/ConfigController.php @@ -60,8 +60,8 @@ class Monitoring_ConfigController extends ModuleActionController { $config = $this->Config('backends'); $form = new ConfirmRemovalForm(array( - 'onSuccess' => function ($request) use ($config) { - $backendName = $request->getQuery('backend'); + 'onSuccess' => function ($form) use ($config) { + $backendName = $form->getRequest()->getQuery('backend'); $configForm = new BackendConfigForm(); $configForm->setIniConfig($config); @@ -92,8 +92,8 @@ class Monitoring_ConfigController extends ModuleActionController { $config = $this->Config('instances'); $form = new ConfirmRemovalForm(array( - 'onSuccess' => function ($request) use ($config) { - $instanceName = $request->getQuery('instance'); + 'onSuccess' => function ($form) use ($config) { + $instanceName = $form->getRequest()->getQuery('instance'); $configForm = new InstanceConfigForm(); $configForm->setIniConfig($config); From be6358452e9d91912ef09ab19bab9833a055ec43 Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 18 Nov 2014 13:13:02 +0100 Subject: [PATCH 06/17] Do not redirect to the wizard in case of an empty config.ini --- application/controllers/AuthenticationController.php | 11 ++--------- 1 file changed, 2 insertions(+), 9 deletions(-) diff --git a/application/controllers/AuthenticationController.php b/application/controllers/AuthenticationController.php index b0d93ddf0..00dae1c6d 100644 --- a/application/controllers/AuthenticationController.php +++ b/application/controllers/AuthenticationController.php @@ -33,15 +33,8 @@ class AuthenticationController extends ActionController */ public function loginAction() { - if (@file_exists(Config::$configDir . '/setup.token')) { - try { - $config = Config::app()->toArray(); - if (empty($config)) { - $this->redirectNow(Url::fromPath('setup')); - } - } catch (NotReadableError $e) { - // Gets thrown in case of insufficient permission only - } + if (@file_exists(Config::resolvePath('setup.token')) && !@file_exists(Config::resolvePath('config.ini'))) { + $this->redirectNow(Url::fromPath('setup')); } $auth = $this->Auth(); From 68277d3ecc474e65274a3618aa9abf90bd091cf1 Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 18 Nov 2014 13:13:34 +0100 Subject: [PATCH 07/17] Re-add build/* to .gitignore --- .gitignore | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.gitignore b/.gitignore index d7a87ccdd..3cc377b8d 100644 --- a/.gitignore +++ b/.gitignore @@ -10,3 +10,5 @@ var/log/* # Exclude symlink you need for packaging /debian + +build/* From 4a4fbaee8e239ccdfd79a23dde13b4202a90d5f5 Mon Sep 17 00:00:00 2001 From: Alexander Fuhr Date: Tue, 18 Nov 2014 14:58:05 +0100 Subject: [PATCH 08/17] Add Help decorator for icon help description refs #7696 --- library/Icinga/Web/Form/Decorator/Help.php | 33 ++++++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 library/Icinga/Web/Form/Decorator/Help.php diff --git a/library/Icinga/Web/Form/Decorator/Help.php b/library/Icinga/Web/Form/Decorator/Help.php new file mode 100644 index 000000000..1f8df2ce0 --- /dev/null +++ b/library/Icinga/Web/Form/Decorator/Help.php @@ -0,0 +1,33 @@ +getElement(); + $description = $element->getView()->escape($element->getDescription()); + + if (! empty($description)) { + $helpIcon = Icinga::app()->getViewRenderer()->view->icon('help', $description); + return $helpIcon . $content; + } + + return $content; + } +} From 38ef33276a608abed515f929f0b9e6814d79e549 Mon Sep 17 00:00:00 2001 From: Alexander Fuhr Date: Tue, 18 Nov 2014 14:58:54 +0100 Subject: [PATCH 09/17] Replace description decorator through help decorator refs #7696 resolves #7696 --- library/Icinga/Web/Form.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/library/Icinga/Web/Form.php b/library/Icinga/Web/Form.php index 854a6fa4a..1627cfe48 100644 --- a/library/Icinga/Web/Form.php +++ b/library/Icinga/Web/Form.php @@ -109,7 +109,7 @@ class Form extends Zend_Form public static $defaultElementDecorators = array( array('ViewHelper', array('separator' => '')), array('Errors', array('separator' => '')), - array('Description', array('tag' => 'span', 'class' => 'description', 'separator' => '')), + array('Help'), array('Label', array('separator' => '')), array('HtmlTag', array('tag' => 'div', 'class' => 'element')) ); From 760bf1a020f221699dc7b19c4d7fc0eb99cc3f94 Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 18 Nov 2014 15:04:11 +0100 Subject: [PATCH 10/17] Disable partial validation of forms by default --- library/Icinga/Web/Form.php | 34 ++++++++++++++++++++++++++++++++-- 1 file changed, 32 insertions(+), 2 deletions(-) diff --git a/library/Icinga/Web/Form.php b/library/Icinga/Web/Form.php index 1627cfe48..75357e2fb 100644 --- a/library/Icinga/Web/Form.php +++ b/library/Icinga/Web/Form.php @@ -101,6 +101,13 @@ class Form extends Zend_Form */ protected $uidElementName = 'formUID'; + /** + * Whether the form should validate the sent data when being automatically submitted + * + * @var bool + */ + protected $validatePartial = false; + /** * Default element decorators * @@ -333,6 +340,29 @@ class Form extends Zend_Form return $this->uidElementName; } + /** + * Set whether this form should validate the sent data when being automatically submitted + * + * @param bool $state + * + * @return self + */ + public function setValidatePartial($state) + { + $this->validatePartial = $state; + return $this; + } + + /** + * Return whether this form should validate the sent data when being automatically submitted + * + * @return bool + */ + public function getValidatePartial() + { + return $this->validatePartial; + } + /** * Create this form * @@ -580,8 +610,8 @@ class Form extends Zend_Form || ($this->onSuccess === null && false !== $this->onSuccess()))) { $this->getResponse()->redirectAndExit($this->getRedirectUrl()); } - } else { - // The form can't be processed but we want to show validation errors though + } elseif ($this->getValidatePartial()) { + // The form can't be processed but we may want to show validation errors though $this->isValidPartial($formData); } } else { From 1cbdd2b51c566eada82efdb5dd5d4e2a569dbf95 Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 18 Nov 2014 15:06:36 +0100 Subject: [PATCH 11/17] Fix that hidden elements are getting ovewritten when validating a form This works by "disabling" hidden elements which causes the browser not to submit them. Due to a bug in Zend we need to manually ensure that Form::isValid does not overwrite the value of disabled elements with null. fixes #7717 --- .../Authentication/AutologinBackendForm.php | 2 +- .../Config/Authentication/DbBackendForm.php | 2 +- .../Config/Authentication/LdapBackendForm.php | 2 +- library/Icinga/Web/Form.php | 16 ++++++++++++++++ 4 files changed, 19 insertions(+), 3 deletions(-) diff --git a/application/forms/Config/Authentication/AutologinBackendForm.php b/application/forms/Config/Authentication/AutologinBackendForm.php index 1725ea3c9..a21d2c006 100644 --- a/application/forms/Config/Authentication/AutologinBackendForm.php +++ b/application/forms/Config/Authentication/AutologinBackendForm.php @@ -66,7 +66,7 @@ class AutologinBackendForm extends Form 'hidden', 'backend', array( - 'required' => true, + 'disabled' => true, 'value' => 'autologin' ) ); diff --git a/application/forms/Config/Authentication/DbBackendForm.php b/application/forms/Config/Authentication/DbBackendForm.php index 31e6b2472..572a09c2e 100644 --- a/application/forms/Config/Authentication/DbBackendForm.php +++ b/application/forms/Config/Authentication/DbBackendForm.php @@ -75,7 +75,7 @@ class DbBackendForm extends Form 'hidden', 'backend', array( - 'required' => true, + 'disabled' => true, 'value' => 'db' ) ); diff --git a/application/forms/Config/Authentication/LdapBackendForm.php b/application/forms/Config/Authentication/LdapBackendForm.php index 3be140fb8..9b48c3dbc 100644 --- a/application/forms/Config/Authentication/LdapBackendForm.php +++ b/application/forms/Config/Authentication/LdapBackendForm.php @@ -96,7 +96,7 @@ class LdapBackendForm extends Form 'hidden', 'backend', array( - 'required' => true, + 'disabled' => true, 'value' => 'ldap' ) ); diff --git a/library/Icinga/Web/Form.php b/library/Icinga/Web/Form.php index 75357e2fb..8d75a9df3 100644 --- a/library/Icinga/Web/Form.php +++ b/library/Icinga/Web/Form.php @@ -665,6 +665,14 @@ class Form extends Zend_Form public function isValidPartial(array $formData) { $this->create($formData); + + // Ensure that disabled elements are not overwritten (http://www.zendframework.com/issues/browse/ZF-6909) + foreach ($this->getElements() as $name => $element) { + if ($element->getAttrib('disabled')) { + $formData[$name] = $element->getValue(); + } + } + return parent::isValidPartial($formData); } @@ -678,6 +686,14 @@ class Form extends Zend_Form public function isValid($formData) { $this->create($formData); + + // Ensure that disabled elements are not overwritten (http://www.zendframework.com/issues/browse/ZF-6909) + foreach ($this->getElements() as $name => $element) { + if ($element->getAttrib('disabled')) { + $formData[$name] = $element->getValue(); + } + } + return parent::isValid($formData); } From 7eab09c2a214acb89cae3eb56aa59b3805d4db7c Mon Sep 17 00:00:00 2001 From: Eric Lippmann Date: Tue, 18 Nov 2014 16:06:39 +0100 Subject: [PATCH 12/17] Tests: Fix ApplicationBootstrap mock --- library/Icinga/Test/BaseTestCase.php | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/library/Icinga/Test/BaseTestCase.php b/library/Icinga/Test/BaseTestCase.php index 41cd1099c..c70bc5cd9 100644 --- a/library/Icinga/Test/BaseTestCase.php +++ b/library/Icinga/Test/BaseTestCase.php @@ -158,11 +158,17 @@ namespace Icinga\Test { ->andReturnUsing(function ($name, $default) { return $default; })->byDefault(); $responseMock = Mockery::mock('Icinga\Web\Response')->shouldDeferMissing(); - // Can't express this as demeter chains. See: https://github.com/padraic/mockery/issues/59 $bootstrapMock = Mockery::mock('Icinga\Application\ApplicationBootstrap')->shouldDeferMissing(); + $libDir = dirname(self::$libDir); $bootstrapMock->shouldReceive('getFrontController')->andReturn($bootstrapMock) ->shouldReceive('getApplicationDir')->andReturn(self::$appDir) + ->shouldReceive('getLibraryDir')->andReturnUsing(function ($subdir = null) use ($libDir) { + if ($subdir !== null) { + $libDir .= '/' . ltrim($subdir, '/'); + } + return $libDir; + }) ->shouldReceive('getRequest')->andReturn($requestMock) ->shouldReceive('getResponse')->andReturn($responseMock); From 7a7157ebef9b112f2189062b37f538ed15e45ccd Mon Sep 17 00:00:00 2001 From: Alexander Fuhr Date: Tue, 18 Nov 2014 16:10:17 +0100 Subject: [PATCH 13/17] Move command note to the `getHelp()' and add the help as an icon --- .../application/forms/Command/CommandForm.php | 10 +++++++ .../DisableNotificationsExpireCommandForm.php | 22 +++++++------- .../Object/AcknowledgeProblemCommandForm.php | 26 ++++++++-------- .../Command/Object/AddCommentCommandForm.php | 22 +++++++------- .../ScheduleServiceCheckCommandForm.php | 13 ++++++++ .../ScheduleServiceDowntimeCommandForm.php | 30 ++++++++++--------- .../views/scripts/partials/command-form.phtml | 4 +-- .../process/disable-notifications.phtml | 2 +- 8 files changed, 80 insertions(+), 49 deletions(-) diff --git a/modules/monitoring/application/forms/Command/CommandForm.php b/modules/monitoring/application/forms/Command/CommandForm.php index 807e1e6ca..fd67e140d 100644 --- a/modules/monitoring/application/forms/Command/CommandForm.php +++ b/modules/monitoring/application/forms/Command/CommandForm.php @@ -44,6 +44,16 @@ abstract class CommandForm extends Form return $this->backend; } + /** + * Get the command help description + * + * @return string|null + */ + public function getHelp() + { + return null; + } + /** * Get the transport used to send commands * diff --git a/modules/monitoring/application/forms/Command/Instance/DisableNotificationsExpireCommandForm.php b/modules/monitoring/application/forms/Command/Instance/DisableNotificationsExpireCommandForm.php index 5620d4908..0e64a4b03 100644 --- a/modules/monitoring/application/forms/Command/Instance/DisableNotificationsExpireCommandForm.php +++ b/modules/monitoring/application/forms/Command/Instance/DisableNotificationsExpireCommandForm.php @@ -24,22 +24,24 @@ class DisableNotificationsExpireCommandForm extends CommandForm $this->setSubmitLabel(mt('monitoring', 'Disable Notifications')); } + /** + * (non-PHPDoc) + * @see \Icinga\Module\Monitoring\Forms\Command\CommandForm::getHelp() For the method documentation. + */ + public function getHelp() + { + return mt( + 'monitoring', + 'This command is used to disable host and service notifications for a specific time.' + ); + } + /** * (non-PHPDoc) * @see \Icinga\Web\Form::createElements() For the method documentation. */ public function createElements(array $formData = array()) { - $this->addElement( - 'note', - 'command-info', - array( - 'value' => mt( - 'monitoring', - 'This command is used to disable host and service notifications for a specific time.' - ) - ) - ); $expireTime = new DateTime(); $expireTime->add(new DateInterval('PT1H')); $this->addElement( diff --git a/modules/monitoring/application/forms/Command/Object/AcknowledgeProblemCommandForm.php b/modules/monitoring/application/forms/Command/Object/AcknowledgeProblemCommandForm.php index 9123fddc1..3456e1bfb 100644 --- a/modules/monitoring/application/forms/Command/Object/AcknowledgeProblemCommandForm.php +++ b/modules/monitoring/application/forms/Command/Object/AcknowledgeProblemCommandForm.php @@ -25,6 +25,20 @@ class AcknowledgeProblemCommandForm extends ObjectsCommandForm ); } + /** + * (non-PHPDoc) + * @see \Icinga\Module\Monitoring\Forms\Command\CommandForm::getHelp() For the method documentation. + */ + public function getHelp() + { + return mt( + 'monitoring', + 'This command is used to acknowledge host or service problems. When a problem is acknowledged,' + . ' future notifications about problems are temporarily disabled until the host or service' + . ' recovers.' + ); + } + /** * (non-PHPDoc) * @see \Icinga\Web\Form::createElements() For the method documentation. @@ -32,18 +46,6 @@ class AcknowledgeProblemCommandForm extends ObjectsCommandForm public function createElements(array $formData = array()) { $this->addElements(array( - array( - 'note', - 'command-info', - array( - 'value' => mt( - 'monitoring', - 'This command is used to acknowledge host or service problems. When a problem is acknowledged,' - . ' future notifications about problems are temporarily disabled until the host or service' - . ' recovers.' - ) - ) - ), array( 'textarea', 'comment', diff --git a/modules/monitoring/application/forms/Command/Object/AddCommentCommandForm.php b/modules/monitoring/application/forms/Command/Object/AddCommentCommandForm.php index 5d9a71d51..f5adf6c71 100644 --- a/modules/monitoring/application/forms/Command/Object/AddCommentCommandForm.php +++ b/modules/monitoring/application/forms/Command/Object/AddCommentCommandForm.php @@ -23,6 +23,18 @@ class AddCommentCommandForm extends ObjectsCommandForm ); } + /** + * (non-PHPDoc) + * @see \Icinga\Module\Monitoring\Forms\Command\CommandForm::getHelp() For the method documentation. + */ + public function getHelp() + { + return mt( + 'monitoring', + 'This command is used to add host or service comments.' + ); + } + /** * (non-PHPDoc) * @see \Icinga\Web\Form::createElements() For the method documentation. @@ -30,16 +42,6 @@ class AddCommentCommandForm extends ObjectsCommandForm public function createElements(array $formData = array()) { $this->addElements(array( - array( - 'note', - 'command-info', - array( - 'value' => mt( - 'monitoring', - 'This command is used to add host or service comments.' - ) - ) - ), array( 'textarea', 'comment', diff --git a/modules/monitoring/application/forms/Command/Object/ScheduleServiceCheckCommandForm.php b/modules/monitoring/application/forms/Command/Object/ScheduleServiceCheckCommandForm.php index faba7a769..9e04a2254 100644 --- a/modules/monitoring/application/forms/Command/Object/ScheduleServiceCheckCommandForm.php +++ b/modules/monitoring/application/forms/Command/Object/ScheduleServiceCheckCommandForm.php @@ -26,6 +26,19 @@ class ScheduleServiceCheckCommandForm extends ObjectsCommandForm ); } + /** + * (non-PHPDoc) + * @see \Icinga\Module\Monitoring\Forms\Command\CommandForm::getHelp() For the method documentation. + */ + public function getHelp() + { + return mt( + 'monitoring', + 'This command is used to schedule the next check of hosts or services. Icinga will re-queue the' + . ' hosts or services to be checked at the time you specify.' + ); + } + /** * (non-PHPDoc) * @see \Icinga\Web\Form::createElements() For the method documentation. diff --git a/modules/monitoring/application/forms/Command/Object/ScheduleServiceDowntimeCommandForm.php b/modules/monitoring/application/forms/Command/Object/ScheduleServiceDowntimeCommandForm.php index 18bbd0593..9fd86a82b 100644 --- a/modules/monitoring/application/forms/Command/Object/ScheduleServiceDowntimeCommandForm.php +++ b/modules/monitoring/application/forms/Command/Object/ScheduleServiceDowntimeCommandForm.php @@ -36,6 +36,22 @@ class ScheduleServiceDowntimeCommandForm extends ObjectsCommandForm ); } + /** + * (non-PHPDoc) + * @see \Icinga\Module\Monitoring\Forms\Command\CommandForm::getHelp() For the method documentation. + */ + public function getHelp() + { + return mt( + 'monitoring', + 'This command is used to schedule host and service downtimes. During the specified downtime,' + . ' Icinga will not send notifications out about the hosts and services. When the scheduled' + . ' downtime expires, Icinga will send out notifications for the hosts and services as it' + . ' normally would. Scheduled downtimes are preserved across program shutdowns and' + . ' restarts.' + ); + } + /** * (non-PHPDoc) * @see \Icinga\Web\Form::createElements() For the method documentation. @@ -46,20 +62,6 @@ class ScheduleServiceDowntimeCommandForm extends ObjectsCommandForm $end = clone $start; $end->add(new DateInterval('PT1H')); $this->addElements(array( - array( - 'note', - 'command-info', - array( - 'value' => mt( - 'monitoring', - 'This command is used to schedule host and service downtimes. During the specified downtime,' - . ' Icinga will not send notifications out about the hosts and services. When the scheduled' - . ' downtime expires, Icinga will send out notifications for the hosts and services as it' - . ' normally would. Scheduled downtimes are preserved across program shutdowns and' - . ' restarts.' - ) - ) - ), array( 'textarea', 'comment', diff --git a/modules/monitoring/application/views/scripts/partials/command-form.phtml b/modules/monitoring/application/views/scripts/partials/command-form.phtml index 4740f3348..b6990cf25 100644 --- a/modules/monitoring/application/views/scripts/partials/command-form.phtml +++ b/modules/monitoring/application/views/scripts/partials/command-form.phtml @@ -1,9 +1,9 @@
tabs->showOnlyCloseButton() ?>
- +
-

+

icon('help', $form->getHelp()) ?>

diff --git a/modules/monitoring/application/views/scripts/process/disable-notifications.phtml b/modules/monitoring/application/views/scripts/process/disable-notifications.phtml index 547b3ac37..2fb3c6c6e 100644 --- a/modules/monitoring/application/views/scripts/process/disable-notifications.phtml +++ b/modules/monitoring/application/views/scripts/process/disable-notifications.phtml @@ -2,7 +2,7 @@ tabs->showOnlyCloseButton() ?>
-

+

icon('help', $form->getHelp()) ?>

notifications_enabled === false): ?>
translate('Host and service notifications are already disabled.') ?> From 4f55a9e3eb3ccb4f0563f52d00be52258a83fc08 Mon Sep 17 00:00:00 2001 From: Eric Lippmann Date: Tue, 18 Nov 2014 16:15:48 +0100 Subject: [PATCH 14/17] Remove Icinga-Design from doc --- doc/Icinga-Design/bootstrap.min.css | 9 - doc/Icinga-Design/documentation.css | 125 --- doc/Icinga-Design/documentation.html | 974 ------------------ doc/Icinga-Design/icinga-design.css | 955 ----------------- doc/Icinga-Design/images/acknowledgement.png | Bin 501 -> 0 bytes doc/Icinga-Design/images/comment.png | Bin 491 -> 0 bytes doc/Icinga-Design/images/comment_petrol.png | Bin 502 -> 0 bytes .../images/configuration_petrol.png | Bin 645 -> 0 bytes doc/Icinga-Design/images/create.png | Bin 475 -> 0 bytes doc/Icinga-Design/images/dashboard.png | Bin 415 -> 0 bytes doc/Icinga-Design/images/dashboard_petrol.png | Bin 420 -> 0 bytes doc/Icinga-Design/images/disabled.png | Bin 535 -> 0 bytes doc/Icinga-Design/images/edit.png | Bin 486 -> 0 bytes doc/Icinga-Design/images/error.png | Bin 532 -> 0 bytes doc/Icinga-Design/images/flapping.png | Bin 621 -> 0 bytes doc/Icinga-Design/images/host.png | Bin 512 -> 0 bytes doc/Icinga-Design/images/host_petrol.png | Bin 489 -> 0 bytes doc/Icinga-Design/images/in_downtime.png | Bin 490 -> 0 bytes .../images/in_downtime_petrol.png | Bin 497 -> 0 bytes doc/Icinga-Design/images/logo_icinga.png | Bin 2619 -> 0 bytes .../images/notification_petrol.png | Bin 604 -> 0 bytes doc/Icinga-Design/images/refresh.png | Bin 523 -> 0 bytes doc/Icinga-Design/images/remove.png | Bin 661 -> 0 bytes doc/Icinga-Design/images/reschedule.png | Bin 400 -> 0 bytes doc/Icinga-Design/images/save.png | Bin 506 -> 0 bytes doc/Icinga-Design/images/search.png | Bin 491 -> 0 bytes doc/Icinga-Design/images/service.png | Bin 496 -> 0 bytes doc/Icinga-Design/images/service_petrol.png | Bin 505 -> 0 bytes doc/Icinga-Design/images/submit.png | Bin 418 -> 0 bytes doc/Icinga-Design/images/unhandled.png | Bin 553 -> 0 bytes doc/Icinga-Design/images/user.png | Bin 487 -> 0 bytes 31 files changed, 2063 deletions(-) delete mode 100644 doc/Icinga-Design/bootstrap.min.css delete mode 100644 doc/Icinga-Design/documentation.css delete mode 100644 doc/Icinga-Design/documentation.html delete mode 100644 doc/Icinga-Design/icinga-design.css delete mode 100644 doc/Icinga-Design/images/acknowledgement.png delete mode 100644 doc/Icinga-Design/images/comment.png delete mode 100644 doc/Icinga-Design/images/comment_petrol.png delete mode 100644 doc/Icinga-Design/images/configuration_petrol.png delete mode 100644 doc/Icinga-Design/images/create.png delete mode 100644 doc/Icinga-Design/images/dashboard.png delete mode 100644 doc/Icinga-Design/images/dashboard_petrol.png delete mode 100644 doc/Icinga-Design/images/disabled.png delete mode 100644 doc/Icinga-Design/images/edit.png delete mode 100644 doc/Icinga-Design/images/error.png delete mode 100644 doc/Icinga-Design/images/flapping.png delete mode 100644 doc/Icinga-Design/images/host.png delete mode 100644 doc/Icinga-Design/images/host_petrol.png delete mode 100644 doc/Icinga-Design/images/in_downtime.png delete mode 100644 doc/Icinga-Design/images/in_downtime_petrol.png delete mode 100644 doc/Icinga-Design/images/logo_icinga.png delete mode 100644 doc/Icinga-Design/images/notification_petrol.png delete mode 100644 doc/Icinga-Design/images/refresh.png delete mode 100644 doc/Icinga-Design/images/remove.png delete mode 100644 doc/Icinga-Design/images/reschedule.png delete mode 100644 doc/Icinga-Design/images/save.png delete mode 100644 doc/Icinga-Design/images/search.png delete mode 100644 doc/Icinga-Design/images/service.png delete mode 100644 doc/Icinga-Design/images/service_petrol.png delete mode 100644 doc/Icinga-Design/images/submit.png delete mode 100644 doc/Icinga-Design/images/unhandled.png delete mode 100644 doc/Icinga-Design/images/user.png diff --git a/doc/Icinga-Design/bootstrap.min.css b/doc/Icinga-Design/bootstrap.min.css deleted file mode 100644 index a553c4f5e..000000000 --- a/doc/Icinga-Design/bootstrap.min.css +++ /dev/null @@ -1,9 +0,0 @@ -/*! - * Bootstrap v3.0.0 - * - * Copyright 2013 Twitter, Inc - * Licensed under the Apache License v2.0 - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Designed and built with all the love in the world by @mdo and @fat. - *//*! normalize.css v2.1.0 | MIT License | git.io/normalize */article,aside,details,figcaption,figure,footer,header,hgroup,main,nav,section,summary{display:block}audio,canvas,video{display:inline-block}audio:not([controls]){display:none;height:0}[hidden]{display:none}html{font-family:sans-serif;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%}body{margin:0}a:focus{outline:thin dotted}a:active,a:hover{outline:0}h1{margin:.67em 0;font-size:2em}abbr[title]{border-bottom:1px dotted}b,strong{font-weight:bold}dfn{font-style:italic}hr{height:0;-moz-box-sizing:content-box;box-sizing:content-box}mark{color:#000;background:#ff0}code,kbd,pre,samp{font-family:monospace,serif;font-size:1em}pre{white-space:pre-wrap}q{quotes:"\201C" "\201D" "\2018" "\2019"}small{font-size:80%}sub,sup{position:relative;font-size:75%;line-height:0;vertical-align:baseline}sup{top:-0.5em}sub{bottom:-0.25em}img{border:0}svg:not(:root){overflow:hidden}figure{margin:0}fieldset{padding:.35em .625em .75em;margin:0 2px;border:1px solid #c0c0c0}legend{padding:0;border:0}button,input,select,textarea{margin:0;font-family:inherit;font-size:100%}button,input{line-height:normal}button,select{text-transform:none}button,html input[type="button"],input[type="reset"],input[type="submit"]{cursor:pointer;-webkit-appearance:button}button[disabled],html input[disabled]{cursor:default}input[type="checkbox"],input[type="radio"]{padding:0;box-sizing:border-box}input[type="search"]{-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box;-webkit-appearance:textfield}input[type="search"]::-webkit-search-cancel-button,input[type="search"]::-webkit-search-decoration{-webkit-appearance:none}button::-moz-focus-inner,input::-moz-focus-inner{padding:0;border:0}textarea{overflow:auto;vertical-align:top}table{border-collapse:collapse;border-spacing:0}@media print{*{color:#000!important;text-shadow:none!important;background:transparent!important;box-shadow:none!important}a,a:visited{text-decoration:underline}a[href]:after{content:" (" attr(href) ")"}abbr[title]:after{content:" (" attr(title) ")"}.ir a:after,a[href^="javascript:"]:after,a[href^="#"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100%!important}@page{margin:2cm .5cm}p,h2,h3{orphans:3;widows:3}h2,h3{page-break-after:avoid}.navbar{display:none}.table td,.table th{background-color:#fff!important}.btn>.caret,.dropup>.btn>.caret{border-top-color:#000!important}.label{border:1px solid #000}.table{border-collapse:collapse!important}.table-bordered th,.table-bordered td{border:1px solid #ddd!important}}*,*:before,*:after{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}html{font-size:62.5%;-webkit-tap-highlight-color:rgba(0,0,0,0)}body{font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:14px;line-height:1.428571429;color:#333;background-color:#fff}input,button,select,textarea{font-family:inherit;font-size:inherit;line-height:inherit}button,input,select[multiple],textarea{background-image:none}a{color:#428bca;text-decoration:none}a:hover,a:focus{color:#2a6496;text-decoration:underline}a:focus{outline:thin dotted #333;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}img{vertical-align:middle}.img-responsive{display:block;height:auto;max-width:100%}.img-rounded{border-radius:6px}.img-thumbnail{display:inline-block;height:auto;max-width:100%;padding:4px;line-height:1.428571429;background-color:#fff;border:1px solid #ddd;border-radius:4px;-webkit-transition:all .2s ease-in-out;transition:all .2s ease-in-out}.img-circle{border-radius:50%}hr{margin-top:20px;margin-bottom:20px;border:0;border-top:1px solid #eee}.sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0 0 0 0);border:0}p{margin:0 0 10px}.lead{margin-bottom:20px;font-size:16.099999999999998px;font-weight:200;line-height:1.4}@media(min-width:768px){.lead{font-size:21px}}small{font-size:85%}cite{font-style:normal}.text-muted{color:#999}.text-primary{color:#428bca}.text-warning{color:#c09853}.text-danger{color:#b94a48}.text-success{color:#468847}.text-info{color:#3a87ad}.text-left{text-align:left}.text-right{text-align:right}.text-center{text-align:center}h1,h2,h3,h4,h5,h6,.h1,.h2,.h3,.h4,.h5,.h6{font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-weight:500;line-height:1.1}h1 small,h2 small,h3 small,h4 small,h5 small,h6 small,.h1 small,.h2 small,.h3 small,.h4 small,.h5 small,.h6 small{font-weight:normal;line-height:1;color:#999}h1,h2,h3{margin-top:20px;margin-bottom:10px}h4,h5,h6{margin-top:10px;margin-bottom:10px}h1,.h1{font-size:36px}h2,.h2{font-size:30px}h3,.h3{font-size:24px}h4,.h4{font-size:18px}h5,.h5{font-size:14px}h6,.h6{font-size:12px}h1 small,.h1 small{font-size:24px}h2 small,.h2 small{font-size:18px}h3 small,.h3 small,h4 small,.h4 small{font-size:14px}.page-header{padding-bottom:9px;margin:40px 0 20px;border-bottom:1px solid #eee}ul,ol{margin-top:0;margin-bottom:10px}ul ul,ol ul,ul ol,ol ol{margin-bottom:0}.list-unstyled{padding-left:0;list-style:none}.list-inline{padding-left:0;list-style:none}.list-inline>li{display:inline-block;padding-right:5px;padding-left:5px}dl{margin-bottom:20px}dt,dd{line-height:1.428571429}dt{font-weight:bold}dd{margin-left:0}@media(min-width:768px){.dl-horizontal dt{float:left;width:160px;overflow:hidden;clear:left;text-align:right;text-overflow:ellipsis;white-space:nowrap}.dl-horizontal dd{margin-left:180px}.dl-horizontal dd:before,.dl-horizontal dd:after{display:table;content:" "}.dl-horizontal dd:after{clear:both}.dl-horizontal dd:before,.dl-horizontal dd:after{display:table;content:" "}.dl-horizontal dd:after{clear:both}}abbr[title],abbr[data-original-title]{cursor:help;border-bottom:1px dotted #999}abbr.initialism{font-size:90%;text-transform:uppercase}blockquote{padding:10px 20px;margin:0 0 20px;border-left:5px solid #eee}blockquote p{font-size:17.5px;font-weight:300;line-height:1.25}blockquote p:last-child{margin-bottom:0}blockquote small{display:block;line-height:1.428571429;color:#999}blockquote small:before{content:'\2014 \00A0'}blockquote.pull-right{padding-right:15px;padding-left:0;border-right:5px solid #eee;border-left:0}blockquote.pull-right p,blockquote.pull-right small{text-align:right}blockquote.pull-right small:before{content:''}blockquote.pull-right small:after{content:'\00A0 \2014'}q:before,q:after,blockquote:before,blockquote:after{content:""}address{display:block;margin-bottom:20px;font-style:normal;line-height:1.428571429}code,pre{font-family:Monaco,Menlo,Consolas,"Courier New",monospace}code{padding:2px 4px;font-size:90%;color:#c7254e;white-space:nowrap;background-color:#f9f2f4;border-radius:4px}pre{display:block;padding:9.5px;margin:0 0 10px;font-size:13px;line-height:1.428571429;color:#333;word-break:break-all;word-wrap:break-word;background-color:#f5f5f5;border:1px solid #ccc;border-radius:4px}pre.prettyprint{margin-bottom:20px}pre code{padding:0;font-size:inherit;color:inherit;white-space:pre-wrap;background-color:transparent;border:0}.pre-scrollable{max-height:340px;overflow-y:scroll}.container{padding-right:15px;padding-left:15px;margin-right:auto;margin-left:auto}.container:before,.container:after{display:table;content:" "}.container:after{clear:both}.container:before,.container:after{display:table;content:" "}.container:after{clear:both}.row{margin-right:-15px;margin-left:-15px}.row:before,.row:after{display:table;content:" "}.row:after{clear:both}.row:before,.row:after{display:table;content:" "}.row:after{clear:both}.col-xs-1,.col-xs-2,.col-xs-3,.col-xs-4,.col-xs-5,.col-xs-6,.col-xs-7,.col-xs-8,.col-xs-9,.col-xs-10,.col-xs-11,.col-xs-12,.col-sm-1,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9,.col-sm-10,.col-sm-11,.col-sm-12,.col-md-1,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9,.col-md-10,.col-md-11,.col-md-12,.col-lg-1,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9,.col-lg-10,.col-lg-11,.col-lg-12{position:relative;min-height:1px;padding-right:15px;padding-left:15px}.col-xs-1,.col-xs-2,.col-xs-3,.col-xs-4,.col-xs-5,.col-xs-6,.col-xs-7,.col-xs-8,.col-xs-9,.col-xs-10,.col-xs-11{float:left}.col-xs-1{width:8.333333333333332%}.col-xs-2{width:16.666666666666664%}.col-xs-3{width:25%}.col-xs-4{width:33.33333333333333%}.col-xs-5{width:41.66666666666667%}.col-xs-6{width:50%}.col-xs-7{width:58.333333333333336%}.col-xs-8{width:66.66666666666666%}.col-xs-9{width:75%}.col-xs-10{width:83.33333333333334%}.col-xs-11{width:91.66666666666666%}.col-xs-12{width:100%}@media(min-width:768px){.container{max-width:750px}.col-sm-1,.col-sm-2,.col-sm-3,.col-sm-4,.col-sm-5,.col-sm-6,.col-sm-7,.col-sm-8,.col-sm-9,.col-sm-10,.col-sm-11{float:left}.col-sm-1{width:8.333333333333332%}.col-sm-2{width:16.666666666666664%}.col-sm-3{width:25%}.col-sm-4{width:33.33333333333333%}.col-sm-5{width:41.66666666666667%}.col-sm-6{width:50%}.col-sm-7{width:58.333333333333336%}.col-sm-8{width:66.66666666666666%}.col-sm-9{width:75%}.col-sm-10{width:83.33333333333334%}.col-sm-11{width:91.66666666666666%}.col-sm-12{width:100%}.col-sm-push-1{left:8.333333333333332%}.col-sm-push-2{left:16.666666666666664%}.col-sm-push-3{left:25%}.col-sm-push-4{left:33.33333333333333%}.col-sm-push-5{left:41.66666666666667%}.col-sm-push-6{left:50%}.col-sm-push-7{left:58.333333333333336%}.col-sm-push-8{left:66.66666666666666%}.col-sm-push-9{left:75%}.col-sm-push-10{left:83.33333333333334%}.col-sm-push-11{left:91.66666666666666%}.col-sm-pull-1{right:8.333333333333332%}.col-sm-pull-2{right:16.666666666666664%}.col-sm-pull-3{right:25%}.col-sm-pull-4{right:33.33333333333333%}.col-sm-pull-5{right:41.66666666666667%}.col-sm-pull-6{right:50%}.col-sm-pull-7{right:58.333333333333336%}.col-sm-pull-8{right:66.66666666666666%}.col-sm-pull-9{right:75%}.col-sm-pull-10{right:83.33333333333334%}.col-sm-pull-11{right:91.66666666666666%}.col-sm-offset-1{margin-left:8.333333333333332%}.col-sm-offset-2{margin-left:16.666666666666664%}.col-sm-offset-3{margin-left:25%}.col-sm-offset-4{margin-left:33.33333333333333%}.col-sm-offset-5{margin-left:41.66666666666667%}.col-sm-offset-6{margin-left:50%}.col-sm-offset-7{margin-left:58.333333333333336%}.col-sm-offset-8{margin-left:66.66666666666666%}.col-sm-offset-9{margin-left:75%}.col-sm-offset-10{margin-left:83.33333333333334%}.col-sm-offset-11{margin-left:91.66666666666666%}}@media(min-width:992px){.container{max-width:970px}.col-md-1,.col-md-2,.col-md-3,.col-md-4,.col-md-5,.col-md-6,.col-md-7,.col-md-8,.col-md-9,.col-md-10,.col-md-11{float:left}.col-md-1{width:8.333333333333332%}.col-md-2{width:16.666666666666664%}.col-md-3{width:25%}.col-md-4{width:33.33333333333333%}.col-md-5{width:41.66666666666667%}.col-md-6{width:50%}.col-md-7{width:58.333333333333336%}.col-md-8{width:66.66666666666666%}.col-md-9{width:75%}.col-md-10{width:83.33333333333334%}.col-md-11{width:91.66666666666666%}.col-md-12{width:100%}.col-md-push-0{left:auto}.col-md-push-1{left:8.333333333333332%}.col-md-push-2{left:16.666666666666664%}.col-md-push-3{left:25%}.col-md-push-4{left:33.33333333333333%}.col-md-push-5{left:41.66666666666667%}.col-md-push-6{left:50%}.col-md-push-7{left:58.333333333333336%}.col-md-push-8{left:66.66666666666666%}.col-md-push-9{left:75%}.col-md-push-10{left:83.33333333333334%}.col-md-push-11{left:91.66666666666666%}.col-md-pull-0{right:auto}.col-md-pull-1{right:8.333333333333332%}.col-md-pull-2{right:16.666666666666664%}.col-md-pull-3{right:25%}.col-md-pull-4{right:33.33333333333333%}.col-md-pull-5{right:41.66666666666667%}.col-md-pull-6{right:50%}.col-md-pull-7{right:58.333333333333336%}.col-md-pull-8{right:66.66666666666666%}.col-md-pull-9{right:75%}.col-md-pull-10{right:83.33333333333334%}.col-md-pull-11{right:91.66666666666666%}.col-md-offset-0{margin-left:0}.col-md-offset-1{margin-left:8.333333333333332%}.col-md-offset-2{margin-left:16.666666666666664%}.col-md-offset-3{margin-left:25%}.col-md-offset-4{margin-left:33.33333333333333%}.col-md-offset-5{margin-left:41.66666666666667%}.col-md-offset-6{margin-left:50%}.col-md-offset-7{margin-left:58.333333333333336%}.col-md-offset-8{margin-left:66.66666666666666%}.col-md-offset-9{margin-left:75%}.col-md-offset-10{margin-left:83.33333333333334%}.col-md-offset-11{margin-left:91.66666666666666%}}@media(min-width:1200px){.container{max-width:1170px}.col-lg-1,.col-lg-2,.col-lg-3,.col-lg-4,.col-lg-5,.col-lg-6,.col-lg-7,.col-lg-8,.col-lg-9,.col-lg-10,.col-lg-11{float:left}.col-lg-1{width:8.333333333333332%}.col-lg-2{width:16.666666666666664%}.col-lg-3{width:25%}.col-lg-4{width:33.33333333333333%}.col-lg-5{width:41.66666666666667%}.col-lg-6{width:50%}.col-lg-7{width:58.333333333333336%}.col-lg-8{width:66.66666666666666%}.col-lg-9{width:75%}.col-lg-10{width:83.33333333333334%}.col-lg-11{width:91.66666666666666%}.col-lg-12{width:100%}.col-lg-push-0{left:auto}.col-lg-push-1{left:8.333333333333332%}.col-lg-push-2{left:16.666666666666664%}.col-lg-push-3{left:25%}.col-lg-push-4{left:33.33333333333333%}.col-lg-push-5{left:41.66666666666667%}.col-lg-push-6{left:50%}.col-lg-push-7{left:58.333333333333336%}.col-lg-push-8{left:66.66666666666666%}.col-lg-push-9{left:75%}.col-lg-push-10{left:83.33333333333334%}.col-lg-push-11{left:91.66666666666666%}.col-lg-pull-0{right:auto}.col-lg-pull-1{right:8.333333333333332%}.col-lg-pull-2{right:16.666666666666664%}.col-lg-pull-3{right:25%}.col-lg-pull-4{right:33.33333333333333%}.col-lg-pull-5{right:41.66666666666667%}.col-lg-pull-6{right:50%}.col-lg-pull-7{right:58.333333333333336%}.col-lg-pull-8{right:66.66666666666666%}.col-lg-pull-9{right:75%}.col-lg-pull-10{right:83.33333333333334%}.col-lg-pull-11{right:91.66666666666666%}.col-lg-offset-0{margin-left:0}.col-lg-offset-1{margin-left:8.333333333333332%}.col-lg-offset-2{margin-left:16.666666666666664%}.col-lg-offset-3{margin-left:25%}.col-lg-offset-4{margin-left:33.33333333333333%}.col-lg-offset-5{margin-left:41.66666666666667%}.col-lg-offset-6{margin-left:50%}.col-lg-offset-7{margin-left:58.333333333333336%}.col-lg-offset-8{margin-left:66.66666666666666%}.col-lg-offset-9{margin-left:75%}.col-lg-offset-10{margin-left:83.33333333333334%}.col-lg-offset-11{margin-left:91.66666666666666%}}table{max-width:100%;background-color:transparent}th{text-align:left}.table{width:100%;margin-bottom:20px}.table thead>tr>th,.table tbody>tr>th,.table tfoot>tr>th,.table thead>tr>td,.table tbody>tr>td,.table tfoot>tr>td{padding:8px;line-height:1.428571429;vertical-align:top;border-top:1px solid #ddd}.table thead>tr>th{vertical-align:bottom;border-bottom:2px solid #ddd}.table caption+thead tr:first-child th,.table colgroup+thead tr:first-child th,.table thead:first-child tr:first-child th,.table caption+thead tr:first-child td,.table colgroup+thead tr:first-child td,.table thead:first-child tr:first-child td{border-top:0}.table tbody+tbody{border-top:2px solid #ddd}.table .table{background-color:#fff}.table-condensed thead>tr>th,.table-condensed tbody>tr>th,.table-condensed tfoot>tr>th,.table-condensed thead>tr>td,.table-condensed tbody>tr>td,.table-condensed tfoot>tr>td{padding:5px}.table-bordered{border:1px solid #ddd}.table-bordered>thead>tr>th,.table-bordered>tbody>tr>th,.table-bordered>tfoot>tr>th,.table-bordered>thead>tr>td,.table-bordered>tbody>tr>td,.table-bordered>tfoot>tr>td{border:1px solid #ddd}.table-bordered>thead>tr>th,.table-bordered>thead>tr>td{border-bottom-width:2px}.table-striped>tbody>tr:nth-child(odd)>td,.table-striped>tbody>tr:nth-child(odd)>th{background-color:#f9f9f9}.table-hover>tbody>tr:hover>td,.table-hover>tbody>tr:hover>th{background-color:#f5f5f5}table col[class*="col-"]{display:table-column;float:none}table td[class*="col-"],table th[class*="col-"]{display:table-cell;float:none}.table>thead>tr>td.active,.table>tbody>tr>td.active,.table>tfoot>tr>td.active,.table>thead>tr>th.active,.table>tbody>tr>th.active,.table>tfoot>tr>th.active,.table>thead>tr.active>td,.table>tbody>tr.active>td,.table>tfoot>tr.active>td,.table>thead>tr.active>th,.table>tbody>tr.active>th,.table>tfoot>tr.active>th{background-color:#f5f5f5}.table>thead>tr>td.success,.table>tbody>tr>td.success,.table>tfoot>tr>td.success,.table>thead>tr>th.success,.table>tbody>tr>th.success,.table>tfoot>tr>th.success,.table>thead>tr.success>td,.table>tbody>tr.success>td,.table>tfoot>tr.success>td,.table>thead>tr.success>th,.table>tbody>tr.success>th,.table>tfoot>tr.success>th{background-color:#dff0d8;border-color:#d6e9c6}.table-hover>tbody>tr>td.success:hover,.table-hover>tbody>tr>th.success:hover,.table-hover>tbody>tr.success:hover>td{background-color:#d0e9c6;border-color:#c9e2b3}.table>thead>tr>td.danger,.table>tbody>tr>td.danger,.table>tfoot>tr>td.danger,.table>thead>tr>th.danger,.table>tbody>tr>th.danger,.table>tfoot>tr>th.danger,.table>thead>tr.danger>td,.table>tbody>tr.danger>td,.table>tfoot>tr.danger>td,.table>thead>tr.danger>th,.table>tbody>tr.danger>th,.table>tfoot>tr.danger>th{background-color:#f2dede;border-color:#eed3d7}.table-hover>tbody>tr>td.danger:hover,.table-hover>tbody>tr>th.danger:hover,.table-hover>tbody>tr.danger:hover>td{background-color:#ebcccc;border-color:#e6c1c7}.table>thead>tr>td.warning,.table>tbody>tr>td.warning,.table>tfoot>tr>td.warning,.table>thead>tr>th.warning,.table>tbody>tr>th.warning,.table>tfoot>tr>th.warning,.table>thead>tr.warning>td,.table>tbody>tr.warning>td,.table>tfoot>tr.warning>td,.table>thead>tr.warning>th,.table>tbody>tr.warning>th,.table>tfoot>tr.warning>th{background-color:#fcf8e3;border-color:#fbeed5}.table-hover>tbody>tr>td.warning:hover,.table-hover>tbody>tr>th.warning:hover,.table-hover>tbody>tr.warning:hover>td{background-color:#faf2cc;border-color:#f8e5be}@media(max-width:768px){.table-responsive{width:100%;margin-bottom:15px;overflow-x:scroll;overflow-y:hidden;border:1px solid #ddd}.table-responsive>.table{margin-bottom:0;background-color:#fff}.table-responsive>.table>thead>tr>th,.table-responsive>.table>tbody>tr>th,.table-responsive>.table>tfoot>tr>th,.table-responsive>.table>thead>tr>td,.table-responsive>.table>tbody>tr>td,.table-responsive>.table>tfoot>tr>td{white-space:nowrap}.table-responsive>.table-bordered{border:0}.table-responsive>.table-bordered>thead>tr>th:first-child,.table-responsive>.table-bordered>tbody>tr>th:first-child,.table-responsive>.table-bordered>tfoot>tr>th:first-child,.table-responsive>.table-bordered>thead>tr>td:first-child,.table-responsive>.table-bordered>tbody>tr>td:first-child,.table-responsive>.table-bordered>tfoot>tr>td:first-child{border-left:0}.table-responsive>.table-bordered>thead>tr>th:last-child,.table-responsive>.table-bordered>tbody>tr>th:last-child,.table-responsive>.table-bordered>tfoot>tr>th:last-child,.table-responsive>.table-bordered>thead>tr>td:last-child,.table-responsive>.table-bordered>tbody>tr>td:last-child,.table-responsive>.table-bordered>tfoot>tr>td:last-child{border-right:0}.table-responsive>.table-bordered>thead>tr:last-child>th,.table-responsive>.table-bordered>tbody>tr:last-child>th,.table-responsive>.table-bordered>tfoot>tr:last-child>th,.table-responsive>.table-bordered>thead>tr:last-child>td,.table-responsive>.table-bordered>tbody>tr:last-child>td,.table-responsive>.table-bordered>tfoot>tr:last-child>td{border-bottom:0}}fieldset{padding:0;margin:0;border:0}legend{display:block;width:100%;padding:0;margin-bottom:20px;font-size:21px;line-height:inherit;color:#333;border:0;border-bottom:1px solid #e5e5e5}label{display:inline-block;margin-bottom:5px;font-weight:bold}input[type="search"]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}input[type="radio"],input[type="checkbox"]{margin:4px 0 0;margin-top:1px \9;line-height:normal}input[type="file"]{display:block}select[multiple],select[size]{height:auto}select optgroup{font-family:inherit;font-size:inherit;font-style:inherit}input[type="file"]:focus,input[type="radio"]:focus,input[type="checkbox"]:focus{outline:thin dotted #333;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}input[type="number"]::-webkit-outer-spin-button,input[type="number"]::-webkit-inner-spin-button{height:auto}.form-control:-moz-placeholder{color:#999}.form-control::-moz-placeholder{color:#999}.form-control:-ms-input-placeholder{color:#999}.form-control::-webkit-input-placeholder{color:#999}.form-control{display:block;width:100%;height:34px;padding:6px 12px;font-size:14px;line-height:1.428571429;color:#555;vertical-align:middle;background-color:#fff;border:1px solid #ccc;border-radius:4px;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);-webkit-transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s;transition:border-color ease-in-out .15s,box-shadow ease-in-out .15s}.form-control:focus{border-color:#66afe9;outline:0;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 8px rgba(102,175,233,0.6);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 8px rgba(102,175,233,0.6)}.form-control[disabled],.form-control[readonly],fieldset[disabled] .form-control{cursor:not-allowed;background-color:#eee}textarea.form-control{height:auto}.form-group{margin-bottom:15px}.radio,.checkbox{display:block;min-height:20px;padding-left:20px;margin-top:10px;margin-bottom:10px;vertical-align:middle}.radio label,.checkbox label{display:inline;margin-bottom:0;font-weight:normal;cursor:pointer}.radio input[type="radio"],.radio-inline input[type="radio"],.checkbox input[type="checkbox"],.checkbox-inline input[type="checkbox"]{float:left;margin-left:-20px}.radio+.radio,.checkbox+.checkbox{margin-top:-5px}.radio-inline,.checkbox-inline{display:inline-block;padding-left:20px;margin-bottom:0;font-weight:normal;vertical-align:middle;cursor:pointer}.radio-inline+.radio-inline,.checkbox-inline+.checkbox-inline{margin-top:0;margin-left:10px}input[type="radio"][disabled],input[type="checkbox"][disabled],.radio[disabled],.radio-inline[disabled],.checkbox[disabled],.checkbox-inline[disabled],fieldset[disabled] input[type="radio"],fieldset[disabled] input[type="checkbox"],fieldset[disabled] .radio,fieldset[disabled] .radio-inline,fieldset[disabled] .checkbox,fieldset[disabled] .checkbox-inline{cursor:not-allowed}.input-sm{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.input-sm{height:30px;line-height:30px}textarea.input-sm{height:auto}.input-lg{height:45px;padding:10px 16px;font-size:18px;line-height:1.33;border-radius:6px}select.input-lg{height:45px;line-height:45px}textarea.input-lg{height:auto}.has-warning .help-block,.has-warning .control-label{color:#c09853}.has-warning .form-control{border-color:#c09853;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-warning .form-control:focus{border-color:#a47e3c;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #dbc59e;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #dbc59e}.has-warning .input-group-addon{color:#c09853;background-color:#fcf8e3;border-color:#c09853}.has-error .help-block,.has-error .control-label{color:#b94a48}.has-error .form-control{border-color:#b94a48;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-error .form-control:focus{border-color:#953b39;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #d59392;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #d59392}.has-error .input-group-addon{color:#b94a48;background-color:#f2dede;border-color:#b94a48}.has-success .help-block,.has-success .control-label{color:#468847}.has-success .form-control{border-color:#468847;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-success .form-control:focus{border-color:#356635;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #7aba7b;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #7aba7b}.has-success .input-group-addon{color:#468847;background-color:#dff0d8;border-color:#468847}.form-control-static{padding-top:7px;margin-bottom:0}.help-block{display:block;margin-top:5px;margin-bottom:10px;color:#737373}@media(min-width:768px){.form-inline .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.form-inline .form-control{display:inline-block}.form-inline .radio,.form-inline .checkbox{display:inline-block;padding-left:0;margin-top:0;margin-bottom:0}.form-inline .radio input[type="radio"],.form-inline .checkbox input[type="checkbox"]{float:none;margin-left:0}}.form-horizontal .control-label,.form-horizontal .radio,.form-horizontal .checkbox,.form-horizontal .radio-inline,.form-horizontal .checkbox-inline{padding-top:7px;margin-top:0;margin-bottom:0}.form-horizontal .form-group{margin-right:-15px;margin-left:-15px}.form-horizontal .form-group:before,.form-horizontal .form-group:after{display:table;content:" "}.form-horizontal .form-group:after{clear:both}.form-horizontal .form-group:before,.form-horizontal .form-group:after{display:table;content:" "}.form-horizontal .form-group:after{clear:both}@media(min-width:768px){.form-horizontal .control-label{text-align:right}}.btn{display:inline-block;padding:6px 12px;margin-bottom:0;font-size:14px;font-weight:normal;line-height:1.428571429;text-align:center;white-space:nowrap;vertical-align:middle;cursor:pointer;border:1px solid transparent;border-radius:4px;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;-o-user-select:none;user-select:none}.btn:focus{outline:thin dotted #333;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}.btn:hover,.btn:focus{color:#333;text-decoration:none}.btn:active,.btn.active{background-image:none;outline:0;-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,0.125);box-shadow:inset 0 3px 5px rgba(0,0,0,0.125)}.btn.disabled,.btn[disabled],fieldset[disabled] .btn{pointer-events:none;cursor:not-allowed;opacity:.65;filter:alpha(opacity=65);-webkit-box-shadow:none;box-shadow:none}.btn-default{color:#333;background-color:#fff;border-color:#ccc}.btn-default:hover,.btn-default:focus,.btn-default:active,.btn-default.active,.open .dropdown-toggle.btn-default{color:#333;background-color:#ebebeb;border-color:#adadad}.btn-default:active,.btn-default.active,.open .dropdown-toggle.btn-default{background-image:none}.btn-default.disabled,.btn-default[disabled],fieldset[disabled] .btn-default,.btn-default.disabled:hover,.btn-default[disabled]:hover,fieldset[disabled] .btn-default:hover,.btn-default.disabled:focus,.btn-default[disabled]:focus,fieldset[disabled] .btn-default:focus,.btn-default.disabled:active,.btn-default[disabled]:active,fieldset[disabled] .btn-default:active,.btn-default.disabled.active,.btn-default[disabled].active,fieldset[disabled] .btn-default.active{background-color:#fff;border-color:#ccc}.btn-primary{color:#fff;background-color:#428bca;border-color:#357ebd}.btn-primary:hover,.btn-primary:focus,.btn-primary:active,.btn-primary.active,.open .dropdown-toggle.btn-primary{color:#fff;background-color:#3276b1;border-color:#285e8e}.btn-primary:active,.btn-primary.active,.open .dropdown-toggle.btn-primary{background-image:none}.btn-primary.disabled,.btn-primary[disabled],fieldset[disabled] .btn-primary,.btn-primary.disabled:hover,.btn-primary[disabled]:hover,fieldset[disabled] .btn-primary:hover,.btn-primary.disabled:focus,.btn-primary[disabled]:focus,fieldset[disabled] .btn-primary:focus,.btn-primary.disabled:active,.btn-primary[disabled]:active,fieldset[disabled] .btn-primary:active,.btn-primary.disabled.active,.btn-primary[disabled].active,fieldset[disabled] .btn-primary.active{background-color:#428bca;border-color:#357ebd}.btn-warning{color:#fff;background-color:#f0ad4e;border-color:#eea236}.btn-warning:hover,.btn-warning:focus,.btn-warning:active,.btn-warning.active,.open .dropdown-toggle.btn-warning{color:#fff;background-color:#ed9c28;border-color:#d58512}.btn-warning:active,.btn-warning.active,.open .dropdown-toggle.btn-warning{background-image:none}.btn-warning.disabled,.btn-warning[disabled],fieldset[disabled] .btn-warning,.btn-warning.disabled:hover,.btn-warning[disabled]:hover,fieldset[disabled] .btn-warning:hover,.btn-warning.disabled:focus,.btn-warning[disabled]:focus,fieldset[disabled] .btn-warning:focus,.btn-warning.disabled:active,.btn-warning[disabled]:active,fieldset[disabled] .btn-warning:active,.btn-warning.disabled.active,.btn-warning[disabled].active,fieldset[disabled] .btn-warning.active{background-color:#f0ad4e;border-color:#eea236}.btn-danger{color:#fff;background-color:#d9534f;border-color:#d43f3a}.btn-danger:hover,.btn-danger:focus,.btn-danger:active,.btn-danger.active,.open .dropdown-toggle.btn-danger{color:#fff;background-color:#d2322d;border-color:#ac2925}.btn-danger:active,.btn-danger.active,.open .dropdown-toggle.btn-danger{background-image:none}.btn-danger.disabled,.btn-danger[disabled],fieldset[disabled] .btn-danger,.btn-danger.disabled:hover,.btn-danger[disabled]:hover,fieldset[disabled] .btn-danger:hover,.btn-danger.disabled:focus,.btn-danger[disabled]:focus,fieldset[disabled] .btn-danger:focus,.btn-danger.disabled:active,.btn-danger[disabled]:active,fieldset[disabled] .btn-danger:active,.btn-danger.disabled.active,.btn-danger[disabled].active,fieldset[disabled] .btn-danger.active{background-color:#d9534f;border-color:#d43f3a}.btn-success{color:#fff;background-color:#5cb85c;border-color:#4cae4c}.btn-success:hover,.btn-success:focus,.btn-success:active,.btn-success.active,.open .dropdown-toggle.btn-success{color:#fff;background-color:#47a447;border-color:#398439}.btn-success:active,.btn-success.active,.open .dropdown-toggle.btn-success{background-image:none}.btn-success.disabled,.btn-success[disabled],fieldset[disabled] .btn-success,.btn-success.disabled:hover,.btn-success[disabled]:hover,fieldset[disabled] .btn-success:hover,.btn-success.disabled:focus,.btn-success[disabled]:focus,fieldset[disabled] .btn-success:focus,.btn-success.disabled:active,.btn-success[disabled]:active,fieldset[disabled] .btn-success:active,.btn-success.disabled.active,.btn-success[disabled].active,fieldset[disabled] .btn-success.active{background-color:#5cb85c;border-color:#4cae4c}.btn-info{color:#fff;background-color:#5bc0de;border-color:#46b8da}.btn-info:hover,.btn-info:focus,.btn-info:active,.btn-info.active,.open .dropdown-toggle.btn-info{color:#fff;background-color:#39b3d7;border-color:#269abc}.btn-info:active,.btn-info.active,.open .dropdown-toggle.btn-info{background-image:none}.btn-info.disabled,.btn-info[disabled],fieldset[disabled] .btn-info,.btn-info.disabled:hover,.btn-info[disabled]:hover,fieldset[disabled] .btn-info:hover,.btn-info.disabled:focus,.btn-info[disabled]:focus,fieldset[disabled] .btn-info:focus,.btn-info.disabled:active,.btn-info[disabled]:active,fieldset[disabled] .btn-info:active,.btn-info.disabled.active,.btn-info[disabled].active,fieldset[disabled] .btn-info.active{background-color:#5bc0de;border-color:#46b8da}.btn-link{font-weight:normal;color:#428bca;cursor:pointer;border-radius:0}.btn-link,.btn-link:active,.btn-link[disabled],fieldset[disabled] .btn-link{background-color:transparent;-webkit-box-shadow:none;box-shadow:none}.btn-link,.btn-link:hover,.btn-link:focus,.btn-link:active{border-color:transparent}.btn-link:hover,.btn-link:focus{color:#2a6496;text-decoration:underline;background-color:transparent}.btn-link[disabled]:hover,fieldset[disabled] .btn-link:hover,.btn-link[disabled]:focus,fieldset[disabled] .btn-link:focus{color:#999;text-decoration:none}.btn-lg{padding:10px 16px;font-size:18px;line-height:1.33;border-radius:6px}.btn-sm,.btn-xs{padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}.btn-xs{padding:1px 5px}.btn-block{display:block;width:100%;padding-right:0;padding-left:0}.btn-block+.btn-block{margin-top:5px}input[type="submit"].btn-block,input[type="reset"].btn-block,input[type="button"].btn-block{width:100%}.fade{opacity:0;-webkit-transition:opacity .15s linear;transition:opacity .15s linear}.fade.in{opacity:1}.collapse{display:none}.collapse.in{display:block}.collapsing{position:relative;height:0;overflow:hidden;-webkit-transition:height .35s ease;transition:height .35s ease}@font-face{font-family:'Glyphicons Halflings';src:url('../fonts/glyphicons-halflings-regular.eot');src:url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'),url('../fonts/glyphicons-halflings-regular.woff') format('woff'),url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'),url('../fonts/glyphicons-halflings-regular.svg#glyphicons-halflingsregular') format('svg')}.glyphicon{position:relative;top:1px;display:inline-block;font-family:'Glyphicons Halflings';-webkit-font-smoothing:antialiased;font-style:normal;font-weight:normal;line-height:1}.glyphicon-asterisk:before{content:"\2a"}.glyphicon-plus:before{content:"\2b"}.glyphicon-euro:before{content:"\20ac"}.glyphicon-minus:before{content:"\2212"}.glyphicon-cloud:before{content:"\2601"}.glyphicon-envelope:before{content:"\2709"}.glyphicon-pencil:before{content:"\270f"}.glyphicon-glass:before{content:"\e001"}.glyphicon-music:before{content:"\e002"}.glyphicon-search:before{content:"\e003"}.glyphicon-heart:before{content:"\e005"}.glyphicon-star:before{content:"\e006"}.glyphicon-star-empty:before{content:"\e007"}.glyphicon-user:before{content:"\e008"}.glyphicon-film:before{content:"\e009"}.glyphicon-th-large:before{content:"\e010"}.glyphicon-th:before{content:"\e011"}.glyphicon-th-list:before{content:"\e012"}.glyphicon-ok:before{content:"\e013"}.glyphicon-remove:before{content:"\e014"}.glyphicon-zoom-in:before{content:"\e015"}.glyphicon-zoom-out:before{content:"\e016"}.glyphicon-off:before{content:"\e017"}.glyphicon-signal:before{content:"\e018"}.glyphicon-cog:before{content:"\e019"}.glyphicon-trash:before{content:"\e020"}.glyphicon-home:before{content:"\e021"}.glyphicon-file:before{content:"\e022"}.glyphicon-time:before{content:"\e023"}.glyphicon-road:before{content:"\e024"}.glyphicon-download-alt:before{content:"\e025"}.glyphicon-download:before{content:"\e026"}.glyphicon-upload:before{content:"\e027"}.glyphicon-inbox:before{content:"\e028"}.glyphicon-play-circle:before{content:"\e029"}.glyphicon-repeat:before{content:"\e030"}.glyphicon-refresh:before{content:"\e031"}.glyphicon-list-alt:before{content:"\e032"}.glyphicon-flag:before{content:"\e034"}.glyphicon-headphones:before{content:"\e035"}.glyphicon-volume-off:before{content:"\e036"}.glyphicon-volume-down:before{content:"\e037"}.glyphicon-volume-up:before{content:"\e038"}.glyphicon-qrcode:before{content:"\e039"}.glyphicon-barcode:before{content:"\e040"}.glyphicon-tag:before{content:"\e041"}.glyphicon-tags:before{content:"\e042"}.glyphicon-book:before{content:"\e043"}.glyphicon-print:before{content:"\e045"}.glyphicon-font:before{content:"\e047"}.glyphicon-bold:before{content:"\e048"}.glyphicon-italic:before{content:"\e049"}.glyphicon-text-height:before{content:"\e050"}.glyphicon-text-width:before{content:"\e051"}.glyphicon-align-left:before{content:"\e052"}.glyphicon-align-center:before{content:"\e053"}.glyphicon-align-right:before{content:"\e054"}.glyphicon-align-justify:before{content:"\e055"}.glyphicon-list:before{content:"\e056"}.glyphicon-indent-left:before{content:"\e057"}.glyphicon-indent-right:before{content:"\e058"}.glyphicon-facetime-video:before{content:"\e059"}.glyphicon-picture:before{content:"\e060"}.glyphicon-map-marker:before{content:"\e062"}.glyphicon-adjust:before{content:"\e063"}.glyphicon-tint:before{content:"\e064"}.glyphicon-edit:before{content:"\e065"}.glyphicon-share:before{content:"\e066"}.glyphicon-check:before{content:"\e067"}.glyphicon-move:before{content:"\e068"}.glyphicon-step-backward:before{content:"\e069"}.glyphicon-fast-backward:before{content:"\e070"}.glyphicon-backward:before{content:"\e071"}.glyphicon-play:before{content:"\e072"}.glyphicon-pause:before{content:"\e073"}.glyphicon-stop:before{content:"\e074"}.glyphicon-forward:before{content:"\e075"}.glyphicon-fast-forward:before{content:"\e076"}.glyphicon-step-forward:before{content:"\e077"}.glyphicon-eject:before{content:"\e078"}.glyphicon-chevron-left:before{content:"\e079"}.glyphicon-chevron-right:before{content:"\e080"}.glyphicon-plus-sign:before{content:"\e081"}.glyphicon-minus-sign:before{content:"\e082"}.glyphicon-remove-sign:before{content:"\e083"}.glyphicon-ok-sign:before{content:"\e084"}.glyphicon-question-sign:before{content:"\e085"}.glyphicon-info-sign:before{content:"\e086"}.glyphicon-screenshot:before{content:"\e087"}.glyphicon-remove-circle:before{content:"\e088"}.glyphicon-ok-circle:before{content:"\e089"}.glyphicon-ban-circle:before{content:"\e090"}.glyphicon-arrow-left:before{content:"\e091"}.glyphicon-arrow-right:before{content:"\e092"}.glyphicon-arrow-up:before{content:"\e093"}.glyphicon-arrow-down:before{content:"\e094"}.glyphicon-share-alt:before{content:"\e095"}.glyphicon-resize-full:before{content:"\e096"}.glyphicon-resize-small:before{content:"\e097"}.glyphicon-exclamation-sign:before{content:"\e101"}.glyphicon-gift:before{content:"\e102"}.glyphicon-leaf:before{content:"\e103"}.glyphicon-eye-open:before{content:"\e105"}.glyphicon-eye-close:before{content:"\e106"}.glyphicon-warning-sign:before{content:"\e107"}.glyphicon-plane:before{content:"\e108"}.glyphicon-random:before{content:"\e110"}.glyphicon-comment:before{content:"\e111"}.glyphicon-magnet:before{content:"\e112"}.glyphicon-chevron-up:before{content:"\e113"}.glyphicon-chevron-down:before{content:"\e114"}.glyphicon-retweet:before{content:"\e115"}.glyphicon-shopping-cart:before{content:"\e116"}.glyphicon-folder-close:before{content:"\e117"}.glyphicon-folder-open:before{content:"\e118"}.glyphicon-resize-vertical:before{content:"\e119"}.glyphicon-resize-horizontal:before{content:"\e120"}.glyphicon-hdd:before{content:"\e121"}.glyphicon-bullhorn:before{content:"\e122"}.glyphicon-certificate:before{content:"\e124"}.glyphicon-thumbs-up:before{content:"\e125"}.glyphicon-thumbs-down:before{content:"\e126"}.glyphicon-hand-right:before{content:"\e127"}.glyphicon-hand-left:before{content:"\e128"}.glyphicon-hand-up:before{content:"\e129"}.glyphicon-hand-down:before{content:"\e130"}.glyphicon-circle-arrow-right:before{content:"\e131"}.glyphicon-circle-arrow-left:before{content:"\e132"}.glyphicon-circle-arrow-up:before{content:"\e133"}.glyphicon-circle-arrow-down:before{content:"\e134"}.glyphicon-globe:before{content:"\e135"}.glyphicon-tasks:before{content:"\e137"}.glyphicon-filter:before{content:"\e138"}.glyphicon-fullscreen:before{content:"\e140"}.glyphicon-dashboard:before{content:"\e141"}.glyphicon-heart-empty:before{content:"\e143"}.glyphicon-link:before{content:"\e144"}.glyphicon-phone:before{content:"\e145"}.glyphicon-usd:before{content:"\e148"}.glyphicon-gbp:before{content:"\e149"}.glyphicon-sort:before{content:"\e150"}.glyphicon-sort-by-alphabet:before{content:"\e151"}.glyphicon-sort-by-alphabet-alt:before{content:"\e152"}.glyphicon-sort-by-order:before{content:"\e153"}.glyphicon-sort-by-order-alt:before{content:"\e154"}.glyphicon-sort-by-attributes:before{content:"\e155"}.glyphicon-sort-by-attributes-alt:before{content:"\e156"}.glyphicon-unchecked:before{content:"\e157"}.glyphicon-expand:before{content:"\e158"}.glyphicon-collapse-down:before{content:"\e159"}.glyphicon-collapse-up:before{content:"\e160"}.glyphicon-log-in:before{content:"\e161"}.glyphicon-flash:before{content:"\e162"}.glyphicon-log-out:before{content:"\e163"}.glyphicon-new-window:before{content:"\e164"}.glyphicon-record:before{content:"\e165"}.glyphicon-save:before{content:"\e166"}.glyphicon-open:before{content:"\e167"}.glyphicon-saved:before{content:"\e168"}.glyphicon-import:before{content:"\e169"}.glyphicon-export:before{content:"\e170"}.glyphicon-send:before{content:"\e171"}.glyphicon-floppy-disk:before{content:"\e172"}.glyphicon-floppy-saved:before{content:"\e173"}.glyphicon-floppy-remove:before{content:"\e174"}.glyphicon-floppy-save:before{content:"\e175"}.glyphicon-floppy-open:before{content:"\e176"}.glyphicon-credit-card:before{content:"\e177"}.glyphicon-transfer:before{content:"\e178"}.glyphicon-cutlery:before{content:"\e179"}.glyphicon-header:before{content:"\e180"}.glyphicon-compressed:before{content:"\e181"}.glyphicon-earphone:before{content:"\e182"}.glyphicon-phone-alt:before{content:"\e183"}.glyphicon-tower:before{content:"\e184"}.glyphicon-stats:before{content:"\e185"}.glyphicon-sd-video:before{content:"\e186"}.glyphicon-hd-video:before{content:"\e187"}.glyphicon-subtitles:before{content:"\e188"}.glyphicon-sound-stereo:before{content:"\e189"}.glyphicon-sound-dolby:before{content:"\e190"}.glyphicon-sound-5-1:before{content:"\e191"}.glyphicon-sound-6-1:before{content:"\e192"}.glyphicon-sound-7-1:before{content:"\e193"}.glyphicon-copyright-mark:before{content:"\e194"}.glyphicon-registration-mark:before{content:"\e195"}.glyphicon-cloud-download:before{content:"\e197"}.glyphicon-cloud-upload:before{content:"\e198"}.glyphicon-tree-conifer:before{content:"\e199"}.glyphicon-tree-deciduous:before{content:"\e200"}.glyphicon-briefcase:before{content:"\1f4bc"}.glyphicon-calendar:before{content:"\1f4c5"}.glyphicon-pushpin:before{content:"\1f4cc"}.glyphicon-paperclip:before{content:"\1f4ce"}.glyphicon-camera:before{content:"\1f4f7"}.glyphicon-lock:before{content:"\1f512"}.glyphicon-bell:before{content:"\1f514"}.glyphicon-bookmark:before{content:"\1f516"}.glyphicon-fire:before{content:"\1f525"}.glyphicon-wrench:before{content:"\1f527"}.caret{display:inline-block;width:0;height:0;margin-left:2px;vertical-align:middle;border-top:4px solid #000;border-right:4px solid transparent;border-bottom:0 dotted;border-left:4px solid transparent;content:""}.dropdown{position:relative}.dropdown-toggle:focus{outline:0}.dropdown-menu{position:absolute;top:100%;left:0;z-index:1000;display:none;float:left;min-width:160px;padding:5px 0;margin:2px 0 0;font-size:14px;list-style:none;background-color:#fff;border:1px solid #ccc;border:1px solid rgba(0,0,0,0.15);border-radius:4px;-webkit-box-shadow:0 6px 12px rgba(0,0,0,0.175);box-shadow:0 6px 12px rgba(0,0,0,0.175);background-clip:padding-box}.dropdown-menu.pull-right{right:0;left:auto}.dropdown-menu .divider{height:1px;margin:9px 0;overflow:hidden;background-color:#e5e5e5}.dropdown-menu>li>a{display:block;padding:3px 20px;clear:both;font-weight:normal;line-height:1.428571429;color:#333;white-space:nowrap}.dropdown-menu>li>a:hover,.dropdown-menu>li>a:focus{color:#fff;text-decoration:none;background-color:#428bca}.dropdown-menu>.active>a,.dropdown-menu>.active>a:hover,.dropdown-menu>.active>a:focus{color:#fff;text-decoration:none;background-color:#428bca;outline:0}.dropdown-menu>.disabled>a,.dropdown-menu>.disabled>a:hover,.dropdown-menu>.disabled>a:focus{color:#999}.dropdown-menu>.disabled>a:hover,.dropdown-menu>.disabled>a:focus{text-decoration:none;cursor:not-allowed;background-color:transparent;background-image:none;filter:progid:DXImageTransform.Microsoft.gradient(enabled=false)}.open>.dropdown-menu{display:block}.open>a{outline:0}.dropdown-header{display:block;padding:3px 20px;font-size:12px;line-height:1.428571429;color:#999}.dropdown-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:990}.pull-right>.dropdown-menu{right:0;left:auto}.dropup .caret,.navbar-fixed-bottom .dropdown .caret{border-top:0 dotted;border-bottom:4px solid #000;content:""}.dropup .dropdown-menu,.navbar-fixed-bottom .dropdown .dropdown-menu{top:auto;bottom:100%;margin-bottom:1px}@media(min-width:768px){.navbar-right .dropdown-menu{right:0;left:auto}}.btn-default .caret{border-top-color:#333}.btn-primary .caret,.btn-success .caret,.btn-warning .caret,.btn-danger .caret,.btn-info .caret{border-top-color:#fff}.dropup .btn-default .caret{border-bottom-color:#333}.dropup .btn-primary .caret,.dropup .btn-success .caret,.dropup .btn-warning .caret,.dropup .btn-danger .caret,.dropup .btn-info .caret{border-bottom-color:#fff}.btn-group,.btn-group-vertical{position:relative;display:inline-block;vertical-align:middle}.btn-group>.btn,.btn-group-vertical>.btn{position:relative;float:left}.btn-group>.btn:hover,.btn-group-vertical>.btn:hover,.btn-group>.btn:focus,.btn-group-vertical>.btn:focus,.btn-group>.btn:active,.btn-group-vertical>.btn:active,.btn-group>.btn.active,.btn-group-vertical>.btn.active{z-index:2}.btn-group>.btn:focus,.btn-group-vertical>.btn:focus{outline:0}.btn-group .btn+.btn,.btn-group .btn+.btn-group,.btn-group .btn-group+.btn,.btn-group .btn-group+.btn-group{margin-left:-1px}.btn-toolbar:before,.btn-toolbar:after{display:table;content:" "}.btn-toolbar:after{clear:both}.btn-toolbar:before,.btn-toolbar:after{display:table;content:" "}.btn-toolbar:after{clear:both}.btn-toolbar .btn-group{float:left}.btn-toolbar>.btn+.btn,.btn-toolbar>.btn-group+.btn,.btn-toolbar>.btn+.btn-group,.btn-toolbar>.btn-group+.btn-group{margin-left:5px}.btn-group>.btn:not(:first-child):not(:last-child):not(.dropdown-toggle){border-radius:0}.btn-group>.btn:first-child{margin-left:0}.btn-group>.btn:first-child:not(:last-child):not(.dropdown-toggle){border-top-right-radius:0;border-bottom-right-radius:0}.btn-group>.btn:last-child:not(:first-child),.btn-group>.dropdown-toggle:not(:first-child){border-bottom-left-radius:0;border-top-left-radius:0}.btn-group>.btn-group{float:left}.btn-group>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group>.btn-group:first-child>.btn:last-child,.btn-group>.btn-group:first-child>.dropdown-toggle{border-top-right-radius:0;border-bottom-right-radius:0}.btn-group>.btn-group:last-child>.btn:first-child{border-bottom-left-radius:0;border-top-left-radius:0}.btn-group .dropdown-toggle:active,.btn-group.open .dropdown-toggle{outline:0}.btn-group-xs>.btn{padding:5px 10px;padding:1px 5px;font-size:12px;line-height:1.5;border-radius:3px}.btn-group-sm>.btn{padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}.btn-group-lg>.btn{padding:10px 16px;font-size:18px;line-height:1.33;border-radius:6px}.btn-group>.btn+.dropdown-toggle{padding-right:8px;padding-left:8px}.btn-group>.btn-lg+.dropdown-toggle{padding-right:12px;padding-left:12px}.btn-group.open .dropdown-toggle{-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,0.125);box-shadow:inset 0 3px 5px rgba(0,0,0,0.125)}.btn .caret{margin-left:0}.btn-lg .caret{border-width:5px 5px 0;border-bottom-width:0}.dropup .btn-lg .caret{border-width:0 5px 5px}.btn-group-vertical>.btn,.btn-group-vertical>.btn-group{display:block;float:none;width:100%;max-width:100%}.btn-group-vertical>.btn-group:before,.btn-group-vertical>.btn-group:after{display:table;content:" "}.btn-group-vertical>.btn-group:after{clear:both}.btn-group-vertical>.btn-group:before,.btn-group-vertical>.btn-group:after{display:table;content:" "}.btn-group-vertical>.btn-group:after{clear:both}.btn-group-vertical>.btn-group>.btn{float:none}.btn-group-vertical>.btn+.btn,.btn-group-vertical>.btn+.btn-group,.btn-group-vertical>.btn-group+.btn,.btn-group-vertical>.btn-group+.btn-group{margin-top:-1px;margin-left:0}.btn-group-vertical>.btn:not(:first-child):not(:last-child){border-radius:0}.btn-group-vertical>.btn:first-child:not(:last-child){border-top-right-radius:4px;border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn:last-child:not(:first-child){border-top-right-radius:0;border-bottom-left-radius:4px;border-top-left-radius:0}.btn-group-vertical>.btn-group:not(:first-child):not(:last-child)>.btn{border-radius:0}.btn-group-vertical>.btn-group:first-child>.btn:last-child,.btn-group-vertical>.btn-group:first-child>.dropdown-toggle{border-bottom-right-radius:0;border-bottom-left-radius:0}.btn-group-vertical>.btn-group:last-child>.btn:first-child{border-top-right-radius:0;border-top-left-radius:0}.btn-group-justified{display:table;width:100%;border-collapse:separate;table-layout:fixed}.btn-group-justified .btn{display:table-cell;float:none;width:1%}[data-toggle="buttons"]>.btn>input[type="radio"],[data-toggle="buttons"]>.btn>input[type="checkbox"]{display:none}.input-group{position:relative;display:table;border-collapse:separate}.input-group.col{float:none;padding-right:0;padding-left:0}.input-group .form-control{width:100%;margin-bottom:0}.input-group-lg>.form-control,.input-group-lg>.input-group-addon,.input-group-lg>.input-group-btn>.btn{height:45px;padding:10px 16px;font-size:18px;line-height:1.33;border-radius:6px}select.input-group-lg>.form-control,select.input-group-lg>.input-group-addon,select.input-group-lg>.input-group-btn>.btn{height:45px;line-height:45px}textarea.input-group-lg>.form-control,textarea.input-group-lg>.input-group-addon,textarea.input-group-lg>.input-group-btn>.btn{height:auto}.input-group-sm>.form-control,.input-group-sm>.input-group-addon,.input-group-sm>.input-group-btn>.btn{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.input-group-sm>.form-control,select.input-group-sm>.input-group-addon,select.input-group-sm>.input-group-btn>.btn{height:30px;line-height:30px}textarea.input-group-sm>.form-control,textarea.input-group-sm>.input-group-addon,textarea.input-group-sm>.input-group-btn>.btn{height:auto}.input-group-addon,.input-group-btn,.input-group .form-control{display:table-cell}.input-group-addon:not(:first-child):not(:last-child),.input-group-btn:not(:first-child):not(:last-child),.input-group .form-control:not(:first-child):not(:last-child){border-radius:0}.input-group-addon,.input-group-btn{width:1%;white-space:nowrap;vertical-align:middle}.input-group-addon{padding:6px 12px;font-size:14px;font-weight:normal;line-height:1;text-align:center;background-color:#eee;border:1px solid #ccc;border-radius:4px}.input-group-addon.input-sm{padding:5px 10px;font-size:12px;border-radius:3px}.input-group-addon.input-lg{padding:10px 16px;font-size:18px;border-radius:6px}.input-group-addon input[type="radio"],.input-group-addon input[type="checkbox"]{margin-top:0}.input-group .form-control:first-child,.input-group-addon:first-child,.input-group-btn:first-child>.btn,.input-group-btn:first-child>.dropdown-toggle,.input-group-btn:last-child>.btn:not(:last-child):not(.dropdown-toggle){border-top-right-radius:0;border-bottom-right-radius:0}.input-group-addon:first-child{border-right:0}.input-group .form-control:last-child,.input-group-addon:last-child,.input-group-btn:last-child>.btn,.input-group-btn:last-child>.dropdown-toggle,.input-group-btn:first-child>.btn:not(:first-child){border-bottom-left-radius:0;border-top-left-radius:0}.input-group-addon:last-child{border-left:0}.input-group-btn{position:relative;white-space:nowrap}.input-group-btn>.btn{position:relative}.input-group-btn>.btn+.btn{margin-left:-4px}.input-group-btn>.btn:hover,.input-group-btn>.btn:active{z-index:2}.nav{padding-left:0;margin-bottom:0;list-style:none}.nav:before,.nav:after{display:table;content:" "}.nav:after{clear:both}.nav:before,.nav:after{display:table;content:" "}.nav:after{clear:both}.nav>li{position:relative;display:block}.nav>li>a{position:relative;display:block;padding:10px 15px}.nav>li>a:hover,.nav>li>a:focus{text-decoration:none;background-color:#eee}.nav>li.disabled>a{color:#999}.nav>li.disabled>a:hover,.nav>li.disabled>a:focus{color:#999;text-decoration:none;cursor:not-allowed;background-color:transparent}.nav .open>a,.nav .open>a:hover,.nav .open>a:focus{background-color:#eee;border-color:#428bca}.nav .nav-divider{height:1px;margin:9px 0;overflow:hidden;background-color:#e5e5e5}.nav>li>a>img{max-width:none}.nav-tabs{border-bottom:1px solid #ddd}.nav-tabs>li{float:left;margin-bottom:-1px}.nav-tabs>li>a{margin-right:2px;line-height:1.428571429;border:1px solid transparent;border-radius:4px 4px 0 0}.nav-tabs>li>a:hover{border-color:#eee #eee #ddd}.nav-tabs>li.active>a,.nav-tabs>li.active>a:hover,.nav-tabs>li.active>a:focus{color:#555;cursor:default;background-color:#fff;border:1px solid #ddd;border-bottom-color:transparent}.nav-tabs.nav-justified{width:100%;border-bottom:0}.nav-tabs.nav-justified>li{float:none}.nav-tabs.nav-justified>li>a{text-align:center}@media(min-width:768px){.nav-tabs.nav-justified>li{display:table-cell;width:1%}}.nav-tabs.nav-justified>li>a{margin-right:0;border-bottom:1px solid #ddd}.nav-tabs.nav-justified>.active>a{border-bottom-color:#fff}.nav-pills>li{float:left}.nav-pills>li>a{border-radius:5px}.nav-pills>li+li{margin-left:2px}.nav-pills>li.active>a,.nav-pills>li.active>a:hover,.nav-pills>li.active>a:focus{color:#fff;background-color:#428bca}.nav-stacked>li{float:none}.nav-stacked>li+li{margin-top:2px;margin-left:0}.nav-justified{width:100%}.nav-justified>li{float:none}.nav-justified>li>a{text-align:center}@media(min-width:768px){.nav-justified>li{display:table-cell;width:1%}}.nav-tabs-justified{border-bottom:0}.nav-tabs-justified>li>a{margin-right:0;border-bottom:1px solid #ddd}.nav-tabs-justified>.active>a{border-bottom-color:#fff}.tabbable:before,.tabbable:after{display:table;content:" "}.tabbable:after{clear:both}.tabbable:before,.tabbable:after{display:table;content:" "}.tabbable:after{clear:both}.tab-content>.tab-pane,.pill-content>.pill-pane{display:none}.tab-content>.active,.pill-content>.active{display:block}.nav .caret{border-top-color:#428bca;border-bottom-color:#428bca}.nav a:hover .caret{border-top-color:#2a6496;border-bottom-color:#2a6496}.nav-tabs .dropdown-menu{margin-top:-1px;border-top-right-radius:0;border-top-left-radius:0}.navbar{position:relative;z-index:1000;min-height:50px;margin-bottom:20px;border:1px solid transparent}.navbar:before,.navbar:after{display:table;content:" "}.navbar:after{clear:both}.navbar:before,.navbar:after{display:table;content:" "}.navbar:after{clear:both}@media(min-width:768px){.navbar{border-radius:4px}}.navbar-header:before,.navbar-header:after{display:table;content:" "}.navbar-header:after{clear:both}.navbar-header:before,.navbar-header:after{display:table;content:" "}.navbar-header:after{clear:both}@media(min-width:768px){.navbar-header{float:left}}.navbar-collapse{max-height:340px;padding-right:15px;padding-left:15px;overflow-x:visible;border-top:1px solid transparent;box-shadow:inset 0 1px 0 rgba(255,255,255,0.1);-webkit-overflow-scrolling:touch}.navbar-collapse:before,.navbar-collapse:after{display:table;content:" "}.navbar-collapse:after{clear:both}.navbar-collapse:before,.navbar-collapse:after{display:table;content:" "}.navbar-collapse:after{clear:both}.navbar-collapse.in{overflow-y:auto}@media(min-width:768px){.navbar-collapse{width:auto;border-top:0;box-shadow:none}.navbar-collapse.collapse{display:block!important;height:auto!important;padding-bottom:0;overflow:visible!important}.navbar-collapse.in{overflow-y:visible}.navbar-collapse .navbar-nav.navbar-left:first-child{margin-left:-15px}.navbar-collapse .navbar-nav.navbar-right:last-child{margin-right:-15px}.navbar-collapse .navbar-text:last-child{margin-right:0}}.container>.navbar-header,.container>.navbar-collapse{margin-right:-15px;margin-left:-15px}@media(min-width:768px){.container>.navbar-header,.container>.navbar-collapse{margin-right:0;margin-left:0}}.navbar-static-top{border-width:0 0 1px}@media(min-width:768px){.navbar-static-top{border-radius:0}}.navbar-fixed-top,.navbar-fixed-bottom{position:fixed;right:0;left:0;border-width:0 0 1px}@media(min-width:768px){.navbar-fixed-top,.navbar-fixed-bottom{border-radius:0}}.navbar-fixed-top{top:0;z-index:1030}.navbar-fixed-bottom{bottom:0;margin-bottom:0}.navbar-brand{float:left;padding:15px 15px;font-size:18px;line-height:20px}.navbar-brand:hover,.navbar-brand:focus{text-decoration:none}@media(min-width:768px){.navbar>.container .navbar-brand{margin-left:-15px}}.navbar-toggle{position:relative;float:right;padding:9px 10px;margin-top:8px;margin-right:15px;margin-bottom:8px;background-color:transparent;border:1px solid transparent;border-radius:4px}.navbar-toggle .icon-bar{display:block;width:22px;height:2px;border-radius:1px}.navbar-toggle .icon-bar+.icon-bar{margin-top:4px}@media(min-width:768px){.navbar-toggle{display:none}}.navbar-nav{margin:7.5px -15px}.navbar-nav>li>a{padding-top:10px;padding-bottom:10px;line-height:20px}@media(max-width:767px){.navbar-nav .open .dropdown-menu{position:static;float:none;width:auto;margin-top:0;background-color:transparent;border:0;box-shadow:none}.navbar-nav .open .dropdown-menu>li>a,.navbar-nav .open .dropdown-menu .dropdown-header{padding:5px 15px 5px 25px}.navbar-nav .open .dropdown-menu>li>a{line-height:20px}.navbar-nav .open .dropdown-menu>li>a:hover,.navbar-nav .open .dropdown-menu>li>a:focus{background-image:none}}@media(min-width:768px){.navbar-nav{float:left;margin:0}.navbar-nav>li{float:left}.navbar-nav>li>a{padding-top:15px;padding-bottom:15px}}@media(min-width:768px){.navbar-left{float:left!important}.navbar-right{float:right!important}}.navbar-form{padding:10px 15px;margin-top:8px;margin-right:-15px;margin-bottom:8px;margin-left:-15px;border-top:1px solid transparent;border-bottom:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1);box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1)}@media(min-width:768px){.navbar-form .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.navbar-form .form-control{display:inline-block}.navbar-form .radio,.navbar-form .checkbox{display:inline-block;padding-left:0;margin-top:0;margin-bottom:0}.navbar-form .radio input[type="radio"],.navbar-form .checkbox input[type="checkbox"]{float:none;margin-left:0}}@media(max-width:767px){.navbar-form .form-group{margin-bottom:5px}}@media(min-width:768px){.navbar-form{width:auto;padding-top:0;padding-bottom:0;margin-right:0;margin-left:0;border:0;-webkit-box-shadow:none;box-shadow:none}}.navbar-nav>li>.dropdown-menu{margin-top:0;border-top-right-radius:0;border-top-left-radius:0}.navbar-fixed-bottom .navbar-nav>li>.dropdown-menu{border-bottom-right-radius:0;border-bottom-left-radius:0}.navbar-nav.pull-right>li>.dropdown-menu,.navbar-nav>li>.dropdown-menu.pull-right{right:0;left:auto}.navbar-btn{margin-top:8px;margin-bottom:8px}.navbar-text{float:left;margin-top:15px;margin-bottom:15px}@media(min-width:768px){.navbar-text{margin-right:15px;margin-left:15px}}.navbar-default{background-color:#f8f8f8;border-color:#e7e7e7}.navbar-default .navbar-brand{color:#777}.navbar-default .navbar-brand:hover,.navbar-default .navbar-brand:focus{color:#5e5e5e;background-color:transparent}.navbar-default .navbar-text{color:#777}.navbar-default .navbar-nav>li>a{color:#777}.navbar-default .navbar-nav>li>a:hover,.navbar-default .navbar-nav>li>a:focus{color:#333;background-color:transparent}.navbar-default .navbar-nav>.active>a,.navbar-default .navbar-nav>.active>a:hover,.navbar-default .navbar-nav>.active>a:focus{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav>.disabled>a,.navbar-default .navbar-nav>.disabled>a:hover,.navbar-default .navbar-nav>.disabled>a:focus{color:#ccc;background-color:transparent}.navbar-default .navbar-toggle{border-color:#ddd}.navbar-default .navbar-toggle:hover,.navbar-default .navbar-toggle:focus{background-color:#ddd}.navbar-default .navbar-toggle .icon-bar{background-color:#ccc}.navbar-default .navbar-collapse,.navbar-default .navbar-form{border-color:#e6e6e6}.navbar-default .navbar-nav>.dropdown>a:hover .caret,.navbar-default .navbar-nav>.dropdown>a:focus .caret{border-top-color:#333;border-bottom-color:#333}.navbar-default .navbar-nav>.open>a,.navbar-default .navbar-nav>.open>a:hover,.navbar-default .navbar-nav>.open>a:focus{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav>.open>a .caret,.navbar-default .navbar-nav>.open>a:hover .caret,.navbar-default .navbar-nav>.open>a:focus .caret{border-top-color:#555;border-bottom-color:#555}.navbar-default .navbar-nav>.dropdown>a .caret{border-top-color:#777;border-bottom-color:#777}@media(max-width:767px){.navbar-default .navbar-nav .open .dropdown-menu>li>a{color:#777}.navbar-default .navbar-nav .open .dropdown-menu>li>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>li>a:focus{color:#333;background-color:transparent}.navbar-default .navbar-nav .open .dropdown-menu>.active>a,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:focus{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:focus{color:#ccc;background-color:transparent}}.navbar-default .navbar-link{color:#777}.navbar-default .navbar-link:hover{color:#333}.navbar-inverse{background-color:#222;border-color:#080808}.navbar-inverse .navbar-brand{color:#999}.navbar-inverse .navbar-brand:hover,.navbar-inverse .navbar-brand:focus{color:#fff;background-color:transparent}.navbar-inverse .navbar-text{color:#999}.navbar-inverse .navbar-nav>li>a{color:#999}.navbar-inverse .navbar-nav>li>a:hover,.navbar-inverse .navbar-nav>li>a:focus{color:#fff;background-color:transparent}.navbar-inverse .navbar-nav>.active>a,.navbar-inverse .navbar-nav>.active>a:hover,.navbar-inverse .navbar-nav>.active>a:focus{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav>.disabled>a,.navbar-inverse .navbar-nav>.disabled>a:hover,.navbar-inverse .navbar-nav>.disabled>a:focus{color:#444;background-color:transparent}.navbar-inverse .navbar-toggle{border-color:#333}.navbar-inverse .navbar-toggle:hover,.navbar-inverse .navbar-toggle:focus{background-color:#333}.navbar-inverse .navbar-toggle .icon-bar{background-color:#fff}.navbar-inverse .navbar-collapse,.navbar-inverse .navbar-form{border-color:#101010}.navbar-inverse .navbar-nav>.open>a,.navbar-inverse .navbar-nav>.open>a:hover,.navbar-inverse .navbar-nav>.open>a:focus{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav>.dropdown>a:hover .caret{border-top-color:#fff;border-bottom-color:#fff}.navbar-inverse .navbar-nav>.dropdown>a .caret{border-top-color:#999;border-bottom-color:#999}.navbar-inverse .navbar-nav>.open>a .caret,.navbar-inverse .navbar-nav>.open>a:hover .caret,.navbar-inverse .navbar-nav>.open>a:focus .caret{border-top-color:#fff;border-bottom-color:#fff}@media(max-width:767px){.navbar-inverse .navbar-nav .open .dropdown-menu>.dropdown-header{border-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a{color:#999}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:focus{color:#fff;background-color:transparent}.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:focus{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:focus{color:#444;background-color:transparent}}.navbar-inverse .navbar-link{color:#999}.navbar-inverse .navbar-link:hover{color:#fff}.breadcrumb{padding:8px 15px;margin-bottom:20px;list-style:none;background-color:#f5f5f5;border-radius:4px}.breadcrumb>li{display:inline-block}.breadcrumb>li+li:before{padding:0 5px;color:#ccc;content:"/\00a0"}.breadcrumb>.active{color:#999}.pagination{display:inline-block;padding-left:0;margin:20px 0;border-radius:4px}.pagination>li{display:inline}.pagination>li>a,.pagination>li>span{position:relative;float:left;padding:6px 12px;margin-left:-1px;line-height:1.428571429;text-decoration:none;background-color:#fff;border:1px solid #ddd}.pagination>li:first-child>a,.pagination>li:first-child>span{margin-left:0;border-bottom-left-radius:4px;border-top-left-radius:4px}.pagination>li:last-child>a,.pagination>li:last-child>span{border-top-right-radius:4px;border-bottom-right-radius:4px}.pagination>li>a:hover,.pagination>li>span:hover,.pagination>li>a:focus,.pagination>li>span:focus{background-color:#eee}.pagination>.active>a,.pagination>.active>span,.pagination>.active>a:hover,.pagination>.active>span:hover,.pagination>.active>a:focus,.pagination>.active>span:focus{z-index:2;color:#fff;cursor:default;background-color:#428bca;border-color:#428bca}.pagination>.disabled>span,.pagination>.disabled>a,.pagination>.disabled>a:hover,.pagination>.disabled>a:focus{color:#999;cursor:not-allowed;background-color:#fff;border-color:#ddd}.pagination-lg>li>a,.pagination-lg>li>span{padding:10px 16px;font-size:18px}.pagination-lg>li:first-child>a,.pagination-lg>li:first-child>span{border-bottom-left-radius:6px;border-top-left-radius:6px}.pagination-lg>li:last-child>a,.pagination-lg>li:last-child>span{border-top-right-radius:6px;border-bottom-right-radius:6px}.pagination-sm>li>a,.pagination-sm>li>span{padding:5px 10px;font-size:12px}.pagination-sm>li:first-child>a,.pagination-sm>li:first-child>span{border-bottom-left-radius:3px;border-top-left-radius:3px}.pagination-sm>li:last-child>a,.pagination-sm>li:last-child>span{border-top-right-radius:3px;border-bottom-right-radius:3px}.pager{padding-left:0;margin:20px 0;text-align:center;list-style:none}.pager:before,.pager:after{display:table;content:" "}.pager:after{clear:both}.pager:before,.pager:after{display:table;content:" "}.pager:after{clear:both}.pager li{display:inline}.pager li>a,.pager li>span{display:inline-block;padding:5px 14px;background-color:#fff;border:1px solid #ddd;border-radius:15px}.pager li>a:hover,.pager li>a:focus{text-decoration:none;background-color:#eee}.pager .next>a,.pager .next>span{float:right}.pager .previous>a,.pager .previous>span{float:left}.pager .disabled>a,.pager .disabled>a:hover,.pager .disabled>a:focus,.pager .disabled>span{color:#999;cursor:not-allowed;background-color:#fff}.label{display:inline;padding:.2em .6em .3em;font-size:75%;font-weight:bold;line-height:1;color:#fff;text-align:center;white-space:nowrap;vertical-align:baseline;border-radius:.25em}.label[href]:hover,.label[href]:focus{color:#fff;text-decoration:none;cursor:pointer}.label:empty{display:none}.label-default{background-color:#999}.label-default[href]:hover,.label-default[href]:focus{background-color:#808080}.label-primary{background-color:#428bca}.label-primary[href]:hover,.label-primary[href]:focus{background-color:#3071a9}.label-success{background-color:#5cb85c}.label-success[href]:hover,.label-success[href]:focus{background-color:#449d44}.label-info{background-color:#5bc0de}.label-info[href]:hover,.label-info[href]:focus{background-color:#31b0d5}.label-warning{background-color:#f0ad4e}.label-warning[href]:hover,.label-warning[href]:focus{background-color:#ec971f}.label-danger{background-color:#d9534f}.label-danger[href]:hover,.label-danger[href]:focus{background-color:#c9302c}.badge{display:inline-block;min-width:10px;padding:3px 7px;font-size:12px;font-weight:bold;line-height:1;color:#fff;text-align:center;white-space:nowrap;vertical-align:baseline;background-color:#999;border-radius:10px}.badge:empty{display:none}a.badge:hover,a.badge:focus{color:#fff;text-decoration:none;cursor:pointer}.btn .badge{position:relative;top:-1px}a.list-group-item.active>.badge,.nav-pills>.active>a>.badge{color:#428bca;background-color:#fff}.nav-pills>li>a>.badge{margin-left:3px}.jumbotron{padding:30px;margin-bottom:30px;font-size:21px;font-weight:200;line-height:2.1428571435;color:inherit;background-color:#eee}.jumbotron h1{line-height:1;color:inherit}.jumbotron p{line-height:1.4}.container .jumbotron{border-radius:6px}@media screen and (min-width:768px){.jumbotron{padding-top:48px;padding-bottom:48px}.container .jumbotron{padding-right:60px;padding-left:60px}.jumbotron h1{font-size:63px}}.thumbnail{display:inline-block;display:block;height:auto;max-width:100%;padding:4px;line-height:1.428571429;background-color:#fff;border:1px solid #ddd;border-radius:4px;-webkit-transition:all .2s ease-in-out;transition:all .2s ease-in-out}.thumbnail>img{display:block;height:auto;max-width:100%}a.thumbnail:hover,a.thumbnail:focus{border-color:#428bca}.thumbnail>img{margin-right:auto;margin-left:auto}.thumbnail .caption{padding:9px;color:#333}.alert{padding:15px;margin-bottom:20px;border:1px solid transparent;border-radius:4px}.alert h4{margin-top:0;color:inherit}.alert .alert-link{font-weight:bold}.alert>p,.alert>ul{margin-bottom:0}.alert>p+p{margin-top:5px}.alert-dismissable{padding-right:35px}.alert-dismissable .close{position:relative;top:-2px;right:-21px;color:inherit}.alert-success{color:#468847;background-color:#dff0d8;border-color:#d6e9c6}.alert-success hr{border-top-color:#c9e2b3}.alert-success .alert-link{color:#356635}.alert-info{color:#3a87ad;background-color:#d9edf7;border-color:#bce8f1}.alert-info hr{border-top-color:#a6e1ec}.alert-info .alert-link{color:#2d6987}.alert-warning{color:#c09853;background-color:#fcf8e3;border-color:#fbeed5}.alert-warning hr{border-top-color:#f8e5be}.alert-warning .alert-link{color:#a47e3c}.alert-danger{color:#b94a48;background-color:#f2dede;border-color:#eed3d7}.alert-danger hr{border-top-color:#e6c1c7}.alert-danger .alert-link{color:#953b39}@-webkit-keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}@-moz-keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}@-o-keyframes progress-bar-stripes{from{background-position:0 0}to{background-position:40px 0}}@keyframes progress-bar-stripes{from{background-position:40px 0}to{background-position:0 0}}.progress{height:20px;margin-bottom:20px;overflow:hidden;background-color:#f5f5f5;border-radius:4px;-webkit-box-shadow:inset 0 1px 2px rgba(0,0,0,0.1);box-shadow:inset 0 1px 2px rgba(0,0,0,0.1)}.progress-bar{float:left;width:0;height:100%;font-size:12px;color:#fff;text-align:center;background-color:#428bca;-webkit-box-shadow:inset 0 -1px 0 rgba(0,0,0,0.15);box-shadow:inset 0 -1px 0 rgba(0,0,0,0.15);-webkit-transition:width .6s ease;transition:width .6s ease}.progress-striped .progress-bar{background-image:-webkit-gradient(linear,0 100%,100% 0,color-stop(0.25,rgba(255,255,255,0.15)),color-stop(0.25,transparent),color-stop(0.5,transparent),color-stop(0.5,rgba(255,255,255,0.15)),color-stop(0.75,rgba(255,255,255,0.15)),color-stop(0.75,transparent),to(transparent));background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:-moz-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-size:40px 40px}.progress.active .progress-bar{-webkit-animation:progress-bar-stripes 2s linear infinite;-moz-animation:progress-bar-stripes 2s linear infinite;-ms-animation:progress-bar-stripes 2s linear infinite;-o-animation:progress-bar-stripes 2s linear infinite;animation:progress-bar-stripes 2s linear infinite}.progress-bar-success{background-color:#5cb85c}.progress-striped .progress-bar-success{background-image:-webkit-gradient(linear,0 100%,100% 0,color-stop(0.25,rgba(255,255,255,0.15)),color-stop(0.25,transparent),color-stop(0.5,transparent),color-stop(0.5,rgba(255,255,255,0.15)),color-stop(0.75,rgba(255,255,255,0.15)),color-stop(0.75,transparent),to(transparent));background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:-moz-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent)}.progress-bar-info{background-color:#5bc0de}.progress-striped .progress-bar-info{background-image:-webkit-gradient(linear,0 100%,100% 0,color-stop(0.25,rgba(255,255,255,0.15)),color-stop(0.25,transparent),color-stop(0.5,transparent),color-stop(0.5,rgba(255,255,255,0.15)),color-stop(0.75,rgba(255,255,255,0.15)),color-stop(0.75,transparent),to(transparent));background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:-moz-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent)}.progress-bar-warning{background-color:#f0ad4e}.progress-striped .progress-bar-warning{background-image:-webkit-gradient(linear,0 100%,100% 0,color-stop(0.25,rgba(255,255,255,0.15)),color-stop(0.25,transparent),color-stop(0.5,transparent),color-stop(0.5,rgba(255,255,255,0.15)),color-stop(0.75,rgba(255,255,255,0.15)),color-stop(0.75,transparent),to(transparent));background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:-moz-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent)}.progress-bar-danger{background-color:#d9534f}.progress-striped .progress-bar-danger{background-image:-webkit-gradient(linear,0 100%,100% 0,color-stop(0.25,rgba(255,255,255,0.15)),color-stop(0.25,transparent),color-stop(0.5,transparent),color-stop(0.5,rgba(255,255,255,0.15)),color-stop(0.75,rgba(255,255,255,0.15)),color-stop(0.75,transparent),to(transparent));background-image:-webkit-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:-moz-linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent);background-image:linear-gradient(45deg,rgba(255,255,255,0.15) 25%,transparent 25%,transparent 50%,rgba(255,255,255,0.15) 50%,rgba(255,255,255,0.15) 75%,transparent 75%,transparent)}.media,.media-body{overflow:hidden;zoom:1}.media,.media .media{margin-top:15px}.media:first-child{margin-top:0}.media-object{display:block}.media-heading{margin:0 0 5px}.media>.pull-left{margin-right:10px}.media>.pull-right{margin-left:10px}.media-list{padding-left:0;list-style:none}.list-group{padding-left:0;margin-bottom:20px}.list-group-item{position:relative;display:block;padding:10px 15px;margin-bottom:-1px;background-color:#fff;border:1px solid #ddd}.list-group-item:first-child{border-top-right-radius:4px;border-top-left-radius:4px}.list-group-item:last-child{margin-bottom:0;border-bottom-right-radius:4px;border-bottom-left-radius:4px}.list-group-item>.badge{float:right}.list-group-item>.badge+.badge{margin-right:5px}a.list-group-item{color:#555}a.list-group-item .list-group-item-heading{color:#333}a.list-group-item:hover,a.list-group-item:focus{text-decoration:none;background-color:#f5f5f5}.list-group-item.active,.list-group-item.active:hover,.list-group-item.active:focus{z-index:2;color:#fff;background-color:#428bca;border-color:#428bca}.list-group-item.active .list-group-item-heading,.list-group-item.active:hover .list-group-item-heading,.list-group-item.active:focus .list-group-item-heading{color:inherit}.list-group-item.active .list-group-item-text,.list-group-item.active:hover .list-group-item-text,.list-group-item.active:focus .list-group-item-text{color:#e1edf7}.list-group-item-heading{margin-top:0;margin-bottom:5px}.list-group-item-text{margin-bottom:0;line-height:1.3}.panel{margin-bottom:20px;background-color:#fff;border:1px solid transparent;border-radius:4px;-webkit-box-shadow:0 1px 1px rgba(0,0,0,0.05);box-shadow:0 1px 1px rgba(0,0,0,0.05)}.panel-body{padding:15px}.panel-body:before,.panel-body:after{display:table;content:" "}.panel-body:after{clear:both}.panel-body:before,.panel-body:after{display:table;content:" "}.panel-body:after{clear:both}.panel>.list-group{margin-bottom:0}.panel>.list-group .list-group-item{border-width:1px 0}.panel>.list-group .list-group-item:first-child{border-top-right-radius:0;border-top-left-radius:0}.panel>.list-group .list-group-item:last-child{border-bottom:0}.panel-heading+.list-group .list-group-item:first-child{border-top-width:0}.panel>.table{margin-bottom:0}.panel>.panel-body+.table{border-top:1px solid #ddd}.panel-heading{padding:10px 15px;border-bottom:1px solid transparent;border-top-right-radius:3px;border-top-left-radius:3px}.panel-title{margin-top:0;margin-bottom:0;font-size:16px}.panel-title>a{color:inherit}.panel-footer{padding:10px 15px;background-color:#f5f5f5;border-top:1px solid #ddd;border-bottom-right-radius:3px;border-bottom-left-radius:3px}.panel-group .panel{margin-bottom:0;overflow:hidden;border-radius:4px}.panel-group .panel+.panel{margin-top:5px}.panel-group .panel-heading{border-bottom:0}.panel-group .panel-heading+.panel-collapse .panel-body{border-top:1px solid #ddd}.panel-group .panel-footer{border-top:0}.panel-group .panel-footer+.panel-collapse .panel-body{border-bottom:1px solid #ddd}.panel-default{border-color:#ddd}.panel-default>.panel-heading{color:#333;background-color:#f5f5f5;border-color:#ddd}.panel-default>.panel-heading+.panel-collapse .panel-body{border-top-color:#ddd}.panel-default>.panel-footer+.panel-collapse .panel-body{border-bottom-color:#ddd}.panel-primary{border-color:#428bca}.panel-primary>.panel-heading{color:#fff;background-color:#428bca;border-color:#428bca}.panel-primary>.panel-heading+.panel-collapse .panel-body{border-top-color:#428bca}.panel-primary>.panel-footer+.panel-collapse .panel-body{border-bottom-color:#428bca}.panel-success{border-color:#d6e9c6}.panel-success>.panel-heading{color:#468847;background-color:#dff0d8;border-color:#d6e9c6}.panel-success>.panel-heading+.panel-collapse .panel-body{border-top-color:#d6e9c6}.panel-success>.panel-footer+.panel-collapse .panel-body{border-bottom-color:#d6e9c6}.panel-warning{border-color:#fbeed5}.panel-warning>.panel-heading{color:#c09853;background-color:#fcf8e3;border-color:#fbeed5}.panel-warning>.panel-heading+.panel-collapse .panel-body{border-top-color:#fbeed5}.panel-warning>.panel-footer+.panel-collapse .panel-body{border-bottom-color:#fbeed5}.panel-danger{border-color:#eed3d7}.panel-danger>.panel-heading{color:#b94a48;background-color:#f2dede;border-color:#eed3d7}.panel-danger>.panel-heading+.panel-collapse .panel-body{border-top-color:#eed3d7}.panel-danger>.panel-footer+.panel-collapse .panel-body{border-bottom-color:#eed3d7}.panel-info{border-color:#bce8f1}.panel-info>.panel-heading{color:#3a87ad;background-color:#d9edf7;border-color:#bce8f1}.panel-info>.panel-heading+.panel-collapse .panel-body{border-top-color:#bce8f1}.panel-info>.panel-footer+.panel-collapse .panel-body{border-bottom-color:#bce8f1}.well{min-height:20px;padding:19px;margin-bottom:20px;background-color:#f5f5f5;border:1px solid #e3e3e3;border-radius:4px;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.05);box-shadow:inset 0 1px 1px rgba(0,0,0,0.05)}.well blockquote{border-color:#ddd;border-color:rgba(0,0,0,0.15)}.well-lg{padding:24px;border-radius:6px}.well-sm{padding:9px;border-radius:3px}.close{float:right;font-size:21px;font-weight:bold;line-height:1;color:#000;text-shadow:0 1px 0 #fff;opacity:.2;filter:alpha(opacity=20)}.close:hover,.close:focus{color:#000;text-decoration:none;cursor:pointer;opacity:.5;filter:alpha(opacity=50)}button.close{padding:0;cursor:pointer;background:transparent;border:0;-webkit-appearance:none}.modal-open{overflow:hidden}body.modal-open,.modal-open .navbar-fixed-top,.modal-open .navbar-fixed-bottom{margin-right:15px}.modal{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1040;display:none;overflow:auto;overflow-y:scroll}.modal.fade .modal-dialog{-webkit-transform:translate(0,-25%);-ms-transform:translate(0,-25%);transform:translate(0,-25%);-webkit-transition:-webkit-transform .3s ease-out;-moz-transition:-moz-transform .3s ease-out;-o-transition:-o-transform .3s ease-out;transition:transform .3s ease-out}.modal.in .modal-dialog{-webkit-transform:translate(0,0);-ms-transform:translate(0,0);transform:translate(0,0)}.modal-dialog{z-index:1050;width:auto;padding:10px;margin-right:auto;margin-left:auto}.modal-content{position:relative;background-color:#fff;border:1px solid #999;border:1px solid rgba(0,0,0,0.2);border-radius:6px;outline:0;-webkit-box-shadow:0 3px 9px rgba(0,0,0,0.5);box-shadow:0 3px 9px rgba(0,0,0,0.5);background-clip:padding-box}.modal-backdrop{position:fixed;top:0;right:0;bottom:0;left:0;z-index:1030;background-color:#000}.modal-backdrop.fade{opacity:0;filter:alpha(opacity=0)}.modal-backdrop.in{opacity:.5;filter:alpha(opacity=50)}.modal-header{min-height:16.428571429px;padding:15px;border-bottom:1px solid #e5e5e5}.modal-header .close{margin-top:-2px}.modal-title{margin:0;line-height:1.428571429}.modal-body{position:relative;padding:20px}.modal-footer{padding:19px 20px 20px;margin-top:15px;text-align:right;border-top:1px solid #e5e5e5}.modal-footer:before,.modal-footer:after{display:table;content:" "}.modal-footer:after{clear:both}.modal-footer:before,.modal-footer:after{display:table;content:" "}.modal-footer:after{clear:both}.modal-footer .btn+.btn{margin-bottom:0;margin-left:5px}.modal-footer .btn-group .btn+.btn{margin-left:-1px}.modal-footer .btn-block+.btn-block{margin-left:0}@media screen and (min-width:768px){.modal-dialog{right:auto;left:50%;width:600px;padding-top:30px;padding-bottom:30px}.modal-content{-webkit-box-shadow:0 5px 15px rgba(0,0,0,0.5);box-shadow:0 5px 15px rgba(0,0,0,0.5)}}.tooltip{position:absolute;z-index:1030;display:block;font-size:12px;line-height:1.4;opacity:0;filter:alpha(opacity=0);visibility:visible}.tooltip.in{opacity:.9;filter:alpha(opacity=90)}.tooltip.top{padding:5px 0;margin-top:-3px}.tooltip.right{padding:0 5px;margin-left:3px}.tooltip.bottom{padding:5px 0;margin-top:3px}.tooltip.left{padding:0 5px;margin-left:-3px}.tooltip-inner{max-width:200px;padding:3px 8px;color:#fff;text-align:center;text-decoration:none;background-color:#000;border-radius:4px}.tooltip-arrow{position:absolute;width:0;height:0;border-color:transparent;border-style:solid}.tooltip.top .tooltip-arrow{bottom:0;left:50%;margin-left:-5px;border-top-color:#000;border-width:5px 5px 0}.tooltip.top-left .tooltip-arrow{bottom:0;left:5px;border-top-color:#000;border-width:5px 5px 0}.tooltip.top-right .tooltip-arrow{right:5px;bottom:0;border-top-color:#000;border-width:5px 5px 0}.tooltip.right .tooltip-arrow{top:50%;left:0;margin-top:-5px;border-right-color:#000;border-width:5px 5px 5px 0}.tooltip.left .tooltip-arrow{top:50%;right:0;margin-top:-5px;border-left-color:#000;border-width:5px 0 5px 5px}.tooltip.bottom .tooltip-arrow{top:0;left:50%;margin-left:-5px;border-bottom-color:#000;border-width:0 5px 5px}.tooltip.bottom-left .tooltip-arrow{top:0;left:5px;border-bottom-color:#000;border-width:0 5px 5px}.tooltip.bottom-right .tooltip-arrow{top:0;right:5px;border-bottom-color:#000;border-width:0 5px 5px}.popover{position:absolute;top:0;left:0;z-index:1010;display:none;max-width:276px;padding:1px;text-align:left;white-space:normal;background-color:#fff;border:1px solid #ccc;border:1px solid rgba(0,0,0,0.2);border-radius:6px;-webkit-box-shadow:0 5px 10px rgba(0,0,0,0.2);box-shadow:0 5px 10px rgba(0,0,0,0.2);background-clip:padding-box}.popover.top{margin-top:-10px}.popover.right{margin-left:10px}.popover.bottom{margin-top:10px}.popover.left{margin-left:-10px}.popover-title{padding:8px 14px;margin:0;font-size:14px;font-weight:normal;line-height:18px;background-color:#f7f7f7;border-bottom:1px solid #ebebeb;border-radius:5px 5px 0 0}.popover-content{padding:9px 14px}.popover .arrow,.popover .arrow:after{position:absolute;display:block;width:0;height:0;border-color:transparent;border-style:solid}.popover .arrow{border-width:11px}.popover .arrow:after{border-width:10px;content:""}.popover.top .arrow{bottom:-11px;left:50%;margin-left:-11px;border-top-color:#999;border-top-color:rgba(0,0,0,0.25);border-bottom-width:0}.popover.top .arrow:after{bottom:1px;margin-left:-10px;border-top-color:#fff;border-bottom-width:0;content:" "}.popover.right .arrow{top:50%;left:-11px;margin-top:-11px;border-right-color:#999;border-right-color:rgba(0,0,0,0.25);border-left-width:0}.popover.right .arrow:after{bottom:-10px;left:1px;border-right-color:#fff;border-left-width:0;content:" "}.popover.bottom .arrow{top:-11px;left:50%;margin-left:-11px;border-bottom-color:#999;border-bottom-color:rgba(0,0,0,0.25);border-top-width:0}.popover.bottom .arrow:after{top:1px;margin-left:-10px;border-bottom-color:#fff;border-top-width:0;content:" "}.popover.left .arrow{top:50%;right:-11px;margin-top:-11px;border-left-color:#999;border-left-color:rgba(0,0,0,0.25);border-right-width:0}.popover.left .arrow:after{right:1px;bottom:-10px;border-left-color:#fff;border-right-width:0;content:" "}.carousel{position:relative}.carousel-inner{position:relative;width:100%;overflow:hidden}.carousel-inner>.item{position:relative;display:none;-webkit-transition:.6s ease-in-out left;transition:.6s ease-in-out left}.carousel-inner>.item>img,.carousel-inner>.item>a>img{display:block;height:auto;max-width:100%;line-height:1}.carousel-inner>.active,.carousel-inner>.next,.carousel-inner>.prev{display:block}.carousel-inner>.active{left:0}.carousel-inner>.next,.carousel-inner>.prev{position:absolute;top:0;width:100%}.carousel-inner>.next{left:100%}.carousel-inner>.prev{left:-100%}.carousel-inner>.next.left,.carousel-inner>.prev.right{left:0}.carousel-inner>.active.left{left:-100%}.carousel-inner>.active.right{left:100%}.carousel-control{position:absolute;top:0;bottom:0;left:0;width:15%;font-size:20px;color:#fff;text-align:center;text-shadow:0 1px 2px rgba(0,0,0,0.6);opacity:.5;filter:alpha(opacity=50)}.carousel-control.left{background-image:-webkit-gradient(linear,0 top,100% top,from(rgba(0,0,0,0.5)),to(rgba(0,0,0,0.0001)));background-image:-webkit-linear-gradient(left,color-stop(rgba(0,0,0,0.5) 0),color-stop(rgba(0,0,0,0.0001) 100%));background-image:-moz-linear-gradient(left,rgba(0,0,0,0.5) 0,rgba(0,0,0,0.0001) 100%);background-image:linear-gradient(to right,rgba(0,0,0,0.5) 0,rgba(0,0,0,0.0001) 100%);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#80000000',endColorstr='#00000000',GradientType=1)}.carousel-control.right{right:0;left:auto;background-image:-webkit-gradient(linear,0 top,100% top,from(rgba(0,0,0,0.0001)),to(rgba(0,0,0,0.5)));background-image:-webkit-linear-gradient(left,color-stop(rgba(0,0,0,0.0001) 0),color-stop(rgba(0,0,0,0.5) 100%));background-image:-moz-linear-gradient(left,rgba(0,0,0,0.0001) 0,rgba(0,0,0,0.5) 100%);background-image:linear-gradient(to right,rgba(0,0,0,0.0001) 0,rgba(0,0,0,0.5) 100%);background-repeat:repeat-x;filter:progid:DXImageTransform.Microsoft.gradient(startColorstr='#00000000',endColorstr='#80000000',GradientType=1)}.carousel-control:hover,.carousel-control:focus{color:#fff;text-decoration:none;opacity:.9;filter:alpha(opacity=90)}.carousel-control .icon-prev,.carousel-control .icon-next,.carousel-control .glyphicon-chevron-left,.carousel-control .glyphicon-chevron-right{position:absolute;top:50%;left:50%;z-index:5;display:inline-block}.carousel-control .icon-prev,.carousel-control .icon-next{width:20px;height:20px;margin-top:-10px;margin-left:-10px;font-family:serif}.carousel-control .icon-prev:before{content:'\2039'}.carousel-control .icon-next:before{content:'\203a'}.carousel-indicators{position:absolute;bottom:10px;left:50%;z-index:15;width:60%;padding-left:0;margin-left:-30%;text-align:center;list-style:none}.carousel-indicators li{display:inline-block;width:10px;height:10px;margin:1px;text-indent:-999px;cursor:pointer;border:1px solid #fff;border-radius:10px}.carousel-indicators .active{width:12px;height:12px;margin:0;background-color:#fff}.carousel-caption{position:absolute;right:15%;bottom:20px;left:15%;z-index:10;padding-top:20px;padding-bottom:20px;color:#fff;text-align:center;text-shadow:0 1px 2px rgba(0,0,0,0.6)}.carousel-caption .btn{text-shadow:none}@media screen and (min-width:768px){.carousel-control .icon-prev,.carousel-control .icon-next{width:30px;height:30px;margin-top:-15px;margin-left:-15px;font-size:30px}.carousel-caption{right:20%;left:20%;padding-bottom:30px}.carousel-indicators{bottom:20px}}.clearfix:before,.clearfix:after{display:table;content:" "}.clearfix:after{clear:both}.pull-right{float:right!important}.pull-left{float:left!important}.hide{display:none!important}.show{display:block!important}.invisible{visibility:hidden}.text-hide{font:0/0 a;color:transparent;text-shadow:none;background-color:transparent;border:0}.affix{position:fixed}@-ms-viewport{width:device-width}@media screen and (max-width:400px){@-ms-viewport{width:320px}}.hidden{display:none!important;visibility:hidden!important}.visible-xs{display:none!important}tr.visible-xs{display:none!important}th.visible-xs,td.visible-xs{display:none!important}@media(max-width:767px){.visible-xs{display:block!important}tr.visible-xs{display:table-row!important}th.visible-xs,td.visible-xs{display:table-cell!important}}@media(min-width:768px) and (max-width:991px){.visible-xs.visible-sm{display:block!important}tr.visible-xs.visible-sm{display:table-row!important}th.visible-xs.visible-sm,td.visible-xs.visible-sm{display:table-cell!important}}@media(min-width:992px) and (max-width:1199px){.visible-xs.visible-md{display:block!important}tr.visible-xs.visible-md{display:table-row!important}th.visible-xs.visible-md,td.visible-xs.visible-md{display:table-cell!important}}@media(min-width:1200px){.visible-xs.visible-lg{display:block!important}tr.visible-xs.visible-lg{display:table-row!important}th.visible-xs.visible-lg,td.visible-xs.visible-lg{display:table-cell!important}}.visible-sm{display:none!important}tr.visible-sm{display:none!important}th.visible-sm,td.visible-sm{display:none!important}@media(max-width:767px){.visible-sm.visible-xs{display:block!important}tr.visible-sm.visible-xs{display:table-row!important}th.visible-sm.visible-xs,td.visible-sm.visible-xs{display:table-cell!important}}@media(min-width:768px) and (max-width:991px){.visible-sm{display:block!important}tr.visible-sm{display:table-row!important}th.visible-sm,td.visible-sm{display:table-cell!important}}@media(min-width:992px) and (max-width:1199px){.visible-sm.visible-md{display:block!important}tr.visible-sm.visible-md{display:table-row!important}th.visible-sm.visible-md,td.visible-sm.visible-md{display:table-cell!important}}@media(min-width:1200px){.visible-sm.visible-lg{display:block!important}tr.visible-sm.visible-lg{display:table-row!important}th.visible-sm.visible-lg,td.visible-sm.visible-lg{display:table-cell!important}}.visible-md{display:none!important}tr.visible-md{display:none!important}th.visible-md,td.visible-md{display:none!important}@media(max-width:767px){.visible-md.visible-xs{display:block!important}tr.visible-md.visible-xs{display:table-row!important}th.visible-md.visible-xs,td.visible-md.visible-xs{display:table-cell!important}}@media(min-width:768px) and (max-width:991px){.visible-md.visible-sm{display:block!important}tr.visible-md.visible-sm{display:table-row!important}th.visible-md.visible-sm,td.visible-md.visible-sm{display:table-cell!important}}@media(min-width:992px) and (max-width:1199px){.visible-md{display:block!important}tr.visible-md{display:table-row!important}th.visible-md,td.visible-md{display:table-cell!important}}@media(min-width:1200px){.visible-md.visible-lg{display:block!important}tr.visible-md.visible-lg{display:table-row!important}th.visible-md.visible-lg,td.visible-md.visible-lg{display:table-cell!important}}.visible-lg{display:none!important}tr.visible-lg{display:none!important}th.visible-lg,td.visible-lg{display:none!important}@media(max-width:767px){.visible-lg.visible-xs{display:block!important}tr.visible-lg.visible-xs{display:table-row!important}th.visible-lg.visible-xs,td.visible-lg.visible-xs{display:table-cell!important}}@media(min-width:768px) and (max-width:991px){.visible-lg.visible-sm{display:block!important}tr.visible-lg.visible-sm{display:table-row!important}th.visible-lg.visible-sm,td.visible-lg.visible-sm{display:table-cell!important}}@media(min-width:992px) and (max-width:1199px){.visible-lg.visible-md{display:block!important}tr.visible-lg.visible-md{display:table-row!important}th.visible-lg.visible-md,td.visible-lg.visible-md{display:table-cell!important}}@media(min-width:1200px){.visible-lg{display:block!important}tr.visible-lg{display:table-row!important}th.visible-lg,td.visible-lg{display:table-cell!important}}.hidden-xs{display:block!important}tr.hidden-xs{display:table-row!important}th.hidden-xs,td.hidden-xs{display:table-cell!important}@media(max-width:767px){.hidden-xs{display:none!important}tr.hidden-xs{display:none!important}th.hidden-xs,td.hidden-xs{display:none!important}}@media(min-width:768px) and (max-width:991px){.hidden-xs.hidden-sm{display:none!important}tr.hidden-xs.hidden-sm{display:none!important}th.hidden-xs.hidden-sm,td.hidden-xs.hidden-sm{display:none!important}}@media(min-width:992px) and (max-width:1199px){.hidden-xs.hidden-md{display:none!important}tr.hidden-xs.hidden-md{display:none!important}th.hidden-xs.hidden-md,td.hidden-xs.hidden-md{display:none!important}}@media(min-width:1200px){.hidden-xs.hidden-lg{display:none!important}tr.hidden-xs.hidden-lg{display:none!important}th.hidden-xs.hidden-lg,td.hidden-xs.hidden-lg{display:none!important}}.hidden-sm{display:block!important}tr.hidden-sm{display:table-row!important}th.hidden-sm,td.hidden-sm{display:table-cell!important}@media(max-width:767px){.hidden-sm.hidden-xs{display:none!important}tr.hidden-sm.hidden-xs{display:none!important}th.hidden-sm.hidden-xs,td.hidden-sm.hidden-xs{display:none!important}}@media(min-width:768px) and (max-width:991px){.hidden-sm{display:none!important}tr.hidden-sm{display:none!important}th.hidden-sm,td.hidden-sm{display:none!important}}@media(min-width:992px) and (max-width:1199px){.hidden-sm.hidden-md{display:none!important}tr.hidden-sm.hidden-md{display:none!important}th.hidden-sm.hidden-md,td.hidden-sm.hidden-md{display:none!important}}@media(min-width:1200px){.hidden-sm.hidden-lg{display:none!important}tr.hidden-sm.hidden-lg{display:none!important}th.hidden-sm.hidden-lg,td.hidden-sm.hidden-lg{display:none!important}}.hidden-md{display:block!important}tr.hidden-md{display:table-row!important}th.hidden-md,td.hidden-md{display:table-cell!important}@media(max-width:767px){.hidden-md.hidden-xs{display:none!important}tr.hidden-md.hidden-xs{display:none!important}th.hidden-md.hidden-xs,td.hidden-md.hidden-xs{display:none!important}}@media(min-width:768px) and (max-width:991px){.hidden-md.hidden-sm{display:none!important}tr.hidden-md.hidden-sm{display:none!important}th.hidden-md.hidden-sm,td.hidden-md.hidden-sm{display:none!important}}@media(min-width:992px) and (max-width:1199px){.hidden-md{display:none!important}tr.hidden-md{display:none!important}th.hidden-md,td.hidden-md{display:none!important}}@media(min-width:1200px){.hidden-md.hidden-lg{display:none!important}tr.hidden-md.hidden-lg{display:none!important}th.hidden-md.hidden-lg,td.hidden-md.hidden-lg{display:none!important}}.hidden-lg{display:block!important}tr.hidden-lg{display:table-row!important}th.hidden-lg,td.hidden-lg{display:table-cell!important}@media(max-width:767px){.hidden-lg.hidden-xs{display:none!important}tr.hidden-lg.hidden-xs{display:none!important}th.hidden-lg.hidden-xs,td.hidden-lg.hidden-xs{display:none!important}}@media(min-width:768px) and (max-width:991px){.hidden-lg.hidden-sm{display:none!important}tr.hidden-lg.hidden-sm{display:none!important}th.hidden-lg.hidden-sm,td.hidden-lg.hidden-sm{display:none!important}}@media(min-width:992px) and (max-width:1199px){.hidden-lg.hidden-md{display:none!important}tr.hidden-lg.hidden-md{display:none!important}th.hidden-lg.hidden-md,td.hidden-lg.hidden-md{display:none!important}}@media(min-width:1200px){.hidden-lg{display:none!important}tr.hidden-lg{display:none!important}th.hidden-lg,td.hidden-lg{display:none!important}}.visible-print{display:none!important}tr.visible-print{display:none!important}th.visible-print,td.visible-print{display:none!important}@media print{.visible-print{display:block!important}tr.visible-print{display:table-row!important}th.visible-print,td.visible-print{display:table-cell!important}.hidden-print{display:none!important}tr.hidden-print{display:none!important}th.hidden-print,td.hidden-print{display:none!important}} \ No newline at end of file diff --git a/doc/Icinga-Design/documentation.css b/doc/Icinga-Design/documentation.css deleted file mode 100644 index 30bd9c27f..000000000 --- a/doc/Icinga-Design/documentation.css +++ /dev/null @@ -1,125 +0,0 @@ -/* ========================================================================== - Styles ONLY used for documentation - ========================================================================== */ - -html { - font-family: sans-serif; -} - - -/* Projektname - color customer CI */ - -.docu-project-name { - font-size: 2em; - color: #049BAF; - padding-bottom: 10px; -} - - -.docu-main { - width: 100%; - padding: 20px; - margin: 0 auto; - margin-top: 50px; - display: block; -} - - -.docu-main-headline { - font-size: 2em; - color: #333; - /* customer CI */ - padding-bottom: 10px; - padding-top: 40px; -} - - -.docu-sub-headline { - font-size: 1.5em; - color: #333; - padding-bottom: 3px; - padding-top: 10px; -} - - -.docu-section { - border: 1px solid #dddddd; - overflow: hidden; - display: block; -} - - -.docu-description { - padding-bottom: 10px; -} - - -.docu-example { - background-color: #FFFFFF; - padding: 10px; -} - - -.docu-example:before { - color: #BBBBBB; - content: "Example"; - font-weight: bold; - letter-spacing: 1px; - margin-bottom: 10px; -} - - -.docu-module { - /* width: 320px; */ - /* show your modules in device width */ - padding-top: 10px; -} - - -.docu-codeblock { - background-color: #F7F7F9; - border-top: 1px solid #e1e1e8; - padding: 10px; - overflow: hidden; - height: 100%; -} - - -.docu-codeblock:before { - color: #BBBBBB; - content: "Code"; - font-weight: bold; - letter-spacing: 1px; - margin-bottom: 10px; -} - - -.docu-code { - font-family: "Courier New", Courier, monospace; - font-weight: bold; - color: #777; - padding-top: 10px; - border: none; - background-color: transparent; - display: block; - width: 100%; - height: 150px; -} - - -.docu-footer { - margin-top: 40px; - padding-top: 10px; - border-top: 1px solid #dddddd; - font-size: 0.75em; - color: #ccc; -} - - -.docu-classes { - background-color: #FEFBED; - padding: 3px; - color: #c6b256; - font-family: "Courier New", Courier, monospace, sans-serif; - font-weight: bold; -} diff --git a/doc/Icinga-Design/documentation.html b/doc/Icinga-Design/documentation.html deleted file mode 100644 index e0ae9b066..000000000 --- a/doc/Icinga-Design/documentation.html +++ /dev/null @@ -1,974 +0,0 @@ - - - - - Icinga Documentation - - - - - - - - - - - - - - - - - - - - - - -
- -

Icinga Documentation

- - - -

Basic Elements

- -

Headlines

- - -
-
-
-

Main headline h1

-

Sub headline h2

-
-
- -
- -
-
- - -

Textblocks

-
- Used on simple pages with continuous text e.g. Imprint or Privacy. -
- -
-
-
- -

- Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. -

- -
-
- -
- -
-
- - - - -

Table

-
- Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. -
- -
-
-
- - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
StatusOutput
- - - - - - - - 12 - - -
- - Up
- Since  - 30.09. -
-
- - host_000 - 127.0.0.1 -
- host_000 (checked by localhost.localdomain) OK: random hostcheck ok
- - Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. - -
- - -
-
-
-
- - - 6 - - -
- Unreachable
- Since  - 30.09. -
-
- - host_000 - 127.0.0.1 -
- host_000 (checked by localhost.localdomain) OK: random hostcheck ok - - Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. - -
- - - - - - - 6 - - -
- Down
- Since  - 30.09. -
-
- - host_000 - 127.0.0.1 -
- host_000 (checked by localhost.localdomain) OK: random hostcheck ok -
- - - - - - - 6 - - -
- Up
- Since  - 30.09. -
-
- - host_000 - 127.0.0.1 -
- host_000 (checked by localhost.localdomain) OK: random hostcheck ok -
- - - - - - - 6 - - -
- Up
- Since  - 30.09. -
-
- - host_000 - 127.0.0.1 -
- host_000 (checked by localhost.localdomain) OK: random hostcheck ok - - Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. - -
- - -
-
-
-
- - - 6 - - -
- Down
- Since  - 30.09. -
-
- - host_000 - 127.0.0.1 -
- host_000 (checked by localhost.localdomain) OK: random hostcheck ok - - Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. - -
- - - -
- - -
- -
- - - - - -

Pagination

- -
- The pagination is placed on top and bottom of every list. -
- -
-
-
- - - -
-
- -
- -
-
- - - - -

Details

- -

Basic Example

-
- Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. -
- -
-
-
- - -
-
- Host Status host_000 ölaierjoe paeurüuaeraeüure - Unreachable since 15:59
-
-
- -
- -
-

host_000 (checked by localhost.localdomain) OK: random hostcheck ok sometimes with multiline and html tags\n

-
- -
- Recheck -
- - -
-
- Last Check -
-
- 1381308168 -
-
- -
-
- Next Check -
-
- 1381309978 -
-
- -
-
- - -
-
- Host Address -
-
- 127.0.0.1 -
-
- -
-
- Alias -
-
- random_000 -
-
- - - -
- - - - - -
-
- Box mit Tabelle
-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
LoremIpsum xyzblablubb
08.10. 15:51Lorem ipusm_002
08.10. 15:51Ich bin ein toller Text
Hallo halloServer 123 blablaNoch ein Text
Lorem ipsumJuhuhallo_host01128747404
-
- - - - - -
-
- Heading
-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Passive Checks
Active Checks
Obsessing
Notifications
Event Handler
Flap Detection
-
- - - -
-
- -
- -
-
- - - - -

Form Elements

- -

Select

-
- Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. -
- -
-
-
- - -
-
- - -
-
-
-
-
-
- - -
-
- -
- -
-
- - -

Main Navigation

- -

Without Subnavigation

-
- Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. -
- -
-
-
- - - - -
-
- - -
- - - - -

With Subnavigation

-
- Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. -
- -
-
-
- - - - -
-
- - -
- - - - - - - - - - - -

Dashboard

- - -
-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
- Dies ist eine tolle Headline -
09.10. 17:40 - - - - - Service on Hosta
unknown - - Ping on Host_123456
11.10. - - - - random_06 on Host_insertEFFECT
unknown - - Ping on Host_123456
unknown - - Ping on Host_123456
-
- - - -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
- Dies ist eine tolle Headline -
09.10. - - - - Ping on Host_0815
unknown - - Ping on Host_123456
11.10. - - - - random_06 on Host_insertEFFECT
unknown - - Ping on Host_123456
unknown - - Ping on Host_123456
11.10. - - - - random_06 on Host_insertEFFECT
11.10. - - - - random_06 on Host_insertEFFECT
-
- -
-
- - -
- - - - - - - - - -

Main Header

- -

Sub Header

-
- Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. -
- -
-
-
-

bla

-

blubb

-
-
- -
- -
-
- - - - - - - - - - - - - diff --git a/doc/Icinga-Design/icinga-design.css b/doc/Icinga-Design/icinga-design.css deleted file mode 100644 index d8f2bd724..000000000 --- a/doc/Icinga-Design/icinga-design.css +++ /dev/null @@ -1,955 +0,0 @@ -/* ========================================================================== - Icinga Design - ========================================================================== */ - -html { - font-family: sans-serif; /* 1 */ - -ms-text-size-adjust: 100%; /* 2 */ - -webkit-text-size-adjust: 100%; /* 2 */ - overflow-y: scroll; -} - -body { - margin: 0; - color: #262625; - font-family: "Lucida Grande","Lucida Sans Unicode",Verdana,Helvetica,Arial,sans-serif; - font-size: 16px; -} - -p { - line-height: 18px; -} - -.gap { - margin-bottom: 15px; -} - - -/* ========================================================================== - Links - ========================================================================== */ - -a { - color: #049baf; - text-decoration: none; -} - -/** - * Address `outline` inconsistency between Chrome and other browsers. - */ - -a:focus { - outline: thin dotted; -} - -/** - * Improve readability when focused and also mouse hovered in all browsers. - */ - -a:active, -a:hover { - outline: 0; - color: #049baf; - text-decoration: underline; -} - -/* ========================================================================== - Typography - ========================================================================== */ - -/** - * Address variable `h1` font-size and margin within `section` and `article` - * contexts in Firefox 4+, Safari 5, and Chrome. - */ - -h1 { - color: #262625; - font-size: 20px; -} - -h2 { - color: #262625; - font-size: 16px; -} - - -p { - margin-top: 0; -} - - -/* ========================================================================== - Tables - ========================================================================== */ - - -table, th, td { -text-align: left; -vertical-align: top; -} - -table { - border-collapse: collapse; - border-spacing: 0; -} - -th { - font-weight: bold; - font-size: 18px; - padding: 8px 8px 10px 8px; - border-bottom: 2px solid #ddd; -} - -.table-detail th { - font-size: 16px; - border-top: 0; -} - - -.table-detail thead > tr > th, .table tbody > tr > th, -.table-detail tbody > tr > td, .table tfoot > tr > td { - border-top: 0 !important; -} - - - - -.table-detail > thead { - border-top: 0 !important; -} - - - -td { - padding: 8px 10px 8px 8px !important; - border-bottom: 1px dotted #ddd !important; - border-top: none; - -} - -.pull-right { - float: right !important; - clear: right !important; - - display: block; - clear: right; - overflow: hidden; -} - -.badge-container { - display: block; - overflow: hidden; -} - - -.badge { - background-color: #fff; - border-radius: 2px; - color: #ff3300; - display: inline-block; - font-size: 12px; - font-weight: bold; - line-height: 1; - min-width: 10px; - padding-bottom: 3px; - padding-left: 10px; - padding-right: 10px; - padding-top: 3px; - text-align: center; - vertical-align: baseline; - white-space: nowrap; - border: 1px solid #ff3300; - -} - -.badge a, -.badge a:active, -.badge a:hover, -.badge:hover { - color: #ff3300 !important; - display: inline-block !important; - -} - -.host-name { - display: block; - margin-top: 5px; - font-weight: bold; -} - - -.active { - background-color: #f5f5f5; - -} - -.output-text { - font-size: 12px; - line-height: 14px; - display: inline-block; -} - - - -.panel-disabled { - border-left: 8px solid #FF3300; -} - -.panel-enabled { - border-left: 8px solid #00CC33; -} - - -/* ========================================================================== - Forms - ========================================================================== */ - - -.form-inline .form-group { - display: inline-block; - margin-bottom: 0; - vertical-align: middle; -} -.form-group { - margin-bottom: 15px; -} - -label { - display: inline-block; - font-weight: bold; - margin-bottom: 5px; -} - -.input-sm { - border-radius: 3px; - font-size: 16px; - - - padding: 5px; - margin-right: 15px; - -} -.form-control { - background-color: #FFFFFF; - border: 1px solid #CCCCCC; - border-radius: 4px; - padding: 5px; - box-shadow: 0 1px 1px rgba(0, 0, 0, 0.075) inset; - color: #555555; - display: block; - - - - - vertical-align: middle; - width: 100%; -} - -select.input-sm { - -} - - - -/* ========================================================================== - Pagination - ========================================================================== */ - -.pagination > .active > a, -.pagination > .active > span, -.pagination > .active > a:hover, -.pagination > .active > span:hover, -.pagination > .active > a:focus, -.pagination > .active > span:focus { - - background-color: #049baf !important; - border-color: fuchsia !important; - -} - - -.pagination-sm > li > a, .pagination-sm > li > span { - font-size: 16px !important; -} - - - -/* ========================================================================== - Status colors - ========================================================================== */ - -.status-up { - background-color: #00cc33; /* green */ -} - -.status-warning { - background-color: #00cc33; /* xx */ -} - -.status-critical { - background-color: #ff3300; /* red */ -} - -.status-unknown { - background-color: #00cc33; /* xx */ -} - -.status-pending { - background-color: #00cc33; /* xx */ -} - - - -/** Service status **/ - -.tacheader-status-critical { - background-color: #FF3300; -} - -.tacheader-status-ok { - background-color: #00CC33; -} - -.tacheader-status-warning { - background-color: #FFA500; -} - -.tacheader-status-unknown { - background-color: #E066FF; -} - -/** Host status **/ - -.tacheader-status-unreachable { - background-color: #E066FF; -} - -.tacheader-status-down { - background-color: #FF3300; -} - -.tacheader-status-up { - background-color: #00CC33; -} - - -/* Borders for Detail Headers */ - -.border-status-critical { - border-left: 10px solid #FF3300; -} - -.border-status-ok { - border-left: 10px solid #00CC33; -} - -.border-status-warning { - border-left: 10px solid #FFA500; -} - -.border-status-unknown { - border-left: 10px solid #E066FF; -} - -/** Host status **/ - -.border-status-unreachable { - border-left: 10px solid #E066FF; -} - -.border-status-down { - border-left: 10px solid #FF3300; -} - -.border-status-up { - background-color: #00CC33; -} - - - - - - - -/* ========================================================================== - Icons - ========================================================================== */ - -.icon-table { - width: 16px; - height: 20px; - display: block; - background-position: 50% 0; -} - -.icon-header { - background-position: 0 50%; - padding-left: 25px; - height: 20px; -} - -.icon-btn-small { - background-position: 0 0; - width: 16px; - height: 16px; - display: block; -} - -.icon-table-hint { - width: 16px; - height: 20px; - display: block; - background-position: 50% 50%; -} -.icon-table-hint:after { - content: "edited"; - padding-left: 22px; -} - - -.icon-flapping { - background-image: url('images/flapping.png'); - background-repeat: no-repeat; -} -.icon-comment { - background-image: url('images/comment.png'); - background-repeat: no-repeat; -} -.icon-unhandled { - background-image: url('images/unhandled.png'); - background-repeat: no-repeat; -} -.icon-host { - background-image: url('images/host.png'); - background-repeat: no-repeat; -} -.icon-acknowledgement { - background-image: url('images/acknowledgement.png'); - background-repeat: no-repeat; -} -.icon-remove { - background-image: url('images/remove.png'); - background-repeat: no-repeat; -} -.icon-submit { - background-image: url('images/submit.png'); - background-repeat: no-repeat; -} -.icon-create { - background-image: url('images/create.png'); - background-repeat: no-repeat; -} -.icon-dashboard { - background-image: url('images/dashboard.png'); - background-repeat: no-repeat; -} -.icon-disable { - background-image: url('images/disable.png'); - background-repeat: no-repeat; -} -.icon-edit { - background-image: url('images/edit.png'); - background-repeat: no-repeat; -} -.icon-error { - background-image: url('images/error.png'); - background-repeat: no-repeat; -} -.icon-downtime { - background-image: url('images/in_downtime.png'); - background-repeat: no-repeat; -} -.icon-save { - background-image: url('images/save.png'); - background-repeat: no-repeat; -} -.icon-service { - background-image: url('images/service.png'); - background-repeat: no-repeat; -} -.icon-user { - background-image: url('images/user.png'); - background-repeat: no-repeat; -} -.icon-reschedule { - background-image: url('images/reschedule.png'); - background-repeat: no-repeat; -} -.icon-refresh { - background-image: url('images/refresh.png'); - background-repeat: no-repeat; -} - - -/* ========================================================================== - Details Panel - ========================================================================== */ - - -.panel-heading { - border-bottom: 0; - margin-bottom: 0px !important; - padding-left: 5px; - padding-bottom: 3px; - padding-top: 5px; - overflow: hidden; - border-radius: 0; -} - -.panel-hostname { - font-weight: bold; -} - -.separator { - border-top: 2px solid #ddd; - border-bottom: 0; - margin: 0; - height: 2px; -} - -.panel-header-status { - font-weight: normal; -} - -.panel-row { - display: block; - margin-bottom: 10px; - overflow: hidden; - border-bottom: 1px dotted #ddd; - padding-bottom: 10px; -} - - -.panel-label { - float: left; - padding-right: 10px; - width: 30%; - clear: left; - -} -.panel-content { - float: left; - padding-right: 10px; - display: inline-block; - max-width: 40%; -} - -.panel-button { - float: right; - display: inline-block; - overflow: hidden; -} - -.panel-body { - margin-bottom: 45px; -} - - - -/* ========================================================================== - Buttons - ========================================================================== */ - -.button { - text-align: center; - padding: 3px; - border-width: 1px; - border-style: solid; - border-radius: 3px; -} - -.btn-common { - border-color: #ddd; - color: #262625; - background: rgb(255,255,255); /* Old browsers */ - background: -moz-linear-gradient(top, rgb(255,255,255) 1%, rgb(245,245,245) 100%); /* FF3.6+ */ - background: -webkit-gradient(linear, left top, left bottom, color-stop(1%,rgb(255,255,255)), color-stop(100%,rgb(245,245,245))); /* Chrome,Safari4+ */ - background: -webkit-linear-gradient(top, rgb(255,255,255) 1%,rgb(245,245,245) 100%); /* Chrome10+,Safari5.1+ */ - background: -o-linear-gradient(top, rgb(255,255,255) 1%,rgb(245,245,245) 100%); /* Opera 11.10+ */ - background: -ms-linear-gradient(top, rgb(255,255,255) 1%,rgb(245,245,245) 100%); /* IE10+ */ - background: linear-gradient(to bottom, rgb(255,255,255) 1%,rgb(245,245,245) 100%); /* W3C */ -} - -.panel-row > a:hover, -.btn-common:hover { - border-color: #262625 !important; - color: #262625 !important; - text-decoration: none; -} - - -.btn-cta { - border-color: #049BAF; - color: #049BAF; - background: rgb(255,255,255); /* Old browsers */ - background: -moz-linear-gradient(top, rgb(255,255,255) 1%, rgb(245,245,245) 100%); /* FF3.6+ */ - background: -webkit-gradient(linear, left top, left bottom, color-stop(1%,rgb(255,255,255)), color-stop(100%,rgb(245,245,245))); /* Chrome,Safari4+ */ - background: -webkit-linear-gradient(top, rgb(255,255,255) 1%,rgb(245,245,245) 100%); /* Chrome10+,Safari5.1+ */ - background: -o-linear-gradient(top, rgb(255,255,255) 1%,rgb(245,245,245) 100%); /* Opera 11.10+ */ - background: -ms-linear-gradient(top, rgb(255,255,255) 1%,rgb(245,245,245) 100%); /* IE10+ */ - background: linear-gradient(to bottom, rgb(255,255,255) 1%,rgb(245,245,245) 100%); /* W3C */ -} - - - -.btn-small { - width: 25px; - height: 25px; - display: inline-block; -} - -.btn-wide { - width: 100%; - display: block; -} - -.btn-half-left { - float: left; - width: 48%; -} -.btn-half-right { - float: right; - width: 48%; -} - - -/* ========================================================================== - Main Navigation - ========================================================================== */ - - -.nav-stacked > li + li { - margin-left: 0; - margin-top: 0; -} - - -.nav-stacked { - background-color: #f8f8f8; -} - -.icinga-subnavigation { - list-style: none; -} - - - -.nav-stacked > li { - padding-top: 7px; - padding-bottom: 7px; - border-bottom: 1px dotted #049baf; - border-right: 1px dotted #049baf; -} -.nav-stacked > li:first-child { - border-top: 1px dotted #049baf; -} - - -.icinga-subnavigation > li { - padding-top: 8px; - padding-bottom: 8px; - border-bottom: 1px dotted #049baf; - border-right: 1px dotted #049baf; -} - -ul.icinga-subnavigation { - - border-bottom: 1px dotted #049baf; - margin-left: 0; - padding-left: 15px; -} - -.icinga-subnavigation > li:last-child { - padding-top: 8px; - padding-bottom: 8px; - border-bottom: 0; - -} - -.nav-stacked > li > a, -.icinga-subnavigation > li > a { - padding-left: 40px; - padding-right: 3px; - border-left: 6px solid #049baf; - display: inline-block; -} - -.nav-stacked > li > a.nav-notification, -.icinga-subnavigation > li > a.nav-notification { - border-left: 6px solid red !important; -} - -.nav-stacked > li > a:hover, -.icinga-subnavigation > li > a:focus { -/* font-weight: bold;*/ - background-color: transparent !important; - display: inline-block; -} - -.nav-stacked > li:hover, -.nav-stacked > li:focus, -.icinga-subnavigation > li:hover, -.icinga-subnavigation > li:focus { -background-color: #fff; - -} - -.nav-stacked > li.active, -.icinga-subnavigation > li.active { - background-color: #fff; - border-right: 0; -} - - - - -.nav-icon-hosts { - background-image: url('images/host_petrol.png'); - background-repeat: no-repeat; - background-position: 19px 50%; -} - -.nav-icon-services { - background-image: url('images/service_petrol.png'); - background-repeat: no-repeat; - background-position: 19px 50%; -} -.nav-icon-downtimes { - background-image: url('images/in_downtime_petrol.png'); - background-repeat: no-repeat; - background-position: 19px 50%; -} -.nav-icon-notifications { - background-image: url('images/notification_petrol.png'); - background-repeat: no-repeat; - background-position: 19px 20px; -} -.nav-icon-comments { - background-image: url('images/comment_petrol.png'); - background-repeat: no-repeat; - background-position: 19px 50%; -} -.nav-icon-dashboard { - background-image: url('images/dashboard_petrol.png'); - background-repeat: no-repeat; - background-position: 19px 50%; -} -.nav-icon-configuration { - background-image: url('images/configuration_petrol.png'); - background-repeat: no-repeat; - background-position: 19px 50%; -} - - -.subnav-icon-configuration { - background-image: url('images/configuration_petrol.png'); - background-repeat: no-repeat; - background-position: 19px 50%; -} - - - - - -.badge-container-nav { - display: inline-block; - overflow: hidden; - padding-top: 0; - margin-bottom: 5px; - -} -.badge-nav { - background-color: #fff; - border-radius: 2px; - color: #ff3300; - display: inline-block; - font-size: 12px; - font-weight: bold; - line-height: 1; - min-width: 10px; - padding-bottom: 3px; - padding-left: 7px; - padding-right: 7px; - padding-top: 3px; - text-align: center; - vertical-align: baseline; - white-space: nowrap; - border: 1px solid #ff3300; -} - -.badge-container-subnav { - position: absolute; - overflow: hidden; - padding-top: 0; - margin-left: 2px; - margin-top: -8px; -} -.badge-subnav { - background-color: #fff; - border-radius: 2px; - color: #ff3300; - display: inline-block; - font-size: 10px; - font-weight: bold; - line-height: 1; - min-width: 10px; - padding-bottom: 2px; - padding-left: 5px; - padding-right: 5px; - padding-top: 2px; - text-align: center; - vertical-align: baseline; - white-space: nowrap; - border: 1px solid #ff3300; -} - - - -/* ========================================================================== - Dashboard - ========================================================================== */ - -.dashboard-container { - - margin-right: 40px; - margin-bottom: 20px; - - display: inline-block; - vertical-align: top; - -} - -.dashboard-icons { - display: inline-block; - height: 16px; - width: 16px; -} - - - - -/* ========================================================================== - Top Navbar - ========================================================================== */ - - -.icinga-logo { - background-attachment: scroll; - background-clip: border-box; - background-color: rgba(0, 0, 0, 0); - background-image: url("images/logo_icinga.png"); - background-origin: padding-box; - background-position: center center; - background-repeat: no-repeat; - background-size: auto auto; - display: block; - height: 33px; - margin-bottom: 0; - margin-left: 8px; - margin-right: 30px; - margin-top: 8px; - text-indent: -999px; - width: 94px; -} - -.icinga-icon-user { - background-attachment: scroll; - background-clip: border-box; - background-color: rgba(0, 0, 0, 0); - background-image: url("images/user.png"); - background-origin: padding-box; - background-position: center center; - background-repeat: no-repeat; - background-size: auto auto; - display: inline-block; - height: 16px; - width: 16px; -} - -.icinga-navbar { - margin-right: 15px; -} -.icinga-navbar-reload { - margin-top: 13px; - margin-right: 40px; -} - -.icinga-navbar-search { - background-image: url('images/search.png'); - background-repeat: no-repeat; - background-position: 5px 50%; - padding-left: 25px !important; -} - -.icinga-navbar-search-container { - border-left: 1px solid #ddd; - padding-left: 15px; - margin-top: 12px; -} - - - -.icinga-navbar-hosts-container { - background-image: url('images/host.png'); - background-repeat: no-repeat; - background-position: 5px 50%; - padding-left: 30px !important; - margin-top: 15px; -} -.icinga-navbar-services-container { - background-image: url('images/service.png'); - background-repeat: no-repeat; - background-position: 5px 50%; - padding-left: 25px !important; - margin-top: 15px; -} - -.icinga-navbar-pills { - border-style: solid; - border-width: 1px; - padding: 3px 5px 3px 5px; - border-radius: 3px; - font-size: 13px; -} - - - -/** Service status **/ - -.icinga-navbar-pills-critical { - border-color: #FF3300; - color: #FF3300; -} - -.icinga-navbar-pills-ok { - border-color: #00CC33; - color: #00CC33; -} - -.icinga-navbar-pills-warning { - border-color: #FFA500; - color: #FFA500; -} - -.icinga-navbar-pills-unknown { - border-color: #E066FF; - color: #E066FF; -} - -/** Host status **/ - -.icinga-navbar-pills-unreachable { - border-color: #E066FF; - color: #E066FF; -} - -.icinga-navbar-pills-down { - border-color: #FF3300; - color: #FF3300; -} - -.icinga-navbar-pills-up { - border-color: #00CC33; - color: #00CC33; -} - diff --git a/doc/Icinga-Design/images/acknowledgement.png b/doc/Icinga-Design/images/acknowledgement.png deleted file mode 100644 index eb03d2db9fd1aa0a8b86c45d4fd31cbbda8e12fe..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 501 zcmVT(!FYwK@`UE-y1AVA>fLztJuQ?pK#uz0aPA zel?;WNA$Oc_b8(O7SW$-t?628N{My6!v}0+)@kQ8e8Pjwx>HI##}%BY3J zuawxuMO>JNagYJLMK={0gm!TW=Q8V$ML%?~NTozK*q-1Pp5Q9hGwXN}Jk0=P)`sgC r<15y1_FwQH4rXk_Hl8h-dA@!DHO8Q#1R#?V00000NkvXXu0mjfW){$H diff --git a/doc/Icinga-Design/images/comment.png b/doc/Icinga-Design/images/comment.png deleted file mode 100644 index b7d88a0ace463d9d9df4fc6c1ecf8ae4fba7fd05..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 491 zcmVL(oc)dQ4|O8&u^L%i`hw7iF@u=DT_gonzEf_H(tY#vQvuPY@}x46)3V$ zY$*#HCU(wkWNBk#V?nwWeovm6H1ja0?&93;_n!0pGxXl=rRMg8#{6_sYaGBb&ZA-h z1HK~h5>GPQw+UvLP^dLlv5L=ljaT?IzB`7qID?~D%WU^R?_ES$k0=>Y&h_5ybRx>d zh_V?`)_d=Uh;nCK`($SOJ`3+!V?Q?VSVZX&j`*E{E4YeF{sieGUf^M7`!d07N#fWa!c#oMQfAxSiPH8D3LfEZX8W+49L)3HldQ5eVZ&wY6hQG=UEHHC$%lY=%CLeO?-Xly!DlZD`*2tqj-5kXMi zKOiXb6121=IJA^B78H&yE-nflM^{>2i(dj{ya<4zYVV84Ibwd szyI$&Kwa0T*2(MyR%En5A1!JKJ*~|yoOls<8#^QfRe`9i1_uO;ubI5L%%AC8OEW-O)obw;EAR|Qa;X=4(TXK0hCBZNlvRBQJs3ngPNx_i=Gs17!g%iL zY>MIfAAqu|Pv9bUU@?YL46mk9nuker;5AOA7;d-bdOt=mm}2P97uH}WCeW8+_?Y(# z4C4zFdE*ymV^%)Yjduvxj}K*4cjd?0(T0Jts*3_cc$zs6XCW&bNHJ_pF>Jq)?DmKF}&d4&$JzHGzM!Bhcz6zi&fZ!lwx@P$BO@a=aJkd fe8-}!*I)4)6V$-th-l9300000NkvXXu0mjfy|Nh2 diff --git a/doc/Icinga-Design/images/create.png b/doc/Icinga-Design/images/create.png deleted file mode 100644 index b9bedf82a764de10c8e54a9b7007eade8104b6f8..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 475 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`EX7WqAsj$Z!;#Vf4nJ za0`JjZQG2Dvly;50{sg z1Q>i!TGMp)&q-e26y7}??@wk=a7|=oK6}Q+W%H}q0wUq9lBXA}zP{{j<42d$Rep1S z?c44*wb)F=uuWKI+82MXuMY$69_l%*ob%9}Z-Z=d#LV4}H|IZ)sXtv+xT3&hF=I%? z>ow{7Ohn|1-$x@M8;p02{4#7ns|f@~#4Z$-~2<2%0NQ1MCq!v5{=lnvW% zYqj+D)W-b&6ty(OzHI3+iEGtnWrf$AVswh4Pdex9dj3Cqm4KPwhQ&WuZA<9kmYMoT zqPikqG|S>{h-G@JN0h1L>52pECtbgx;}candCIHnf=fd7fBU2NVCmr}tp1u;|Nq*T zcJ|4nJ za0`Jj4nJ za0`JjuD>E~E=>r_UO%PPAbP0 Hl+XkK{pF#} diff --git a/doc/Icinga-Design/images/disabled.png b/doc/Icinga-Design/images/disabled.png deleted file mode 100644 index 54d036410639f46bded8fb5d7168f30a2f2e1664..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 535 zcmV+y0_gpTP)-fdK@bMu=N>M$1}yvtDJ*uj6G8ugaJdGo#0XZ3U}qgGg=lFkw6ON0 zQqUh@lvFmNf|h%FZ!jQ6u(EJ1a;}^NP42)fyR+~6?(8r#sI}@_&M}7@xQzKO`~^>O zx0H6Pk00~}a*j*5g$=CX6B?YrxD&ixO8e|Dsn)92Dk9y9NE;DpG>z@{h;%k0eT_&f z)7bRlVno`ENJsuh?ujf!q^*dwRBJVeNC)u_*Gg&Mn!$38F&^S{(-mwoD;Y{@*D%5I z5La=(r+#1`@~>|D3fCJP#pjMZ!neJ=!@vg|Yr4blS<~;?aJo!z60b{X-{c&JX8gh_ zOon)jMXc@u>}O*Q_lUGGLn9rJNIxUeg<7koOZx>L z;A75lZjYDG<2~+`(!S*1!?c1;tasqXcELtn+BZvSpHDeE1Uiv9EaQru4nJ za0`JjReY2pud27?%7X5YCtUC4974EPs zu!zg|S8$H2nDpLz(Y35MKAF4bUHal?Kl@5lucYPj$ra7P71Dw067R5CE*GsiB>d)q z?7j!TK5^{n>aUOre7EI?)47-CcKWi-*QF;k}f8%dHH}Ct0l`cDPo__yW>zvz^ z#XEJM%(?b4k*}`fw1s$J--G#LVh`AP=l5&0$L=#Zkj-m9yLtPDo5wfU9H{2aKd)JB zyr@Px%x2}*Qvfc diff --git a/doc/Icinga-Design/images/error.png b/doc/Icinga-Design/images/error.png deleted file mode 100644 index 62458999f89ed83086512a3a09d7dfbc92b30de8..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 532 zcmV+v0_**WP)L(lKk)K@bJ--#@tnK}akttOUW^=`F-Yw6L;J3me5+1wl|zR1hMlRs0xQ z*?4FmjfIv0tAOrWDWngH7K*SIw}DG?ITQyL-n@M?`(~N0*6M#^X4+*$dK!@yr)j#q z97LoOc#94faxU*D>3UO|KgUf}EaLbi(ZmrV(penB3%ta^h;;6+8{iop=Un7m;7Q|l zN3C_+NojC7rNL^$ODPSO8vc~h;L1+@HU|-D77KXTs8cxI@O>;a&7LD%#YWC$7?Jwe zz-C11=UiUn2d+SJ1`TGj^HA0 zjDJqf%RpH`;whEBw9X`^R|rX|&$`9uD9b&iJ>e`1%K( WnT^lgNzbML00005)6a{~K^O<{*Y|71+NF@#^1J=cC|hz;e(aW%)RqeeHf`;;YX5*eh@2d@ zjfexq!9j9yuu@9$qZKzv4l~K7D3{%XA}1e*osYgbt*54D-t){n@AvzeQB{@2ju2Ws zA+-A2v8Mlvi+CDi7^;De7{gxlqJf7g<@tIu#?U}NmZ6C~n7~wwVP#7BMh9NuIXWg+l3dU!rD@G8&0K^pOl;#?8B{;@>oqBq?CVP z5UVhPIb5y}ml!V>j@7`wZCqWZjW`?+77f!=)p7mE-dEDfr*szos#ngJMj{O zDdnmWLhA%};7Fkza2OY`5ncFD*!JNlrm!3*o48wyxrgnTOeufF8EnFBe8yJ{rIcq= z%Ev8qC^zvFYl=Z{Q_44ssk4~GISiCBUZfnr7F=zF(CWqJLUAUg{Hxuh7(*|Xmi_y9 zWZ|8Rrj#En`X`p(cs+#HTnMd0HTJg)i-{ORCwfxKpK9z6dK25uY2{{u00000NkvXX Hu0mjfTF@0O diff --git a/doc/Icinga-Design/images/host.png b/doc/Icinga-Design/images/host.png deleted file mode 100644 index 12eb9a6b965504a0cec6fdde58dd64e5c39c2dc0..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 512 zcmV+b0{{JqP)AAsReSLJ$ptIk{b^#kDP`Ap8Rw8WM!Y<_d{~ zmZpLR2Z`1Y1l^t!1mUKcXem+AZRk0-L4)6E#`M^0R+U>RwiUwA35nuhC zKF6n>p2PTrR*dETKsublXWYg&45sZCRFa3dj+IJq8gKCf&+sC~a!HQ~p?IGdmEb#C z>DDb=4xyOuCBO{U>w;ex#~!vZiiwQiQerxSGkA(exP`SC%Z*Hh`#4({{Kk1)!%dtD zq4N!z+|d3 z7D90~lVBX1b-^L#(*DHB3|!4J|9;v2+Kc~zJIo)+T2B@@qNU9M00004nJ za0`JjZSczqK+cRKc25L z?l_o{xymGyS<#h?`y*!ytMtVw++~#=GsHdYQ-ipgd-*4@b7=fnzGP2^KFi9n)C3t?S4z2%inD|4DTM-_UXB9>Q{6<&hhg1y#kl{`V5b*S8Xy~lcZn% z_NG^6Uecu9W#ybPm+SP-C^YCRE{mP>z@q%^!H&n(e^)li@qgqzUnrL(#l10ThGRkJ z@gE)bOXb~I`nilbu5tb05#JGB)%_~hc72oekH*~=M>5~tD(`+FaQXeAGj}=oC%dHQ5XgA-Jjbt;>a7;>|ASUCcMm!- zhG7J(VgEL9#%HX>7*0@EAxxa1!k3il_xCUmWB7nYTvj1Wbg_;f7{+KqK3+8u+YH`dqb~BVb&-F;7Tz`ylQ=>c{|p=W8Ma694r6hQw83-| z53thG`+Qr3XJNgFs<+o{kd+m@z;ld5wSbp_(>lRp-B{o8JF0K!$D>|Bda3apT7Y3}6{g>LULYM|g_!y2w{s#8(F` z2JSATSy>HY98384KXJe(EM;YNgwrJ5**`&ogSyB++`&LrR%@8YWs>gfckmuRFo?ce n^cVPpDQu?L!}eWHZou9@gXdOoq3=^<00000NkvXXu0mjfY5mU) diff --git a/doc/Icinga-Design/images/logo_icinga.png b/doc/Icinga-Design/images/logo_icinga.png deleted file mode 100644 index 162bfdd69d6fd894dbd895cd1741e5f4c2981615..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2619 zcmai0dpwkB8-AsXC0i*uWHmD;A?D1OcTvnZpXJmbX2xjd9mXk#l$NBglm<)b zqytL6%^{Swk!W{BN)n6cphCV4n|!0g?*8%p_IrQ7_kEt{{$1C7UC({rf4o2Vdb?<8 z7-#?hpylRD_gAhvlrKtMP5JdbYnZ59^kJtEc&m^D$1_C`;J_9}LP$3Ob0_2vG1&>b z+8|p1P+h|f2!TVqJVBOFfMqUXuu?&+k_`a1o29W#77v1vkzXKnwkCQ9uo8JJDjU7o9%(BDl?en8%tT5B{1`DPwL^c(3o7@EVH_Iy z2?F!%(4S3(c=;k}LJ@?t!dh9f@B}iFLd6oS2xJ?A1(Jv-kZ^bsjzF>`5J5Z@Bv>K8 zJZPnwh|K~0>CRuYlqWlM6b#3LI9z;uJT{($6^eG^2vjN+hbQ8QL`x;YQk)P2Go_X> zV&ktF=#ZEt;>N;UVGMFHBQsJcf$h*rr=PDNi1qUNGjWXgOQDn{!%3O3I06=r69^XX z^$9J8{h_~X{79{#W0e#m9$vWFAgCQHx6Pui-ZE?r<#D=zv)UON>K`pM6{;i zY4k-|Cj!C2(UDBEqBszUL_FSxOhB3rohsBX&O6!0DF_je{7ovMx26ZY{~O$b_Dml`C+wb1@_otZO_# zIAQ{lvNn0V-!bsVizjbwV>811-W(igGr@2Jk3si-5^!XkNw*ZruaQ4srUDVWKTf)A zK1-7Eqov2q&aZhoH~M?|T-3sBj`MO}t!wai>OCd28%Ka-QPh63Hp~$WRhI@v49Wx) zi}uK%Yno(Ljfd7(S-kb+2>@>DkG^vC$m$+@D%2mh9Z^yxKjh3luv=|l;Z5IE=eyKv zgVmGLq>XBg2)|lWr@bbc7dH3LcB!wMnV;v5ymJAh8}?mUF}PvdQ%{J^K>c8&?g({yD+!Abq$bQAZ&`k4$kv7(<3rE`w=zQFg9*UK*>ex8iDmju+0hDgoZ zPGdrNj*f$dfC}u=Wo$e`JH@)eGY4MgL)*&;9z8kW{wS0@ppib}o||7< z<+)MbZX+^cty?9ZB94i_(~`Q1q9Zyr!{F0DTE99(lIWy86!hJFf2)y>sO)IzEM6LR zW39cfF9vn@mFC}g{Ku}eT0hEJ7i@DtKgQm2*R__R)Q=-0PT@;RbKpWl z1LMn$7F|NVWeYf(9L;D{$y=LmV1%`O`c&304f5gJ_Ni6)e4Ofg8)8^gRy%*8?3>m( zE7VwK&rgHT@|VemD(Bt1dDpEHD{i;T8a5uji_uh3p&#t?*>lR>N)(`aqRh!)rTLto z7FbgwivQrP62*F}(GYc)&m?J%0IQd?fC@b~2Z?t4qS z{1qc7yu~>4B3MvUhhp#9aj>Ai13zr=ugL8|B`;rgNGd0^m)C~t;U@yInm^Y&A6=o! zO@|H!Be?(Jg$7j92@QIua?a#>tQ`+l3~LBHic?L^Z*=LXBPN5HIV*oGA8TGoB5Znq zNY3p1CXjn8idr;LM=!cRqk%HPtkN!TdcL%&Z{EJy-WI7V+bN`Wi8i*#srPKwD|{3E%IH>EuHaF}j+ z^VNMzlW3WSN4MLM)Vy#gUfYz+wBi|qHny--51^R3C%;xa#x4HNxjA{$D;*;;{tGkP BSt$Sj diff --git a/doc/Icinga-Design/images/notification_petrol.png b/doc/Icinga-Design/images/notification_petrol.png deleted file mode 100644 index cf4e9505a30360e817425fac2a3310b8928836f9..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 604 zcmV-i0;BzjP)LlTS!gQ5eO4@4mU#JYHEzwW^3{QL`+I2qH?TRa~-7pu6j$$ifjE+Kp6F z81!djiwo^CqVPhiXxlDq6QyEcU@L1#M8}~!Z*H4cjN)kNxBbrfanHxOf%l$`j95z` zjm=79*9VZs_5z=Q_`dEGL_nr~x8wTFeX9bbvBSW5;3zNyg!OyZvbzusnx_DP z_a13%CWSQvFH*x42jGj- z>Xg&UEze%dMxE0g`GFrp_kU*QX0IT^8vHugn$Q1jm!W$Uq7Gqp_m6q;^s}F>b45t74Qfc1;(VYw;BPy=5JpXl}Z($y!XJ7 z!2QY!r`09k5Re1f040qbNj(co2)?#o)RMmK`Qk1@c^9}AEU&UOHUdU~7T^N#1~~1s z`WtUc@xf3M#f#;>uKbdM064A6z&UB`lQdQUB=wr6(#$}q*fR}j4;qa$wg6lOa!#xH ql{BmV1*g?L;4rYFdCeF6%lrlyVUb&N#~o7u0000L(xGdXVH5@M-#g}DXmcRA>T@p`G>om-hFJ_Eh_E1-HSJF@m@Hy3$%11h z!LVR783fz&vZk!*#0djIAH&{neEXcb;en@I&OOgLhugK*{12ul2bpmiw{aEoXxPFl zY}DEx;&&qlnbF}E9-_w@>cCsX3Ql3A*8bgrLTgQHO++~tQ8pvWwb5+yMU=Y{|i;kQC3@CC1jW%m1cG|ILdQMMz>>YwtD z_3$L3e26GZtulTwf_!XMA^n1e&RD`khS)oj?>LF&SMGd zxL9kycbvrojAdJoC~N=fVBl^)Yri$lJ@F||;umG%$ar?AMf3mw N002ovPDHLkV1mg5-IxFX diff --git a/doc/Icinga-Design/images/remove.png b/doc/Icinga-Design/images/remove.png deleted file mode 100644 index 98ada7447c70b012c20d175633a670d120224573..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 661 zcmV;G0&4wq$gGR5*=&(ocxjRTKsA&u@}4#yFopbL!=Z^ZmS4zBq z1^k*>k9y82C9YsSwq@3TM-kmP&SDL=;#_7u`9I`oti)my*}npp@ONgNEG6E+@1?|e zX8m+PgjuZ0tnW5#9>0v?XKXAbHf7dpcpC>wiO&YbXIkYY@-A$_7o+CEF&xGA%zC4g z*o5EkHQvPP%sSP`@8BZ#W!C92$gC%D2A4~T*E8#N?7(*18jvSi$A>cOH0b;O@r~#{ zkLa#PbQ^|vdz*;p?niVV4e?Rm_fI>0vQ^)kS(mVvaTOnD)^CRY$CgPe@Yhq=1N_-W zdg46MK`AkV6?iYRJ}4z#!9SVxekt*4Gj=Ys9(hKfl$ga!nRV~L?eB1-3EpZV3r*zk z;}P11jbn1)_Cdbntr7|^&=+@#qUi4_|j%U_ymq|x!dpG_- vhYy!lc^p6CtIT?OIr2c{0`_2YX1((tPzUQN{0FNI00000NkvXXu0mjf!6zy~ diff --git a/doc/Icinga-Design/images/reschedule.png b/doc/Icinga-Design/images/reschedule.png deleted file mode 100644 index 5efc20dbca32ea3edfb7c54340b061117e91d70d..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 400 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`EX7WqAsj$Z!;#Vf4nJ za0`Jjua~oQSQ(x|3W%b_6I{SgI%j}R_t62oUM5OS`nQBhD#Xl`JZC_=1 zSwv{)%5WFU4vocoi`IPlDa?Ok4r9agKU0Ksf0|hw(!KVv z@w;S0sLtc7DS6?h2_`c4`qM;wL%lXG%{!dZ@Ojl;7M(Tq2h0=pIJ}*4(tXv2`9WuH kpVeE%WNs0?fO*G1CaZL>GafVFfkK+W)78&qol`;+0Me10+W-In diff --git a/doc/Icinga-Design/images/save.png b/doc/Icinga-Design/images/save.png deleted file mode 100644 index 2db271920d585eaeffc667dd78df6160689859ac..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 506 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`EX7WqAsj$Z!;#Vf4nJ za0`JjLLym#5l7t?1mG){EDeTV4W0?? z5oX0-onm&F7MFW2Uv-ADS<@lo*}8^Vt6C1Ut_tBQ+<06%j`>@Iw7x6Dl+dL~&-l*V z*|>^_Ii2;EDU-~soxJx$rq(80*__1?*^r(P8@es{pVEfcd&NI9T(vk_k=2^@=RxIL z24iuiXvqgYTNy)AIbNK4nLl&q@|cEIGK`xKWD8vkX8E$})Yh5NXT1%0br|?9In^3I z`)QjrE}QxL#H_HX-*-HBe;LcX!20>?m;X+f3%ydm@PZ-ZL-p4D4||4nJ za0`JjLqX5H$_e_~O zH4M3D`8qU|oLU-`JheMG#F_*G9BWvlyG8z0G8`0%n&~9HRq)CTr6zub6fx7R9H%Pj z-t@x#&BouYi)R+4Kf9e+W_>p=++OLFj99@Y%c#R|&+JNZDf#8#va|bhMdS7#&A~f5 zzVDb9S-+J@@F|~OqT1#>9x<0Ge=Azoo~g>?&`8bV>o2s~oVTr4GEi+}vuD_cJQ1Nlu|k&B*2RD84LZ|(FEZ~fzke(<=IF*{|G3kPU;nZ{aKKmGp#N|c z_wN?>9}UwrB97lY^Q)BON4(3F=8EQw3C1(O{=VVB{Yh~8cNUWqj5fzP|J*UYpwRy1 c+o#9+HGQSuyJojV0|TAG)78&qol`;+08)R(I{*Lx diff --git a/doc/Icinga-Design/images/service.png b/doc/Icinga-Design/images/service.png deleted file mode 100644 index 9df3b48409dda06fedcbf25a1eb1ed661db255d1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 496 zcmVL)3Hk(K@i9BIqkiviv(z{z&`-*5`3JW11B>#wz&dL<_f`5S|MXIE- z2m~<%6i2CGBw=?tm?(ED?R+gn;c+K z>|`NKmsr8~I{xQr##rU}mQsH3fZN3w{;0}^&OOQNF^1KayVC^RCGOx2-o_Xv z+wmIkw;@=KF}!c&yuuG0VXfi6ya0jz|$JAh&@OtFJcT+RmnX(ODXTRdIIzKT=(E2rMyTf zFDl46wy=zM&89W-E};GgqwVfuvwH8R|HS&58c?*ODdi`4d5gHOsR8pbhDQe9g%Wez mEYpGkK2^*9VK*Cgov#4So@B%YS!sX(00004nJ za0`JjF~p*G>E*pyVvZumKHh(2 zox#G*>bQqN`Zdd+j7v)d4!VBi`^KgcEA?3{t|7vzHzRSXPqLsupo$BppyQg{mI*gF zBPWoV;_E=jW%No2hwgTj?B$))``k-NG7uE3!9sn=9KKsI8g7aKfzn zUZqsOTkNCQ;HlF8lWmWD@lKas_V3~!gCkoEJp8{hPCk-u&|lc`^3H~NjMcUWojP7t zu7A$A?~$=s_0L!hH~(qTcaBJ%dn|k|Y1ztCUj;5l?>Q!9_lRp-A+Nr10=Io3*ZL34 z(+kCC&&XT#$-Coa>))x@Eqc2p4cbF9R&C-ljD4ZA|M=2nTIp=YjnWY(jc;VG+LX6y z(>sOxA4Rr*Tw}i_?mpj>@`56ZSetk6cGq~kb(qZfb;GTYr{;Hlb^iczt~>iAI(<$o tG-W>at-SX9eDnG#HxBQxcvt?9_li=+`+8(6j&m diff --git a/doc/Icinga-Design/images/submit.png b/doc/Icinga-Design/images/submit.png deleted file mode 100644 index 40e48260013906316d6e476cb5c79bc1e4dc5bed..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 418 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`EX7WqAsj$Z!;#Vf4nJ za0`JjYhUAuyT`&ebV!&M@r;QSn9lm$I4lM!VYrEeQen+;k@1xsKl`C9e;{s_zwS- zR^5hEZXEIRy1Im8q5UDTd(xNmSz>z%=LCHXh?YtcZB}ZjJEoWyEg~YZJj6G>*|5#~ zjrpeOSu1lh&Wb92@y-fdK@bMu=N_(Bf_8p{6c#(D6G8ug5M#hfP_a@1{)GraglK7MYdI2#~Zs7s8u!*l|a1M**z=t_^FaL@9zSsA?i1a8TZAGMoS!`$#=}JWU5s}tr zu^DkAB5g;cQv<<5M7lhP%}1nZM7rMhy-`Fuj!(FobN8|O&Jp}B+oL&myA`*HC%D*@ zf=z1itUmZvY*Z6Dcbk}CrNJ`Z+8=$f{qPRU4Nl|R0ZE793(kzoX77O8k5&E<i*gp*irN^h^? zP20wNmA8k_#r7)kS-i&moV%U6!`4bSUOl9huSKMvbt~^TOl#Q2hjM#U3bs(5y_$3P rYNi<-FwQHuL(l3ZrQ4q)R&s#(^Y*?OUx0vpXY*eG&s>z~)3kJ7{Agf6%f`WfAX%aE0 z#jYT1Sy&K@f?=*%i&fBe4ezczpO<|u4xI9xncvJg=QrxQ&i}-|A($B}xQ3%WdWYLp z?YG(5g@NYfzF`s9aRZ03of%92vcWn&RJChUY%?>qu!eiPZh%AhIKV$)dF~bP69)(Q zLZ6!}@Ezj;KJIgK1>WFzX8g`&#(o^b+qnW&?G}FE{1m=~FIDaP+4?~r;1OII-L0ffzISh3B}x d$L5`Q@e2jFb Date: Tue, 18 Nov 2014 16:18:09 +0100 Subject: [PATCH 15/17] monitoring: Fix PHPDoc in command-form.phtml --- .../application/views/scripts/partials/command-form.phtml | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/modules/monitoring/application/views/scripts/partials/command-form.phtml b/modules/monitoring/application/views/scripts/partials/command-form.phtml index b6990cf25..76ce0e3ca 100644 --- a/modules/monitoring/application/views/scripts/partials/command-form.phtml +++ b/modules/monitoring/application/views/scripts/partials/command-form.phtml @@ -1,9 +1,8 @@
tabs->showOnlyCloseButton() ?>
-
-

icon('help', $form->getHelp()) ?>

+

icon('help', $form->getHelp()) ?>

From ff3b988324a5756f1e4e56c7cd94c3799378f3a4 Mon Sep 17 00:00:00 2001 From: Eric Lippmann Date: Tue, 18 Nov 2014 16:21:48 +0100 Subject: [PATCH 16/17] doc: View resource configuration directives as table --- doc/resources.md | 140 ++++++++++++++++++++++------------------------- 1 file changed, 64 insertions(+), 76 deletions(-) diff --git a/doc/resources.md b/doc/resources.md index cddfb04d1..fcded81c7 100644 --- a/doc/resources.md +++ b/doc/resources.md @@ -1,96 +1,84 @@ -# Resources +# Resources -The configuration file *config/resources.ini* contains data sources that can be referenced -in other configurations. This allows you to manage all connections to databases at one central -place, avoiding the need to edit several different files, when the connection information of a resource change. +The INI configuration file **config/resources.ini** contains information about data sources that can be referenced in other +configuration files. This allows you to manage all data sources at one central place, avoiding the need to edit several +different files, when the information about a data source changes. -## Configuration +## Configuration -Each section represents a resource, with the section name being the identifier used to -reference this certain section. Depending on the resource type, each section contains different properties. -The property *type* defines the resource type and thus how the properties are going to be interpreted. -The available resource types are 'db', 'statusdat', 'livestatus' and 'ldap' and are -described in detail in the following sections: +Each section in **config/resources.ini** represents a data source with the section name being the identifier used to +reference this specific data source. Depending on the data source type, the sections define different directives. +The available data source types are *db*, *ldap* and *livestatus* which will described in detail in the following +paragraphs. -### db +### Database -This resource type describes a SQL database on an SQL server. Databases can contain users and groups -to handle authentication and permissions, or monitoring data using IDO. +A Database resource defines a connection to a SQL databases which can contain users and groups +to handle authentication and authorization, monitoring data or user preferences. -- *db*: defines the used database vendor, which could be a value like *mysql* or *pgsql*. -- *host*: The hostname that is used to connect to the database. -- *port*: The port that is used to connect to the database. -- *username*: The user name that is used to authenticate. -- *password*: The password of the user given in *username*. -- *dbname*: The name of the database that contains the resources data. +Directive | Description +----------------|------------ +**type** | `db` +**db** | Database management system. Either `mysql` or `pgsql`. +**host** | Connect to the database server on the given host. +**port** | Port number to use for the connection. +**username** | The username to use when connecting to the server. +**password** | The password to use when connecting to the server. +**dbname** | The database to use. -### ldap +**Example:** -The resource is a tree in a ldap domain. This resource type is usually used to fetch users and groups -to handle authentication and permissions. - -- *hostname*: The hostname that is used to connect to the ldap server. -- *port*: The port that is used to connect to the ldap server. -- *root_dn*: The root object of the tree. This is usually an organizational unit like - "ou=people, dc=icinga, dc=org". -- *bind_dn*: The user on the LDAP server that will be used to access it. Usually something - like "cn=admin, cn=config". -- *bind_pw*: The password of the user given in *bind_dn*. +``` +[icingaweb] +type = db +db = mysql +host = localhost +port = 3306 +username = icingaweb +password = icingaweb +dbname = icingaweb +``` -### livestatus +### LDAP -A resource that points to a livestatus socket. This resource type contains monitoring data. +A LDAP resource represents a tree in a LDAP directory. LDAP is usually used for authentication and authorization. -- *socket*: The livestatus socket. Can be either be a path to a domain socket (like - "/usr/local/icinga-mysql/var/rw/live") or to a TCP socket like - (tcp://:) +Directive | Description +----------------|------------ +**type** | `ldap` +**hostname** | Connect to the LDAP server on the given host. +**port** | Port number to use for the connection. +**root_dn** | Root object of the tree, e.g. "ou=people,dc=icinga,dc=org" +**bind_dn** | The user to use when connecting to the server. +**bind_pw** | The password to use when connecting to the server. -### statusdat +**Example:** -A resource that points to statusdat files. This resource type contains monitoring data. - -- *status_file*: The path to the *status.dat* file, like "/usr/local/icinga-mysql/var/status.dat" -- *object_file*: The path to *objects.cache*, like "/usr/local/icinga-mysql/var/objects.cache" +```` +[ad] +type = ldap +hostname = localhost +port = 389 +root_dn = "ou=people,dc=icinga,dc=org" +bind_dn = "cn=admin,ou=people,dc=icinga,dc=org" +bind_pw = admin` +```` -## Factory Implementations +### Livestatus -This section contains documentation documentation for the Icinga2-Web developers that want to -use resources defined in the *resources.ini*. Each supported resource type should have an own -factory class, that can be used to comfortably create instances of classes that provide access -to the data of the resources. +A Livestatus resource represents the location of a Livestatus socket which is used for fetching monitoring data. +Directive | Description +----------------|------------ +**type** | `livestatus` +**socket** | Location of the Livestatus socket. Either a path to a local Livestatus socket or a path to a remote Livestatus socket in the format `tcp://:`. -### ResourceFactory +**Example:** -The ResourceFactory can be used to retrieve objects to access resources. Lets assume -for the following examples, that we have an *resources.ini* that looks like this: - - [statusdat] - type = statusdat - status_file = /usr/local/icinga-mysql/var/status.dat - object_file = /usr/local/icinga-mysql/var/objects.cache - - [ldap_authentication] - type = "ldap" - hostname = "localhost" - port = "389" - root_dn = "ou=people, dc=icinga, dc=org" - bind_dn = "cn=admin, cn=config" - bind_pw = "admin" - - -Here is an example of how to retrieve the resource 'statusdat' from the factory. - - $resource = ResourceFactory::createResource( - ResourceFactory::getResourceConfig('statusdat') - ); - -If you specify a resource that does not exist or has the wrong type, -the factory will throw an ConfigurationException. - - -You can also retrieve a list of all available resources by calling *getResourceConfigs*. - - $resourceConfigs = ResourceFactory::getResourceConfigs(); +```` +[livestatus] +type = livestatus +socket = /var/run/icinga2/cmd/livestatus +```` From f00766323598c9ce5ccad2f70f464a7758ac942d Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Tue, 18 Nov 2014 16:22:33 +0100 Subject: [PATCH 17/17] Show the user a senseful error message in case enabledModules is missing fixes #7205 --- library/Icinga/Application/Modules/Manager.php | 8 ++++++-- library/Icinga/Exception/NotFoundError.php | 9 +++++++++ 2 files changed, 15 insertions(+), 2 deletions(-) create mode 100644 library/Icinga/Exception/NotFoundError.php diff --git a/library/Icinga/Application/Modules/Manager.php b/library/Icinga/Application/Modules/Manager.php index 8857bf2d2..78e505d06 100644 --- a/library/Icinga/Application/Modules/Manager.php +++ b/library/Icinga/Application/Modules/Manager.php @@ -13,6 +13,7 @@ use Icinga\Exception\ConfigurationError; use Icinga\Exception\SystemPermissionException; use Icinga\Exception\ProgrammingError; use Icinga\Exception\NotReadableError; +use Icinga\Exception\NotFoundError; /** * Module manager that handles detecting, enabling and disabling of modules @@ -228,6 +229,7 @@ class Manager * * @return self * @throws ConfigurationError When trying to enable a module that is not installed + * @throws NotFoundError In case the "enabledModules" directory does not exist * @throws SystemPermissionException When insufficient permissions for the application exist */ public function enableModule($name) @@ -245,9 +247,11 @@ class Manager $target = $this->installedBaseDirs[$name]; $link = $this->enableDir . '/' . $name; - if (!is_writable($this->enableDir)) { + if (! is_dir($this->enableDir)) { + throw new NotFoundError('Cannot enable module "%s". Path "%s" not found.', $name, $this->enableDir); + } elseif (!is_writable($this->enableDir)) { throw new SystemPermissionException( - 'Can not enable module "%s". Insufficient system permissions for enabling modules.', + 'Cannot enable module "%s". Insufficient system permissions for enabling modules.', $name ); } diff --git a/library/Icinga/Exception/NotFoundError.php b/library/Icinga/Exception/NotFoundError.php new file mode 100644 index 000000000..c90b0322b --- /dev/null +++ b/library/Icinga/Exception/NotFoundError.php @@ -0,0 +1,9 @@ +