Merge remote-tracking branch 'origin/master' into feature/query-interfaces-6018

Conflicts:
	modules/monitoring/library/Monitoring/Backend/Ido/Query/ContactgroupQuery.php
	modules/monitoring/library/Monitoring/Backend/Ido/Query/IdoQuery.php
	modules/monitoring/library/Monitoring/Backend/Ido/Query/StatusQuery.php
	modules/monitoring/library/Monitoring/Controller.php
This commit is contained in:
Thomas Gelf 2014-05-20 23:15:11 +00:00
commit 12b57c6d95
63 changed files with 1974 additions and 962 deletions

4
.gitignore vendored
View File

@ -1,9 +1,11 @@
# Exclude all hidden files
.*
# But not .gitignore, .vagrant-puppet, .htaccess and .gitkeep
# But not .gitignore, .gitattributes, .vagrant-puppet, .htaccess and .gitkeep
!.gitignore
!.gitattributes
!.vagrant-puppet
!public/.htaccess
!packages/rhel/usr/share/icingaweb/public/.htaccess
!public/.htaccess.in
!.gitkeep

1
.vagrant-puppet/.gitattributes vendored Normal file
View File

@ -0,0 +1 @@
* -crlf

View File

@ -0,0 +1,48 @@
/* Command objects */
object CheckCommand "kernel" {
import "plugin-check-command"
command = [ "sudo", SysconfDir + "/icinga2/scripts/check_kernel" ]
}
object NotificationCommand "mail-host-notification" {
import "plugin-notification-command"
command = [ "/bin/true" ]
env = {
"NOTIFICATIONTYPE" = "$notification.type$"
"HOSTALIAS" = "$host.display_name$",
"HOSTADDRESS" = "$address$",
"HOSTSTATE" = "$host.state$",
"LONGDATETIME" = "$icinga.long_date_time$",
"HOSTOUTPUT" = "$host.output$",
"NOTIFICATIONAUTHORNAME" = "$notification.author$",
"NOTIFICATIONCOMMENT" = "$notification.comment$",
"HOSTDISPLAYNAME" = "$host.display_name$",
"USEREMAIL" = "$user.email$"
}
}
object NotificationCommand "mail-service-notification" {
import "plugin-notification-command"
command = [ "/bin/true" ]
env = {
"NOTIFICATIONTYPE" = "$notification.type$"
"SERVICEDESC" = "$service.name$"
"HOSTALIAS" = "$host.display_name$",
"HOSTADDRESS" = "$address$",
"SERVICESTATE" = "$service.state$",
"LONGDATETIME" = "$icinga.long_date_time$",
"SERVICEOUTPUT" = "$service.output$",
"NOTIFICATIONAUTHORNAME" = "$notification.author$",
"NOTIFICATIONCOMMENT" = "$notification.comment$",
"HOSTDISPLAYNAME" = "$host.display_name$",
"SERVICEDISPLAYNAME" = "$service.display_name$",
"USEREMAIL" = "$user.email$"
}
}

View File

@ -0,0 +1,113 @@
object CheckCommand "dummy-host" {
import "plugin-check-command"
command = [ PluginDir + "/libexec/test_hostcheck.pl" ]
arguments = {
"--type" = "$check_type$"
"--failchance" = "$check_failchance$"
"--previous-state" = "$check_previous_state$"
"--state-duration" = "$check_state_duration$"
"--hostname" = "$check_hostname$"
}
vars.check_type = "UP"
vars.check_failchance = "2%"
vars.check_previous_state = "$state$"
vars.check_state_duration = "$duration_sec$"
vars.check_hostname = "$name$"
}
object CheckCommand "dummy-service" {
import "plugin-check-command"
command = [ PluginDir + "/libexec/test_servicecheck.pl" ]
arguments = {
"--total-critical-on-host" = "$check_critical_on_host$"
"--total-warning-on-host" = "$check_warning_on_host$"
"--type" = "$check_type$"
"--failchance" = "$check_failchance$"
"--previous-state" = "$check_previous_state$"
"--state-duration" = "$check_state_duration$"
"--hostname" = "$check_hostname$"
"--servicedesc" = "$check_servicedesc$"
}
vars.check_critical_on_host = "$host.total_services_critical$"
vars.check_warning_on_host = "$host.total_services_warning$"
vars.check_type = "random"
vars.check_failchange = "5%"
vars.check_previous_state = "$service.state$"
vars.check_duration = "$service.duration_sec$"
vars.check_hostname = "$host.name$"
vars.check_servicedesc = "$service.name$"
}
// Hostgroups
object HostGroup "all-hosts" {
display_name = "All hosts on the system"
assign where true
}
host_types = ["ok", "random", "down", "up", "unreachable", "pending"]
__for (host_type in host_types) {
object HostGroup "all-" + host_type {
display_name = "All " + host_type + " hosts"
assign where regex("^test-" + host_type, host.name)
}
}
service_types = ["ok", "warning", "critical", "unknown", "flapping", "pending"]
// Servicegroups
__for (service_type in service_types) {
object ServiceGroup "service-" + service_type {
display_name = "All " + service_type + " services"
assign where regex("^service-" + service_type, service.name)
}
}
// ---------------------------------------------------------------------------------------------------------------------
// Services
// ---------------------------------------------------------------------------------------------------------------------
__function createService(service_type, num) {
apply Service "service-" + service_type + "-" + string(num + 1) {
import "generic-service"
check_command = "dummy-service"
enable_active_checks = (service_type != "pending")
vars.check_type = service_type
assign where match("*" + service_type + "*", host.vars.check_config)
}
}
__for (num in range(4)) {
__for (service_type in service_types) {
createService(service_type, num)
}
}
// ---------------------------------------------------------------------------------------------------------------------
// Hosts
// ---------------------------------------------------------------------------------------------------------------------
__function createHost(checkType, checkConfig, num, checkEnabled) {
object Host "test-" + checkType + "-" + string(num + 1) {
import "generic-host"
address = "127.0.0.1"
check_command = "dummy-host"
enable_active_checks = checkEnabled
vars.check_type = checkType
vars.check_config = checkConfig
}
}
__for (num in range(10)) {
createHost("ok", "ok", num, true)
createHost("random", "random,flapping", num, true)
createHost("down", "warning,critical", num, true)
createHost("unreachable", "unknown", num, true)
createHost("pending", "pending", num, false)
createHost("flap", "flapping", num, true)
}
// EOF

View File

@ -0,0 +1,13 @@
/**
* The db_ido_mysql library implements IDO functionality
* for MySQL.
*/
library "db_ido_mysql"
object IdoMysqlConnection "ido-mysql" {
user = "icinga2",
password = "icinga2",
host = "localhost",
database = "icinga2"
}

View File

@ -0,0 +1,13 @@
/**
* The db_ido_pgsql library implements IDO functionality
* for PostgreSQL.
*/
library "db_ido_pgsql"
object IdoPgsqlConnection "ido-pgsql" {
user = "icinga2",
password = "icinga2",
host = "localhost",
database = "icinga2"
}

View File

@ -1,2 +1,2 @@
[icinga]
path = "/usr/local/icinga-mysql/var/rw/icinga.cmd"
path = "/var/run/icinga2/cmd/icinga2.cmd"

View File

@ -12,9 +12,9 @@ type = db
db = mysql
host = localhost
port = 3306
password = icinga
username = icinga
dbname = icinga
password = icinga2
username = icinga2
dbname = icinga2
[statusdat]
type = statusdat

View File

@ -5,21 +5,29 @@ include openldap
Exec { path => '/bin:/usr/bin:/sbin' }
$icingaVersion = '1.9.4'
$icinga2Version = '0.0.6'
$icingaVersion = '1.11.2'
$icinga2Version = '0.0.11'
exec { 'create-mysql-icinga-db':
unless => 'mysql -uicinga -picinga icinga',
command => 'mysql -uroot -e "CREATE DATABASE icinga; \
GRANT ALL ON icinga.* TO icinga@localhost \
GRANT SELECT,INSERT,UPDATE,DELETE ON icinga.* TO icinga@localhost \
IDENTIFIED BY \'icinga\';"',
require => Service['mysqld']
}
exec { 'create-mysql-icinga2-db':
unless => 'mysql -uicinga2 -picinga2 icinga2',
command => 'mysql -uroot -e "CREATE DATABASE icinga2; \
GRANT SELECT,INSERT,UPDATE,DELETE ON icinga2.* to icinga2@localhost \
IDENTIFIED BY \'icinga2\';"',
require => Service['mysqld']
}
exec{ 'create-pgsql-icinga-db':
unless => 'sudo -u postgres psql -tAc "SELECT 1 FROM pg_roles WHERE rolname=\'icinga\'" | grep -q 1',
command => 'sudo -u postgres psql -c "CREATE ROLE icinga WITH LOGIN PASSWORD \'icingaweb\';" && \
sudo -u postgres createdb -O icinga -E UTF8 icinga && \
sudo -u postgres createdb -O icinga -E UTF8 -T template0 icinga && \
sudo -u postgres createlang plpgsql icinga',
require => Service['postgresql']
}
@ -40,6 +48,11 @@ group { 'icinga-cmd':
ensure => present
}
group { 'icingacmd':
ensure => present,
require => Exec['install icinga2']
}
user { 'icinga':
ensure => present,
groups => 'icinga-cmd',
@ -47,8 +60,8 @@ user { 'icinga':
}
user { 'apache':
groups => ['icinga-cmd', 'vagrant'],
require => [ Class['apache'], Group['icinga-cmd'] ]
groups => ['icinga-cmd', 'vagrant', 'icingacmd'],
require => [ Class['apache'], Group['icinga-cmd'], Group['icingacmd'] ]
}
cmmi { 'icinga-mysql':
@ -104,7 +117,7 @@ file { '/etc/init.d/ido2db-pgsql':
exec { 'populate-icinga-mysql-db':
unless => 'mysql -uicinga -picinga icinga -e "SELECT * FROM icinga_dbversion;" &> /dev/null',
command => "mysql -uicinga -picinga icinga < /usr/local/src/icinga-mysql/icinga-${icingaVersion}/module/idoutils/db/mysql/mysql.sql",
command => "mysql -uroot icinga < /usr/local/src/icinga-mysql/icinga-${icingaVersion}/module/idoutils/db/mysql/mysql.sql",
require => [ Cmmi['icinga-mysql'], Exec['create-mysql-icinga-db'] ]
}
@ -330,7 +343,91 @@ package { ['cmake', 'boost-devel', 'bison', 'flex']:
ensure => installed
}
#cmmi { 'icinga2':
yumrepo { 'icinga2-repo':
baseurl => "http://packages.icinga.org/epel/6/snapshot/",
enabled => '0',
gpgcheck => '1',
gpgkey => 'http://packages.icinga.org/icinga.key',
descr => "Icinga Repository - ${::architecture}"
}
exec { 'install icinga2':
command => 'yum -d 0 -e 0 -y --enablerepo=icinga2-repo install icinga2',
unless => 'rpm -qa | grep icinga2',
require => Yumrepo['icinga2-repo']
}
exec { 'install icinga2-classicui-config':
command => 'yum -d 0 -e 0 -y --enablerepo=icinga2-repo install icinga2-classicui-config',
unless => 'rpm -qa | grep icinga2-classicui-config',
require => [ Yumrepo['icinga2-repo'], Exec['install icinga2'], Exec['install icinga2-ido-mysql'] ]
}
exec { 'install icinga2-ido-mysql':
command => 'yum -d 0 -e 0 -y --enablerepo=icinga2-repo install icinga2-ido-mysql',
unless => 'rpm -qa | grep icinga2-ido-mysql',
require => [ Yumrepo['icinga2-repo'], Exec['install icinga2'] ],
}
exec { 'install nagios-plugins-all':
command => 'yum -d 0 -e 0 -y --enablerepo=epel install nagios-plugins-all',
unless => 'rpm -qa | grep nagios-plugins-all',
require => [ Class['epel'], Exec['install icinga2'] ],
}
file { '/etc/icinga2/features-enabled/':
ensure => directory,
owner => icinga,
group => icinga,
require => Exec['install icinga2-ido-mysql']
}
file { '/etc/icinga2/features-available/ido-mysql.conf':
source => 'puppet:////vagrant/.vagrant-puppet/files/etc/icinga2/features-available/ido-mysql.conf',
owner => 'icinga',
group => 'icinga',
require => Exec['install icinga2-ido-mysql']
}
file { '/etc/icinga2/features-enabled/ido-mysql.conf':
ensure => 'link',
target => '/etc/icinga2/features-available/ido-mysql.conf',
owner => 'root',
group => 'root',
require => Exec['install icinga2-ido-mysql']
}
file { '/etc/icinga2/conf.d/test-config.conf':
source => 'puppet:////vagrant/.vagrant-puppet/files/etc/icinga2/conf.d/test-config.conf',
owner => 'icinga',
group => 'icinga',
require => [ Exec['install icinga2'], Exec['create_monitoring_test_config'] ]
}
file { '/etc/icinga2/conf.d/commands.conf':
source => 'puppet:////vagrant/.vagrant-puppet/files/etc/icinga2/conf.d/commands.conf',
owner => 'icinga',
group => 'icinga',
require => Exec['install icinga2']
}
service { 'icinga2':
ensure => running,
require => [
Exec['install icinga2'],
File['/etc/icinga2/features-enabled/ido-mysql.conf'],
File['/etc/icinga2/conf.d/test-config.conf'],
File['/etc/icinga2/conf.d/commands.conf']
]
}
exec { 'populate-icinga2-mysql-db':
unless => 'mysql -uicinga2 -picinga2 icinga2 -e "SELECT * FROM icinga_dbversion;" &> /dev/null',
command => "mysql -uroot icinga2 < /usr/share/doc/icinga2-ido-mysql-$icinga2Version/schema/mysql.sql",
require => [ Exec['create-mysql-icinga2-db'], Exec['install icinga2-ido-mysql'] ]
}
# cmmi { 'icinga2':
# url => "https://github.com/Icinga/icinga2/releases/download/v${icinga2Version}/icinga2-${icinga2Version}.tar.gz",
# output => "icinga2-${icinga2Version}.tar.gz",
# configure_command => 'mkdir build &> /dev/null || true && cd build && sudo cmake ..',
@ -338,7 +435,7 @@ package { ['cmake', 'boost-devel', 'bison', 'flex']:
# make => 'true && cd build/ && make && make install',
# require => Package[ ['cmake', 'boost-devel', 'bison', 'flex'] ],
# make_timeout => 900
#}
# }
#configure { 'icingaweb':
# path => '/vagrant',
@ -388,7 +485,7 @@ exec { 'create-mysql-icinga_unittest-db':
exec{ 'create-pgsql-icinga_unittest-db':
unless => 'sudo -u postgres psql -tAc "SELECT 1 FROM pg_roles WHERE rolname=\'icinga_unittest\'" | grep -q 1',
command => 'sudo -u postgres psql -c "CREATE ROLE icinga_unittest WITH LOGIN PASSWORD \'icinga_unittest\';" && \
sudo -u postgres createdb -O icinga_unittest -E UTF8 icinga_unittest && \
sudo -u postgres createdb -O icinga_unittest -E UTF8 -T template0 icinga_unittest && \
sudo -u postgres createlang plpgsql icinga_unittest',
require => Service['postgresql']
}
@ -483,7 +580,7 @@ exec { 'create-mysql-icingaweb-db':
exec { 'create-pgsql-icingaweb-db':
unless => 'sudo -u postgres psql -tAc "SELECT 1 FROM pg_roles WHERE rolname=\'icingaweb\'" | grep -q 1',
command => 'sudo -u postgres psql -c "CREATE ROLE icingaweb WITH LOGIN PASSWORD \'icinga\';" && \
sudo -u postgres createdb -O icingaweb -E UTF8 icingaweb && \
sudo -u postgres createdb -O icingaweb -E UTF8 -T template0 icingaweb && \
sudo -u postgres createlang plpgsql icingaweb',
require => Service['postgresql']
}
@ -699,6 +796,6 @@ file { '/etc/icingaweb/dashboard/dashboard.ini':
group => 'apache',
}
pear::package { 'deepend/Mockery':
channel => 'pear.survivethedeepend.com'
}
# pear::package { 'deepend/Mockery':
# channel => 'pear.survivethedeepend.com'
# }

View File

@ -66,8 +66,9 @@ class ErrorController extends ActionController
break;
default:
$title = preg_replace('/\r?\n.*$/s', '', $exception->getMessage());
$this->getResponse()->setHttpResponseCode(500);
$this->view->title = 'Server error: ' . $exception->getMessage();
$this->view->title = 'Server error: ' . $title;
$this->view->message = $exception->getMessage();
if ($this->getInvokeArg('displayExceptions') == true) {
$this->view->stackTrace = $exception->getTraceAsString();

View File

@ -0,0 +1,111 @@
<?php
// @codeCoverageIgnoreStart
// {{{ICINGA_LICENSE_HEADER}}}
// {{{ICINGA_LICENSE_HEADER}}}
use Icinga\Web\Session;
use Icinga\Web\Wizard\Wizard;
use Icinga\Web\Controller\ActionController;
class InstallController extends ActionController
{
/**
* Whether the controller requires the user to be authenticated
*
* The install wizard has its own authentication mechanism.
*
* @var bool
*/
protected $requiresAuthentication = false;
/**
* Whether the controller requires configuration
*
* The install wizard does not require any configuration.
*
* @var bool
*/
protected $requiresConfiguration = false;
/**
* Show the wizard and run the installation once its finished
*/
public function indexAction()
{
$wizard = $this->createWizard();
if ($wizard->isSubmittedAndValid()) {
$wizard->navigate();
if ($wizard->isFinished()) {
// TODO: Run the installer (Who creates an installer? How do we handle module installers?)
$this->dropConfiguration(); // TODO: Should only be done if the installation has been successfully completed
$this->view->installer = '';
} else {
$this->storeConfiguration($wizard->getConfig());
}
}
$this->view->wizard = $wizard;
}
/**
* Create the wizard and register all pages
*
* @return Wizard
*/
protected function createWizard()
{
$wizard = new Wizard();
$wizard->setTitle('Web');
$wizard->setRequest($this->getRequest());
$wizard->setConfiguration($this->loadConfiguration());
$wizard->addPages(
array(
// t('Welcome') => 'Icinga\Form\Install\WelcomePage',
// t('Requirements') => 'Icinga\Form\Install\RequirementsPage',
// t('Authentication') => 'Icinga\Form\Install\AuthenticationPage',
// t('Administration') => 'Icinga\Form\Install\AdministrationPage',
// t('Preferences') => 'Icinga\Form\Install\PreferencesPage',
t('Logging') => 'Icinga\Form\Install\LoggingPage',
// t('Database Setup') => 'Icinga\Form\Install\DatabasePage',
// t('Summary') => 'Icinga\Form\Install\SummaryPage'
)
);
return $wizard;
}
/**
* Store the given configuration values
*
* @param Zend_Config $config The configuration
*/
protected function storeConfiguration(Zend_Config $config)
{
$session = Session::getSession();
$session->getNamespace('WebWizard')->setAll($config->toArray(), true);
$session->write();
}
/**
* Load all configuration values
*
* @return Zend_Config
*/
protected function loadConfiguration()
{
return new Zend_Config(Session::getSession()->getNamespace('WebWizard')->getAll(), true);
}
/**
* Clear all stored configuration values
*/
protected function dropConfiguration()
{
$session = Session::getSession();
$session->removeNamespace('WebWizard');
$session->write();
}
}
// @codeCoverageIgnoreEnd

View File

@ -30,7 +30,7 @@
namespace Icinga\Form\Config;
use Zend_Config;
use \Zend_Config;
use Icinga\Web\Form;
use Icinga\Application\Icinga;
use Icinga\Web\Form\Validator\WritablePathValidator;
@ -116,7 +116,19 @@ class LoggingForm extends Form
'required' => true,
'label' => t('Application Prefix'),
'helptext' => t('The name of the application by which to prefix syslog messages.'),
'value' => $loggingConfig->get('application', 'icingaweb')
'value' => $loggingConfig->get('application', 'icingaweb'),
'validators' => array(
array(
'Regex',
false,
array(
'pattern' => '/^[^\W]+$/',
'messages' => array(
'regexNotMatch' => 'The application prefix cannot contain any whitespaces.'
)
)
)
)
)
);
$this->addElement(
@ -151,6 +163,16 @@ class LoggingForm extends Form
$this->setSubmitLabel('{{SAVE_ICON}} Save Changes');
}
public function isValid($data) {
foreach ($this->getElements() as $key => $element) {
// Initialize all empty elements with their default values.
if (!isset($data[$key])) {
$data[$key] = $element->getValue();
}
}
return parent::isValid($data);
}
/**
* Return a Zend_Config object containing the state defined in this form
*

View File

@ -0,0 +1,67 @@
<?php
// @codeCoverageIgnoreStart
// {{{ICINGA_LICENSE_HEADER}}}
// {{{ICINGA_LICENSE_HEADER}}}
namespace Icinga\Form\Install;
use Zend_Config;
use Icinga\Web\Wizard\Page;
use Icinga\Form\Config\LoggingForm;
class LoggingPage extends Page
{
/**
* The logging form
*
* @var LoggingForm
*/
protected $loggingForm;
/**
* Initialize this LoggingPage
*/
public function init()
{
$this->setName('logging');
}
/**
* Create and return the logging form
*
* @return LoggingForm
*/
protected function createForm()
{
if ($this->loggingForm === null) {
$this->loggingForm = new LoggingForm();
$this->loggingForm->hideButtons();
$this->loggingForm->setTokenDisabled();
$this->loggingForm->setRequest($this->getRequest());
$this->loggingForm->setConfiguration($this->getConfiguration());
}
return $this->loggingForm;
}
/**
* Create this wizard page
*/
protected function create()
{
$loggingForm = $this->createForm();
$loggingForm->buildForm(); // Needs to get called manually as it's nothing that Zend knows about
$this->addSubForm($loggingForm, $loggingForm->getName());
}
/**
* Return a config containing all values provided by the user
*
* @return Zend_Config
*/
public function getConfig()
{
return $this->createForm()->getConfig();
}
}
// @codeCoverageIgnoreEnd

View File

@ -24,6 +24,7 @@ $isIframe = isset($_GET['_render']) && $_GET['_render'] === 'iframe';
<head>
<meta charset="utf-8">
<meta content="width=320; initial-scale=1.0; maximum-scale=1.0; user-scalable=0;"/>
<meta name="google" value="notranslate">
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
<title><?= $this->title ? $this->escape($this->title) : 'Icinga Web' ?></title>
<!-- TODO: viewport and scale settings make no sense for us, fix this -->

View File

@ -2,6 +2,15 @@
use Icinga\Web\StyleSheet;
$moduleName = $this->layout()->moduleName;
if ($moduleName) {
$moduleClass = ' icinga-module module-' . $moduleName;
} else {
$moduleClass = '';
}
?><!DOCTYPE html>
<html>
<head>
@ -32,7 +41,7 @@ if ( isset($pdf) )
</table>
</div>-->
<h1><?= $this->escape($this->title) ?></h1>
<div id="col1" class="container">
<div id="col1" class="container<?= $moduleClass ?>">
<?= $this->render('inline.phtml') ?>
</div>

View File

@ -0,0 +1,40 @@
<div class="wizard">
<div class="header">
<img src="<?= $this->baseUrl('img/logo_icinga-inv.png'); ?>">
<h1><?= $wizard->getTitle(); ?></h1>
</div>
<div class="sidebar">
<ul>
<?php foreach ($wizard->getPages() as $page): ?>
<li class="<?= $wizard->isCompletedPage($page) ? 'complete' : (
$wizard->isCurrentPage($page) ? 'active' : 'pending'
); ?>">
<?= $page->getTitle(); ?>
<?php if ($wizard->isWizard($page) && $wizard->isCurrentPage($page) && !$wizard->isCompletedPage($page)): ?>
<ul>
<?php foreach ($page->getPages() as $subPage): ?>
<?php if ($page->isCurrentPage($subPage)): ?>
<li class="child active">
<?php else: ?>
<li class="child">
<?php endif ?>
<?= $subPage->getTitle(); ?>
</li>
<?php endforeach ?>
</ul>
<?php endif ?>
</li>
<?php endforeach ?>
<li class="install<?= $wizard->isFinished() ? ' active' : ''; ?>">
<?= $this->translate('Installation'); ?>
</li>
</ul>
</div>
<div class="panel">
<?php if ($wizard->isFinished()): ?>
<?= $this->partial('install/index/installog.phtml', array('installer' => $installer)); ?>
<?php else: ?>
<?= $wizard; ?>
<?php endif ?>
</div>
</div>

View File

@ -0,0 +1 @@
<?= $installer; ?>

View File

@ -75,6 +75,7 @@ create all database tables. You will find the installation guides for the differ
> RPM packages install the schema into /usr/share/doc/icingaweb-&lt;version&gt;/schema
bash$ mysql -u root -p icingaweb < etc/schema/accounts.mysql.sql
bash$ mysql -u root -p icingaweb < etc/schema/preferences.mysql.sql
#### PostgreSQL
@ -108,6 +109,7 @@ And restart your database ('service postgresql restart' or '/etc/init.d/postgres
> RPM packages install the schema into /usr/share/doc/icingaweb-&lt;version&gt;/schema
bash$ psql -U icingaweb -a -f etc/schema/accounts.pgsql.sql
bash$ psql -U icingaweb -a -f etc/schema/preferences.pgsql.sql

384
files
View File

@ -1,384 +0,0 @@
./modules/doc/application/controllers/IndexController.php
./modules/doc/application/controllers/ModuleController.php
./modules/doc/library/Doc/DocParser.php
./modules/doc/library/Doc/Controller.php
./modules/doc/library/Doc/DocException.php
./modules/doc/library/Doc/MarkdownFileIterator.php
./modules/translation/application/clicommands/CompileCommand.php
./modules/translation/application/clicommands/RefreshCommand.php
./modules/translation/library/Translation/Cli/TranslationCommand.php
./modules/translation/library/Translation/Util/GettextTranslationHelper.php
./modules/monitoring/application/forms/Config/Backend/EditBackendForm.php
./modules/monitoring/application/forms/Config/Backend/CreateBackendForm.php
./modules/monitoring/application/forms/Config/ConfirmRemovalForm.php
./modules/monitoring/application/forms/Config/Instance/CreateInstanceForm.php
./modules/monitoring/application/forms/Config/Instance/EditInstanceForm.php
./modules/monitoring/application/forms/Command/DelayNotificationForm.php
./modules/monitoring/application/forms/Command/SubmitPassiveCheckResultForm.php
./modules/monitoring/application/forms/Command/CommandForm.php
./modules/monitoring/application/forms/Command/WithChildrenCommandForm.php
./modules/monitoring/application/forms/Command/CustomNotificationForm.php
./modules/monitoring/application/forms/Command/AcknowledgeForm.php
./modules/monitoring/application/forms/Command/CommentForm.php
./modules/monitoring/application/forms/Command/MultiCommandFlagForm.php
./modules/monitoring/application/forms/Command/RescheduleNextCheckForm.php
./modules/monitoring/application/forms/Command/ScheduleDowntimeForm.php
./modules/monitoring/application/forms/Command/SingleArgumentCommandForm.php
./modules/monitoring/application/forms/Command/DisableNotificationWithExpireForm.php
./modules/monitoring/application/views/helpers/MonitoringFlags.php
./modules/monitoring/application/views/helpers/MonitoringProperties.php
./modules/monitoring/application/views/helpers/CommandForm.php
./modules/monitoring/application/views/helpers/RuntimeVariables.php
./modules/monitoring/application/views/helpers/CheckPerformance.php
./modules/monitoring/application/views/helpers/PluginOutput.php
./modules/monitoring/application/views/helpers/Perfdata.php
./modules/monitoring/application/views/helpers/_RenderServicePerfdata.php
./modules/monitoring/application/views/helpers/SelectionToolbar.php
./modules/monitoring/application/views/helpers/ContactFlags.php
./modules/monitoring/application/views/helpers/ResolveMacros.php
./modules/monitoring/application/views/helpers/MonitoringState.php
./modules/monitoring/application/views/helpers/ResolveComments.php
./modules/monitoring/application/clicommands/NrpeCommand.php
./modules/monitoring/application/clicommands/ConferenceCommand.php
./modules/monitoring/application/clicommands/ListCommand.php
./modules/monitoring/application/controllers/ShowController.php
./modules/monitoring/application/controllers/ConfigController.php
./modules/monitoring/application/controllers/MultiController.php
./modules/monitoring/application/controllers/ListController.php
./modules/monitoring/application/controllers/CommandController.php
./modules/monitoring/application/controllers/MonitoringCommands.php
./modules/monitoring/application/controllers/ChartController.php
./modules/monitoring/application/controllers/TimelineController.php
./modules/monitoring/application/controllers/TacticalController.php
./modules/monitoring/application/controllers/ProcessController.php
./modules/monitoring/library/Monitoring/DataView/Contactgroup.php
./modules/monitoring/library/Monitoring/DataView/Notification.php
./modules/monitoring/library/Monitoring/DataView/Comment.php
./modules/monitoring/library/Monitoring/DataView/Customvar.php
./modules/monitoring/library/Monitoring/DataView/EventHistory.php
./modules/monitoring/library/Monitoring/DataView/StatusSummary.php
./modules/monitoring/library/Monitoring/DataView/DataView.php
./modules/monitoring/library/Monitoring/DataView/Runtimesummary.php
./modules/monitoring/library/Monitoring/DataView/Servicegroup.php
./modules/monitoring/library/Monitoring/DataView/Runtimevariables.php
./modules/monitoring/library/Monitoring/DataView/Contact.php
./modules/monitoring/library/Monitoring/DataView/Programstatus.php
./modules/monitoring/library/Monitoring/DataView/StateHistorySummary.php
./modules/monitoring/library/Monitoring/DataView/Downtime.php
./modules/monitoring/library/Monitoring/DataView/Groupsummary.php
./modules/monitoring/library/Monitoring/DataView/Hostgroup.php
./modules/monitoring/library/Monitoring/DataView/HostStatus.php
./modules/monitoring/library/Monitoring/DataView/ServiceStatus.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/StatusdatQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/ContactgroupQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/ServicegroupsummaryQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/HostgroupQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/CommentQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/DowntimeQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/StatusSummaryQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/GroupsummaryQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/ContactQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/ServicegroupQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/HostlistQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/StatusQuery.php
./modules/monitoring/library/Monitoring/Backend/Statusdat/Query/ServicelistQuery.php
./modules/monitoring/library/Monitoring/Backend/Livestatus/Query/StatusQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/ContactgroupQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/NotificationhistoryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/CustomvarQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/DowntimeendhistoryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/HostgroupQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/CommentQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/DowntimeQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/StatehistoryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/ProgramstatusQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/EventHistoryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/StatusSummaryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/IdoQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/GroupsummaryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/HoststatusQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/RuntimevariablesQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/CommenthistoryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/ContactQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/StateHistorySummaryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/ServicegroupQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/AllcontactsQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/DowntimestarthistoryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/RuntimesummaryQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/StatusQuery.php
./modules/monitoring/library/Monitoring/Backend/Ido/Query/NotificationQuery.php
./modules/monitoring/library/Monitoring/Environment.php
./modules/monitoring/library/Monitoring/Controller.php
./modules/monitoring/library/Monitoring/Timeline/TimeEntry.php
./modules/monitoring/library/Monitoring/Timeline/TimeRange.php
./modules/monitoring/library/Monitoring/Timeline/TimeLine.php
./modules/monitoring/library/Monitoring/Object/Service.php
./modules/monitoring/library/Monitoring/Object/Host.php
./modules/monitoring/library/Monitoring/Object/AbstractObject.php
./modules/monitoring/library/Monitoring/Filter/Type/StatusFilter.php
./modules/monitoring/library/Monitoring/Filter/Registry.php
./modules/monitoring/library/Monitoring/Filter/UrlViewFilter.php
./modules/monitoring/library/Monitoring/Exception/UnsupportedBackendException.php
./modules/monitoring/library/Monitoring/Web/Widget/TimelineIntervalBox.php
./modules/monitoring/library/Monitoring/Web/Hook/TimelineProvider.php
./modules/monitoring/library/Monitoring/Web/Hook/TopBar.php
./modules/monitoring/library/Monitoring/Command/SubmitPassiveCheckresultCommand.php
./modules/monitoring/library/Monitoring/Command/AcknowledgeCommand.php
./modules/monitoring/library/Monitoring/Command/ScheduleDowntimeCommand.php
./modules/monitoring/library/Monitoring/Command/ScheduleCheckCommand.php
./modules/monitoring/library/Monitoring/Command/DisableNotificationWithExpireCommand.php
./modules/monitoring/library/Monitoring/Command/SingleArgumentCommand.php
./modules/monitoring/library/Monitoring/Command/AddCommentCommand.php
./modules/monitoring/library/Monitoring/Command/CustomNotificationCommand.php
./modules/monitoring/library/Monitoring/Command/DelayNotificationCommand.php
./modules/monitoring/library/Monitoring/Plugin.php
./modules/monitoring/library/Monitoring/Cli/CliUtils.php
./modules/monitoring/library/Monitoring/Backend.php
./modules/monitoring/library/Monitoring/Plugin/Perfdata.php
./modules/monitoring/library/Monitoring/Plugin/PerfdataSet.php
./modules/monitoring/run.php
./modules/monitoring/configuration.php
./modules/monitoring/bin/action/list.inc.php
./etc/module_skeleton/application/controllers/IndexController.php
./application/forms/Authentication/LoginForm.php
./application/forms/Config/GeneralForm.php
./application/forms/Config/Authentication/LdapBackendForm.php
./application/forms/Config/Authentication/ReorderForm.php
./application/forms/Config/Authentication/BaseBackendForm.php
./application/forms/Config/Authentication/DbBackendForm.php
./application/forms/Config/LoggingForm.php
./application/forms/Config/ConfirmRemovalForm.php
./application/forms/Config/Resource/CreateResourceForm.php
./application/forms/Config/Resource/EditResourceForm.php
./application/forms/TestForm.php
./application/forms/Dashboard/AddUrlForm.php
./application/forms/Preference/GeneralForm.php
./application/views/helpers/FormNumber.php
./application/views/helpers/DateFormat.php
./application/views/helpers/FormDateTime.php
./application/views/helpers/FormTriStateCheckbox.php
./application/views/helpers/Util.php
./application/clicommands/HelpCommand.php
./application/clicommands/ModuleCommand.php
./application/clicommands/AutocompleteCommand.php
./application/clicommands/WebCommand.php
./application/controllers/ConfigController.php
./application/controllers/ListController.php
./application/controllers/IndexController.php
./application/controllers/LayoutController.php
./application/controllers/PreferenceController.php
./application/controllers/DashboardController.php
./application/controllers/FilterController.php
./application/controllers/StaticController.php
./application/controllers/SearchController.php
./application/controllers/ErrorController.php
./application/controllers/AuthenticationController.php
./library/Icinga/Logger/Logger.php
./library/Icinga/Logger/Writer/StreamWriter.php
./library/Icinga/Logger/Writer/SyslogWriter.php
./library/Icinga/Logger/LogWriter.php
./library/Icinga/User/Preferences.php
./library/Icinga/User/Message.php
./library/Icinga/User/Preferences/Store/IniStore.php
./library/Icinga/User/Preferences/Store/DbStore.php
./library/Icinga/User/Preferences/PreferencesStore.php
./library/Icinga/Authentication/UserBackend.php
./library/Icinga/Authentication/Backend/DbUserBackend.php
./library/Icinga/Authentication/Backend/LdapUserBackend.php
./library/Icinga/Authentication/Membership.php
./library/Icinga/Authentication/Manager.php
./library/Icinga/Authentication/AdmissionLoader.php
./library/Icinga/Authentication/AuthChain.php
./library/Icinga/Data/Db/Query.php
./library/Icinga/Data/Db/TreeToSqlParser.php
./library/Icinga/Data/Db/Connection.php
./library/Icinga/Data/PivotTable.php
./library/Icinga/Data/DatasourceInterface.php
./library/Icinga/Data/DataArray/Query.php
./library/Icinga/Data/DataArray/Datasource.php
./library/Icinga/Data/ResourceFactory.php
./library/Icinga/Data/BaseQuery.php
./library/Icinga/File/Pdf.php
./library/Icinga/File/Csv.php
./library/Icinga/File/Csv/Query.php
./library/Icinga/Test/DbTest.php
./library/Icinga/Test/BaseTestCase.php
./library/Icinga/Test/FormTest.php
./library/Icinga/Protocol/Ldap/Root.php
./library/Icinga/Protocol/Ldap/Query.php
./library/Icinga/Protocol/Ldap/Exception.php
./library/Icinga/Protocol/Ldap/LdapUtils.php
./library/Icinga/Protocol/Ldap/Node.php
./library/Icinga/Protocol/Ldap/Connection.php
./library/Icinga/Protocol/File/Query.php
./library/Icinga/Protocol/File/Reader.php
./library/Icinga/Protocol/Statusdat/Parser.php
./library/Icinga/Protocol/Statusdat/Query.php
./library/Icinga/Protocol/Statusdat/Query/IQueryPart.php
./library/Icinga/Protocol/Statusdat/Query/Group.php
./library/Icinga/Protocol/Statusdat/Query/Expression.php
./library/Icinga/Protocol/Statusdat/View/AccessorStrategy.php
./library/Icinga/Protocol/Statusdat/View/MonitoringObjectList.php
./library/Icinga/Protocol/Statusdat/ObjectContainer.php
./library/Icinga/Protocol/Statusdat/Exception/ParsingException.php
./library/Icinga/Protocol/Statusdat/Reader.php
./library/Icinga/Protocol/Statusdat/IReader.php
./library/Icinga/Protocol/Statusdat/PrintableObject.php
./library/Icinga/Protocol/Statusdat/TreeToStatusdatQueryParser.php
./library/Icinga/Protocol/Statusdat/RuntimeStateContainer.php
./library/Icinga/Protocol/Nrpe/Packet.php
./library/Icinga/Protocol/Nrpe/Connection.php
./library/Icinga/Protocol/Livestatus/Query.php
./library/Icinga/Protocol/Livestatus/Connection.php
./library/Icinga/Protocol/Commandpipe/Transport/Transport.php
./library/Icinga/Protocol/Commandpipe/Transport/LocalPipe.php
./library/Icinga/Protocol/Commandpipe/Transport/SecureShell.php
./library/Icinga/Protocol/Commandpipe/Comment.php
./library/Icinga/Protocol/Commandpipe/Exception/InvalidCommandException.php
./library/Icinga/Protocol/Commandpipe/PropertyModifier.php
./library/Icinga/Protocol/Commandpipe/Command.php
./library/Icinga/Protocol/Commandpipe/CommandPipe.php
./library/Icinga/Application/Platform.php
./library/Icinga/Application/Benchmark.php
./library/Icinga/Application/functions.php
./library/Icinga/Application/LegacyWeb.php
./library/Icinga/Application/Config.php
./library/Icinga/Application/EmbeddedWeb.php
./library/Icinga/Application/ApplicationBootstrap.php
./library/Icinga/Application/Cli.php
./library/Icinga/Application/webrouter.php
./library/Icinga/Application/Modules/Module.php
./library/Icinga/Application/Modules/Manager.php
./library/Icinga/Application/Loader.php
./library/Icinga/Application/Icinga.php
./library/Icinga/Application/Web.php
./library/Icinga/Chart/Primitive/Animation.php
./library/Icinga/Chart/Primitive/Text.php
./library/Icinga/Chart/Primitive/Animatable.php
./library/Icinga/Chart/Primitive/Drawable.php
./library/Icinga/Chart/Primitive/Circle.php
./library/Icinga/Chart/Primitive/Styleable.php
./library/Icinga/Chart/Primitive/RawElement.php
./library/Icinga/Chart/Primitive/Rect.php
./library/Icinga/Chart/Primitive/Line.php
./library/Icinga/Chart/Primitive/Canvas.php
./library/Icinga/Chart/Primitive/PieSlice.php
./library/Icinga/Chart/Primitive/Path.php
./library/Icinga/Chart/Graph/LineGraph.php
./library/Icinga/Chart/Graph/StackedGraph.php
./library/Icinga/Chart/Graph/BarGraph.php
./library/Icinga/Chart/Axis.php
./library/Icinga/Chart/Palette.php
./library/Icinga/Chart/Unit/AxisUnit.php
./library/Icinga/Chart/Unit/LinearUnit.php
./library/Icinga/Chart/Unit/StaticAxis.php
./library/Icinga/Chart/Unit/CalendarUnit.php
./library/Icinga/Chart/PieChart.php
./library/Icinga/Chart/GridChart.php
./library/Icinga/Chart/SVGRenderer.php
./library/Icinga/Chart/Legend.php
./library/Icinga/Chart/Inline/PieChart.php
./library/Icinga/Chart/Inline/Inline.php
./library/Icinga/Chart/Chart.php
./library/Icinga/Chart/Render/RenderContext.php
./library/Icinga/Chart/Render/LayoutBox.php
./library/Icinga/Config/IniEditor.php
./library/Icinga/Config/PreservingIniWriter.php
./library/Icinga/User.php
./library/Icinga/Filter/Query/Tree.php
./library/Icinga/Filter/Query/Node.php
./library/Icinga/Filter/FilterAttribute.php
./library/Icinga/Filter/Type/FilterType.php
./library/Icinga/Filter/Type/BooleanFilter.php
./library/Icinga/Filter/Type/TextFilter.php
./library/Icinga/Filter/Type/TimeRangeSpecifier.php
./library/Icinga/Filter/QueryProposer.php
./library/Icinga/Filter/Registry.php
./library/Icinga/Filter/Filter.php
./library/Icinga/Filter/Filterable.php
./library/Icinga/Filter/Domain.php
./library/Icinga/Exception/NotWritableError.php
./library/Icinga/Exception/MissingParameterException.php
./library/Icinga/Exception/NotImplementedError.php
./library/Icinga/Exception/ConfigurationError.php
./library/Icinga/Exception/NotReadableError.php
./library/Icinga/Exception/SystemPermissionException.php
./library/Icinga/Exception/ProgrammingError.php
./library/Icinga/Web/JavaScript.php
./library/Icinga/Web/Notification.php
./library/Icinga/Web/MenuItem.php
./library/Icinga/Web/Widget/Dashboard.php
./library/Icinga/Web/Widget/FilterBox.php
./library/Icinga/Web/Widget/AlertMessageBox.php
./library/Icinga/Web/Widget/Tabextension/DashboardAction.php
./library/Icinga/Web/Widget/Tabextension/BasketAction.php
./library/Icinga/Web/Widget/Tabextension/Tabextension.php
./library/Icinga/Web/Widget/Tabextension/OutputFormat.php
./library/Icinga/Web/Widget/Chart/InlinePie.php
./library/Icinga/Web/Widget/Chart/HistoryColorGrid.php
./library/Icinga/Web/Widget/AbstractWidget.php
./library/Icinga/Web/Widget/FilterBadgeRenderer.php
./library/Icinga/Web/Widget/Dashboard/Component.php
./library/Icinga/Web/Widget/Dashboard/Pane.php
./library/Icinga/Web/Widget/Tabs.php
./library/Icinga/Web/Widget/Tab.php
./library/Icinga/Web/Widget/Widget.php
./library/Icinga/Web/Widget/SortBox.php
./library/Icinga/Web/Hook.php
./library/Icinga/Web/View/helpers/generic.php
./library/Icinga/Web/View/helpers/url.php
./library/Icinga/Web/View/helpers/format.php
./library/Icinga/Web/Menu.php
./library/Icinga/Web/Session.php
./library/Icinga/Web/Paginator/ScrollingStyle/SlidingWithBorder.php
./library/Icinga/Web/Paginator/Adapter/QueryAdapter.php
./library/Icinga/Web/ViewStream.php
./library/Icinga/Web/Url.php
./library/Icinga/Web/Session/SessionNamespace.php
./library/Icinga/Web/Session/Session.php
./library/Icinga/Web/Session/PhpSession.php
./library/Icinga/Web/StyleSheet.php
./library/Icinga/Web/Hook/Ticket.php
./library/Icinga/Web/Hook/Configuration/ConfigurationTabInterface.php
./library/Icinga/Web/Hook/Configuration/ConfigurationTab.php
./library/Icinga/Web/Hook/Configuration/ConfigurationTabBuilder.php
./library/Icinga/Web/Hook/TopBar.php
./library/Icinga/Web/Hook/Grapher.php
./library/Icinga/Web/Request.php
./library/Icinga/Web/View.php
./library/Icinga/Web/Widget.php
./library/Icinga/Web/Controller/ActionController.php
./library/Icinga/Web/Controller/BaseConfigController.php
./library/Icinga/Web/Controller/BasePreferenceController.php
./library/Icinga/Web/Controller/ControllerTabCollector.php
./library/Icinga/Web/LessCompiler.php
./library/Icinga/Web/Form.php
./library/Icinga/Web/Form/Element/Number.php
./library/Icinga/Web/Form/Element/DateTimePicker.php
./library/Icinga/Web/Form/Element/TriStateCheckbox.php
./library/Icinga/Web/Form/Element/Note.php
./library/Icinga/Web/Form/Decorator/ConditionalHidden.php
./library/Icinga/Web/Form/Decorator/BootstrapForm.php
./library/Icinga/Web/Form/Decorator/HelpText.php
./library/Icinga/Web/Form/Validator/DateFormatValidator.php
./library/Icinga/Web/Form/Validator/TriStateValidator.php
./library/Icinga/Web/Form/Validator/DateTimeValidator.php
./library/Icinga/Web/Form/Validator/TimeFormatValidator.php
./library/Icinga/Web/Form/Validator/WritablePathValidator.php
./library/Icinga/Web/Form/InvalidCSRFTokenException.php
./library/Icinga/Cli/Documentation/CommentParser.php
./library/Icinga/Cli/Params.php
./library/Icinga/Cli/Documentation.php
./library/Icinga/Cli/Screen/AnsiScreen.php
./library/Icinga/Cli/Loader.php
./library/Icinga/Cli/Command.php
./library/Icinga/Cli/Screen.php
./library/Icinga/Util/File.php
./library/Icinga/Util/Dimension.php
./library/Icinga/Util/DateTimeFactory.php
./library/Icinga/Util/Color.php
./library/Icinga/Util/String.php
./library/Icinga/Util/Format.php
./library/Icinga/Util/ConfigAwareFactory.php
./library/Icinga/Util/Translator.php

View File

@ -1,14 +1,15 @@
# $Id$
# Authority: The icinga devel team <icinga-devel at lists.sourceforge.net>
# Upstream: The icinga devel team <icinga-devel at lists.sourceforge.net>
# Authority: The icinga devel team <icinga-devel at lists.icinga.org>
# Upstream: The icinga devel team <icinga-devel at lists.icinga.org>
# ExcludeDist: el4 el3
%define revision 0
%define configdir %{_sysconfdir}/icingaweb
%define logdir %{_localstatedir}/log/icingaweb
%define sharedir %{_datadir}/icingaweb
%define prefixdir %{_datadir}/icingaweb
%define logdir %{sharedir}/log
#%define logdir %{_localstatedir}/log/icingaweb
%if "%{_vendor}" == "suse"
%define phpname php5
@ -41,7 +42,7 @@
Summary: Open Source host, service and network monitoring Web UI
Name: icingaweb2
Version: 1.0.0
Version: 0.0.1
Release: %{revision}%{?dist}
License: GPLv2
Group: Applications/System
@ -52,7 +53,7 @@ BuildArch: noarch
AutoReqProv: Off
%endif
Source0: https://downloads.sourceforge.net/project/icinga/%{name}/%{version}/%{name}-%{version}.tar.gz
Source0: icingaweb2-%{version}.tar.gz
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root
@ -92,108 +93,44 @@ Requires: %{phpname}-json
Requires: apache2-mod_php5
%endif
Requires: %{name}-doc
Requires: %{phpzendname}-Db-Adapter-Pdo
Requires: %{phpzendname}-Db-Adapter-Pdo-Mysql
Requires: php-Icinga
%description
IcingaWeb for Icinga 2 or Icinga 1.x using status data,
IDOUtils or Livestatus as backend provider.
%package config-internal-mysql
Summary: config for internal mysql database
%package -n icingacli
Summary: Icinga CLI
Group: Applications/System
Requires: %{name} = %{version}-%{release}
Requires: %{phpzendname}-Db-Adapter-Pdo
Requires: %{phpzendname}-Db-Adapter-Pdo-Mysql
Requires: php-Icinga
%description config-internal-mysql
Configuration for internal mysql database.
%description -n icingacli
Icinga CLI using php-Icinga Icinga Web 2 backend.
%package config-internal-pgsql
Summary: config for internal pgsql database
%package -n php-Icinga
Summary: Icinga Web 2 PHP Libraries
Group: Applications/System
Requires: %{name} = %{version}-%{release}
Requires: %{phpzendname}-Db-Adapter-Pdo
Requires: %{phpzendname}-Db-Adapter-Pdo-Pgsql
Requires: %{phpname} >= 5.3.0
Requires: %{phpzendname}
%description config-internal-pgsql
Configuration for internal pgsql database.
%package config-backend-statusdata-1x
Summary: Backend config for status data
Group: Applications/System
Requires: %{name} = %{version}-%{release}
Provides: %{name}-config-statusdata
%description -n php-Icinga
Icinga Web 2 PHP Libraries shared with icingacli.
%description config-backend-statusdata-1x
Backend config for status data provided by Icinga 1.x Core.
%package config-backend-ido-mysql-1x
Summary: Backend config for icinga 1.x ido mysql database
Group: Applications/System
Requires: %{name} = %{version}-%{release}
Requires: %{phpname}-mysql
Provides: %{name}-config-ido-mysql
%description config-backend-ido-mysql-1x
Backend config for ido mysql database provided by
Icinga 1.x IDOUtils with MySQL.
%package config-backend-ido-pgsql-1x
Summary: Backend config for icinga 1.x ido pgsql database
Group: Applications/System
Requires: %{name} = %{version}-%{release}
Requires: %{phpname}-pgsql
Provides: %{name}-config-ido-pgsql
%description config-backend-ido-pgsql-1x
Backend config for ido mysql database provided by
Icinga 1.x IDOUtils with PostgreSQL.
%package config-backend-livestatus-1x
Summary: Backend config for icinga 1.x livestatus
Group: Applications/System
Requires: %{name} = %{version}-%{release}
Provides: %{name}-config-livestatus
%description config-backend-livestatus-1x
Backend config for livestatus provided by Icinga 1.x
with mk_livestatus NEB module.
%package config-backend-commands-1x
Summary: Backend config for icinga 1.x commands
Group: Applications/System
Requires: %{name} = %{version}-%{release}
Provides: %{name}-config-commands
%description config-backend-commands-1x
Backend config for external command pipe provided by
Icinga 1.x
%prep
%setup -q -n %{name}-%{version}
#%setup -q -n %{name}-%{version}
%setup -q -n %{name}
%build
%configure \
--prefix="%{prefixdir}" \
--datadir="%{sharedir}" \
--datarootdir="%{sharedir}" \
--sysconfdir="%{configdir}" \
--with-icingaweb-config-path='%{configdir}' \
--with-icingaweb-log-path='%{logdir}' \
--with-web-path='/icingaweb' \
--with-httpd-config-path=%{apacheconfdir} \
--with-web-user='%{apacheuser}' \
--with-web-group='%{apachegroup}' \
--with-internal-db-type='mysql' \
--with-internal-db-name='icingaweb' \
--with-internal-db-host='localhost' \
--with-internal-db-port='3306' \
--with-internal-db-pass='icingaweb' \
--with-internal-db-user='icingaweb' \
--with-internal-authentication=yes \
--with-icinga-commandpipe='%{extcmdfile1x}' \
--with-livestatus-socket='%{livestatussocket1x}'
cat > README.RHEL.SUSE <<"EOF"
IcingaWeb for RHEL and SUSE
@ -205,17 +142,40 @@ EOF
%install
[ "%{buildroot}" != "/" ] && [ -d "%{buildroot}" ] && rm -rf %{buildroot}
%{__mkdir} -p %{buildroot}/%{apacheconfdir}
%{__make} install \
install-apache-config \
DESTDIR="%{buildroot}" \
INSTALL_OPTS="" \
COMMAND_OPTS="" \
INSTALL_OPTS_WEB="" \
INIT_OPTS=""
# prepare configuration for sub packages
# install rhel apache config
install -D -m0644 packages/rhel/etc/httpd/conf.d/icingaweb.conf %{buildroot}/%{apacheconfdir}/icingaweb.conf
# install public, library, modules
%{__mkdir} -p %{buildroot}/%{sharedir}
%{__mkdir} -p %{buildroot}/%{logdir}
%{__mkdir} -p %{buildroot}/%{_sysconfdir}/icingaweb/enabledModules
%{__cp} -r application library modules public %{buildroot}/%{sharedir}/
# install index.php, .htaccess
install -m0644 packages/rhel/usr/share/icingaweb/public/index.php %{buildroot}/%{sharedir}/public/index.php
install -m0644 packages/rhel/usr/share/icingaweb/public/.htaccess %{buildroot}/%{sharedir}/public/.htaccess
# use the vagrant config for configuration for now - TODO
%{__cp} -r .vagrant-puppet/files/etc/icingaweb %{buildroot}/%{_sysconfdir}/
# we use the default 'icinga' database
sed -i 's/icinga2/icinga/g' %{buildroot}/%{_sysconfdir}/icingaweb/resources.ini
# enable the monitoring module by default
ln -s %{sharedir}/modules/monitoring %{buildroot}/%{_sysconfdir}/icingaweb/enabledModules/monitoring
# install icingacli
install -D -m0755 bin/icingacli %{buildroot}/usr/bin/icingacli
# install sql schema files as example
# delete all *.in files
rm -f %{buildroot}/%{_datadir}/%{name}/public/index.php.in
rm -f %{buildroot}/%{_datadir}/%{name}/public/.htaccess.in
%pre
# Add apacheuser in the icingacmd group
@ -243,11 +203,9 @@ fi
%files
# main dirs
%defattr(-,root,root)
%doc etc/schema doc README.RHEL.SUSE
%{sharedir}/application
%{sharedir}/library
%{sharedir}/public
%{sharedir}/modules
%doc etc/schema doc packages/rhel/README
%attr(755,%{apacheuser},%{apachegroup}) %{sharedir}/public
%attr(755,%{apacheuser},%{apachegroup}) %{sharedir}/modules
# configs
%defattr(-,root,root)
%config(noreplace) %attr(-,root,root) %{apacheconfdir}/icingaweb.conf
@ -256,7 +214,14 @@ fi
# logs
%attr(2775,%{apacheuser},%{apachegroup}) %dir %{logdir}
%files -n php-Icinga
%attr(755,%{apacheuser},%{apachegroup}) %{sharedir}/application
%attr(755,%{apacheuser},%{apachegroup}) %{sharedir}/library
%files -n icingacli
%attr(0755,root,root) /usr/bin/icingacli
%changelog
* Sun Oct 20 2013 Michael Friedrich <michael.friedrich@netways.de> - 1.0.0-1
* Tue May 11 2014 Michael Friedrich <michael.friedrich@netways.de> - 0.0.1-1
- initial creation

View File

@ -532,7 +532,7 @@ class Manager
if (! array_key_exists($file, $this->installedBaseDirs)) {
$this->installedBaseDirs[$file] = $canonical . '/' . $file;
} else {
Logger::warning(
Logger::debug(
'Module "%s" already exists in installation path "%s" and is ignored.',
$canonical . '/' . $file,
$this->installedBaseDirs[$file]

View File

@ -87,6 +87,17 @@ if (in_array($path, $special)) {
$pie->initFromRequest();
echo $pie->render();
} elseif ($path === 'png/chart.php') {
if (!array_key_exists('data', $_GET)) {
return false;
}
include __DIR__ . '/EmbeddedWeb.php';
EmbeddedWeb::start();
header('Content-Type: image/png');
$pie = new PieChart();
$pie->initFromRequest();
$pie->toPng();
} elseif (file_exists($baseDir . '/' . $path) && is_file($baseDir . '/' . $path)) {
return false;
} else {

View File

@ -31,12 +31,14 @@
namespace Icinga\Chart\Inline;
use Icinga\Chart\PieChart as PieChartRenderer;
use Imagick;
use Exception;
/**
* Draw an inline pie-chart directly from the available request parameters.
*/
class PieChart extends Inline {
public function render()
public function render($output = true)
{
$pie = new PieChartRenderer();
$pie->disableLegend();
@ -44,6 +46,23 @@ class PieChart extends Inline {
'data' => $this->data, 'colors' => $this->colors, 'labels' => $this->labels
));
$pie->setWidth($this->width)->setHeight($this->height);
echo $pie->render();
if ($output) {
echo $pie->render();
} else {
return $pie->render();
}
}
public function toPng()
{
if (! class_exists('Imagick')) {
// TODO: This is quick & dirty. 404?
throw new Exception('Cannot render PNGs without Imagick');
}
$image = new Imagick();
$image->readImageBlob($this->render(false));
$image->setImageFormat('png24');
$image->resizeImage($this->width, $this->height, imagick::FILTER_LANCZOS, 1);
echo $image;
}
}

View File

@ -75,7 +75,12 @@ class TreeToSqlParser
if (count($right) > 1) {
return 'IN';
} else {
return 'LIKE';
foreach ($right as $r) {
if (strpos($r, '*') !== false) {
return 'LIKE';
}
}
return '=';
}
case Node::OPERATOR_EQUALS_NOT:
if (count($right) > 1) {
@ -171,7 +176,11 @@ class TreeToSqlParser
if ($node->context === Node::CONTEXT_TIMESTRING && !is_numeric($value)) {
$value = strtotime($value);
}
$values[] = $this->query->getDatasource()->getConnection()->quote($value);
if (preg_match('/^\d+$/', $value)) {
$values[] = $value;
} else {
$values[] = $this->query->getDatasource()->getConnection()->quote($value);
}
}
$valueString = join(',', $values);

View File

@ -1,5 +1,4 @@
<?php
// @codeCoverageIgnoreStart
namespace Icinga\File;
@ -18,26 +17,6 @@ spl_autoload_register('DOMPDF_autoload');
class Pdf extends DOMPDF
{
/**
* The amount of table rows that fit on one page before a page-break is inserted.
*
* @var int
*/
public $rowsPerPage = 10;
/**
* Wether tables should only start at new pages.
*
* @var bool
*/
public $tableInitialPageBreak = false;
/**
* Whether occurring tables should be split up into smaller tables to avoid
* errors in the document layout.
*
* @var bool
*/
public $paginateTable = false;
public function __construct()
@ -67,22 +46,10 @@ class Pdf extends DOMPDF
$controller->render();
$layout->content = $controller->getResponse();
$html = $layout->render();
$imgDir = Url::fromPath('img');
$html = preg_replace('~src="' . $imgDir . '/~', 'src="' . Icinga::app()->getBootstrapDirecory() . '/img/', $html);
//echo $html; exit;
$html = preg_replace('~src="/svg/chart.php(.*)"~', 'class="icon" src="http://master1.com/png/chart.php$1"', $html);
$this->load_html($html);
/*
// TODO: We need to find a solution for page footers
$font = Font_Metrics::get_font("helvetica", "bold");
$canvas = $this->get_canvas();
$canvas->page_text(555, 750, "{PAGE_NUM}/{PAGE_COUNT}", $font, 10, array(0,0,0));
$dompdf->page_script('
// $pdf is the variable containing a reference to the canvas object provided by dompdf
$pdf->line(10,730,800,730,array(0,0,0),1);
');
*/
$this->render();
$this->stream(
sprintf(
@ -93,127 +60,4 @@ class Pdf extends DOMPDF
)
);
}
/**
* @param $body
* @param $css
*/
/* public function renderPage($body, $css)
{
$html =
'<html><head></head>'
. '<body>'
. '<style>' . $css
// . Pdf::prepareCss($css)
. '</style>'
. $body
. '</body>'
. '</html>';
if ($this->paginateTable === true) {
$doc = new DOMDocument();
@$doc->loadHTML($html);
$this->paginateHtmlTables($doc);
$html = $doc->saveHtml();
}
$this->load_html($html);
$this->render();
}*/
/**
* Split up tables into multiple elements that each contain $rowsPerPage of all original rows
*
* NOTE: This is a workaround to fix the buggy page-break on table-rows in dompdf.
*
* @param DOMDocument $doc The html document containing the tables.
*
* @return array All paginated tables from the document.
*/
/* private function paginateHtmlTables(DOMDocument $doc)
{
$xpath = new DOMXPath($doc);
$tables = $xpath->query('.//table');
$paginated = array();
$j = 0;
foreach ($tables as $table) {
$containerType = null;
$rows = $xpath->query('.//tr', $table);
$rowCnt = $rows->length;
$tableCnt = (Integer)ceil($rowCnt / $this->rowsPerPage);
$paginated[$j] = array();
if ($rowCnt <= $this->rowsPerPage) {
continue;
}
// remove all rows from the original parent
foreach ($rows as $row) {
if (!isset($containerType)) {
$containerType = $row->parentNode->nodeName;
}
$row->parentNode->removeChild($row);
}
// clone table for each additional page and fetch the row containers
$containers = array();
$pages = array();
if ($this->tableInitialPageBreak) {
$this->pageBreak($doc, $table);
}
for ($i = 0; $i < $tableCnt; $i++) {
// clone table
$currentPage = $table->cloneNode(true);
$pages[$i] = $currentPage;
$table->parentNode->insertBefore($currentPage, $table);
// put it in current paginated table
$paginated[$j] = $currentPage;
// insert page-break
if ($i < $tableCnt - 1) {
$this->pageBreak($doc, $table);
}
// fetch row container
$container = $xpath->query('.//' . $containerType, $currentPage)->item(0);
$containers[$i] = $container;
}
$i = 0;
foreach ($rows as $row) {
$p = (Integer)floor($i / $this->rowsPerPage);
$containers[$p]->appendChild($row);
$i++;
}
// remove original table
$table->parentNode->removeChild($table);
$j++;
}
return $paginated;
}
private function pageBreak($doc, $before)
{
$div = $doc->createElement('div');
$div->setAttribute('style', 'page-break-before: always;');
$before->parentNode->insertBefore($div, $before);
}
*/
/**
* Prepare the given css for rendering with DOMPDF, by removing or hiding all incompatible
* styles
*
* @param $css The css-string
*
* @return string A css-string that is ready to use for DOMPDF
*/
// public static function prepareCss($css)
// {
// $css = preg_replace('/\*:\s*before\s*,\s*/', '', $css);
// $css = preg_replace('/\*\s*:\s*after\s*\{[^\}]*\}/', '', $css);
// return $css;
// }
}
// @codeCoverageIgnoreEnd
}

View File

@ -46,6 +46,7 @@ use Icinga\File\Pdf;
use Icinga\Exception\ProgrammingError;
use Icinga\Web\Session;
use Icinga\Session\SessionNamespace;
use Icinga\Exception\NotReadableError;
/**
* Base class for all core action controllers
@ -61,6 +62,13 @@ class ActionController extends Zend_Controller_Action
*/
protected $requiresAuthentication = true;
/**
* Whether the controller requires configuration
*
* @var bool
*/
protected $requiresConfiguration = true;
private $config;
private $configs = array();
@ -114,26 +122,24 @@ class ActionController extends Zend_Controller_Action
$this->_helper = new Zend_Controller_Action_HelperBroker($this);
$this->_helper->addPath('../application/controllers/helpers');
// when noInit is set (e.g. for testing), authentication and init is skipped
if (isset($invokeArgs['noInit'])) {
// TODO: Find out whether this still makes sense?
return;
}
if ($this->_request->isXmlHttpRequest()) {
$this->windowId = $this->_request->getHeader('X-Icinga-WindowId', null);
}
if ($this->requiresLogin() === false) {
$this->view->tabs = new Tabs();
$this->init();
} else {
$url = $this->getRequestUrl();
if ($url === 'default/index/index') {
// TODO: We need our own router :p
$url = 'dashboard';
if ($this->requiresConfig() === false) {
if ($this->requiresLogin() === false) {
$this->view->tabs = new Tabs();
$this->init();
} else {
$url = $this->getRequestUrl();
if ($url === 'default/index/index') {
// TODO: We need our own router :p
$url = 'dashboard';
}
$this->redirectToLogin($url);
}
$this->redirectToLogin($url);
} else {
$this->redirectNow(Url::fromPath('install'));
}
}
@ -224,11 +230,39 @@ class ActionController extends Zend_Controller_Action
}
}
/**
* Check whether the controller requires configuration. That is when no configuration
* is available and when it is possible to setup the configuration
*
* @return bool
*
* @see requiresConfiguration
*/
protected function requiresConfig()
{
if (!$this->requiresConfiguration) {
return false;
}
if (file_exists(Config::$configDir . '/setup.token')) {
try {
$config = Config::app()->toArray();
} catch (NotReadableError $e) {
return true;
}
return empty($config);
} else {
return false;
}
}
/**
* Check whether the controller requires a login. That is when the controller requires authentication and the
* user is currently not authenticated
*
* @return bool
*
* @see requiresAuthentication
*/
protected function requiresLogin()

View File

@ -127,6 +127,15 @@ class Form extends Zend_Form
*/
protected $last_note_id = 0;
/**
* Whether buttons are shown or not
*
* This is just a q&d solution and MUST NOT survive any refactoring!
*
* @var bool
*/
protected $buttonsHidden = false;
/**
* Getter for the session ID
*
@ -279,11 +288,11 @@ class Form extends Zend_Form
$this->initCsrfToken();
$this->create();
if ($this->submitLabel) {
if (!$this->buttonsHidden && $this->submitLabel) {
$this->addSubmitButton();
}
if ($this->cancelLabel) {
if (!$this->buttonsHidden && $this->cancelLabel) {
$this->addCancelButton();
}
@ -596,4 +605,18 @@ class Form extends Zend_Form
return $this;
}
public function hideButtons()
{
$this->buttonsHidden = true;
}
/**
* q&d solution to be able to recreate a form
*/
public function reset()
{
$this->created = false;
$this->clearElements();
}
}

View File

@ -22,6 +22,7 @@ class StyleSheet
'css/icinga/monitoring-colors.less',
'css/icinga/selection-toolbar.less',
'css/icinga/login.less',
'css/icinga/install.less',
);
public static function compileForPdf()

View File

@ -463,6 +463,25 @@ class Url
return $this;
}
/**
* Shift a query parameter from this URL if it exists, otherwise $default
*
* @param string $param Parameter name
* @param mixed $default Default value in case $param does not exist
*
* @return mixed
*/
public function shift($param, $default = null)
{
if (isset($this->params[$param])) {
$ret = $this->params[$param];
unset($this->params[$param]);
} else {
$ret = $default;
}
return $ret;
}
/**
* Return a copy of this url without the parameter given
*

View File

@ -0,0 +1,93 @@
<?php
// {{{ICINGA_LICENSE_HEADER}}}
// {{{ICINGA_LICENSE_HEADER}}}
namespace Icinga\Web\Wizard;
use Icinga\Web\Form;
class Page extends Form
{
/**
* Whether a CSRF token should not be added to this wizard page
*
* @var bool
*/
protected $tokenDisabled = true;
/**
* The wizard this page is part of
*
* @var Wizard
*/
protected $wizard;
/**
* The title of this wizard page
*
* @var string
*/
protected $title = '';
/**
* Create a new wizard page
*
* @param Wizard $wizard The wizard this page is part of
* @param mixed $options Zend_Form options
*/
public function __construct(Wizard $wizard = null, $options = null)
{
parent::__construct($options);
$this->wizard = $wizard;
}
/**
* Overwrite this to initialize this wizard page
*/
public function init()
{
}
/**
* Return whether this page needs to be shown to the user
*
* Overwrite this to add page specific handling
*
* @return bool
*/
public function isRequired()
{
return true;
}
/**
* Set the title for this wizard page
*
* @param string $title The title to set
*/
public function setTitle($title)
{
$this->title = $title;
}
/**
* Return the title of this wizard page
*
* @return string
*/
public function getTitle()
{
return $this->title;
}
/**
* Return a config containing all values provided by the user
*
* @return Zend_Config
*/
public function getConfig()
{
return $this->getConfiguration();
}
}

View File

@ -0,0 +1,385 @@
<?php
// {{{ICINGA_LICENSE_HEADER}}}
// {{{ICINGA_LICENSE_HEADER}}}
namespace Icinga\Web\Wizard;
use Zend_Config;
use Icinga\Web\Form;
use Icinga\Exception\ProgrammingError;
/**
* Multistep form with support for nesting and dynamic behaviour
*
* @todo Pages that were displayed initially and filled out by the user remain
* currently in the configuration returned by Wizard::getConfig()
*/
class Wizard extends Page
{
/**
* Whether this wizard has been completed
*
* @var bool
*/
protected $finished = false;
/**
* The wizard pages
*
* @var array
*/
protected $pages = array();
/**
* Return the wizard pages
*
* @return array
*/
public function getPages()
{
return array_filter($this->pages, function ($page) { return $page->isRequired(); });
}
/**
* Return a page by its name or null if it's not found
*
* @param string $pageName The name of the page
*
* @return Page|null
*/
public function getPage($pageName)
{
$candidates = array_filter(
$this->pages, // Cannot use getPages() here because I might get called as part of Page::isRequired()
function ($page) use ($pageName) { return $page->getName() === $pageName; }
);
if (!empty($candidates)) {
return array_shift($candidates);
} elseif ($this->wizard !== null) {
return $this->wizard->getPage($pageName);
}
}
/**
* Add a new page to this wizard
*
* @param Page $page The page to add
*/
public function addPage(Page $page)
{
if (!($pageName = $page->getName())) {
throw new ProgrammingError('Wizard page "' . get_class($page) . '" has no unique name');
}
$wizardConfig = $this->getConfig();
if ($wizardConfig->get($pageName) === null) {
$wizardConfig->{$pageName} = new Zend_Config(array(), true);
}
$page->setConfiguration($wizardConfig->{$pageName});
$page->setRequest($this->getRequest());
$page->setTokenDisabled(); // Usually default for pages, but not for wizards
$this->pages[] = $page;
}
/**
* Add multiple pages to this wizard
*
* The given array's keys are titles and its values are class names to add
* as wizard pages. An array as value causes a sub-wizard being added.
*
* @param array $pages The pages to add to the wizard
*/
public function addPages(array $pages)
{
foreach ($pages as $title => $pageClassOrArray) {
if (is_array($pageClassOrArray)) {
$wizard = new static($this);
$wizard->setTitle($title);
$this->addPage($wizard);
$wizard->addPages($pageClassOrArray);
} else {
$page = new $pageClassOrArray($this);
$page->setTitle($title);
$this->addPage($page);
}
}
}
/**
* Return this wizard's progress
*
* @param int $default The step to return in case this wizard has no progress information yet
*
* @return int The current step
*/
public function getProgress($default = 0)
{
return $this->getConfig()->get('progress', $default);
}
/**
* Set this wizard's progress
*
* @param int $step The current step
*/
public function setProgress($step)
{
$config = $this->getConfig();
$config->progress = $step;
}
/**
* Return the current page
*
* @return Page
*
* @throws ProgrammingError In case there are not any pages registered
*/
public function getCurrentPage()
{
$pages = $this->getPages();
if (empty($pages)) {
throw new ProgrammingError('This wizard has no pages');
}
return $pages[$this->getProgress()];
}
/**
* Return whether the given page is the current page
*
* @param Page $page The page to check
*
* @return bool
*/
public function isCurrentPage(Page $page)
{
return $this->getCurrentPage() === $page;
}
/**
* Return whether the given page is the first page in the wizard
*
* @param Page $page The page to check
*
* @return bool
*
* @throws ProgrammingError In case there are not any pages registered
*/
public function isFirstPage(Page $page)
{
$pages = $this->getPages();
if (empty($pages)) {
throw new ProgrammingError('This wizard has no pages');
}
return $pages[0] === $page;
}
/**
* Return whether the given page has been completed
*
* @param Page $page The page to check
*
* @return bool
*
* @throws ProgrammingError In case there are not any pages registered
*/
public function isCompletedPage(Page $page)
{
$pages = $this->getPages();
if (empty($pages)) {
throw new ProgrammingError('This wizard has no pages');
}
return $this->isFinished() || array_search($page, $pages, true) < $this->getProgress();
}
/**
* Return whether the given page is the last page in the wizard
*
* @param Page $page The page to check
*
* @return bool
*
* @throws ProgrammingError In case there are not any pages registered
*/
public function isLastPage(Page $page)
{
$pages = $this->getPages();
if (empty($pages)) {
throw new ProgrammingError('This wizard has no pages');
}
return $pages[count($pages) - 1] === $page;
}
/**
* Return whether this wizard has been completed
*
* @return bool
*/
public function isFinished()
{
return $this->finished && $this->isLastPage($this->getCurrentPage());
}
/**
* Return whether the given page is a wizard
*
* @param Page $page The page to check
*
* @return bool
*/
public function isWizard(Page $page)
{
return $page instanceof self;
}
/**
* Return whether either the back- or next-button was clicked
*
* @see Form::isSubmitted()
*/
public function isSubmitted()
{
$checkData = $this->getRequest()->getParams();
return isset($checkData['btn_return']) || isset($checkData['btn_advance']);
}
/**
* Update the wizard's progress
*
* @param bool $lastStepIsLast Whether the last step of this wizard is actually the very last one
*/
public function navigate($lastStepIsLast = true)
{
$currentPage = $this->getCurrentPage();
if (($pageName = $this->getRequest()->getParam('btn_advance'))) {
if (!$this->isWizard($currentPage) || $currentPage->navigate(false) || $currentPage->isFinished()) {
if ($this->isLastPage($currentPage) && (!$lastStepIsLast || $pageName === 'install')) {
$this->finished = true;
} else {
$pages = $this->getPages();
$newStep = $this->getProgress() + 1;
if (isset($pages[$newStep]) && $pages[$newStep]->getName() === $pageName) {
$this->setProgress($newStep);
$this->reset();
}
}
}
} elseif (($pageName = $this->getRequest()->getParam('btn_return'))) {
if ($this->isWizard($currentPage) && $currentPage->getProgress() > 0) {
$currentPage->navigate(false);
} elseif (!$this->isFirstPage($currentPage)) {
$pages = $this->getPages();
$newStep = $this->getProgress() - 1;
if ($pages[$newStep]->getName() === $pageName) {
$this->setProgress($newStep);
$this->reset();
}
}
}
$config = $this->getConfig();
$config->{$currentPage->getName()} = $currentPage->getConfig();
}
/**
* Setup the current wizard page
*/
protected function create()
{
$currentPage = $this->getCurrentPage();
if ($this->isWizard($currentPage)) {
$this->createWizard($currentPage);
} else {
$this->createPage($currentPage);
}
}
/**
* Display the given page as this wizard's current page
*
* @param Page $page The page
*/
protected function createPage(Page $page)
{
$pages = $this->getPages();
$currentStep = $this->getProgress();
$page->buildForm(); // Needs to get called manually as it's nothing that Zend knows about
$this->addSubForm($page, $page->getName());
if (!$this->isFirstPage($page)) {
$this->addElement(
'button',
'btn_return',
array(
'type' => 'submit',
'label' => t('Previous'),
'value' => $pages[$currentStep - 1]->getName()
)
);
}
$this->addElement(
'button',
'btn_advance',
array(
'type' => 'submit',
'label' => $this->isLastPage($page) ? t('Install') : t('Next'),
'value' => $this->isLastPage($page) ? 'install' : $pages[$currentStep + 1]->getName()
)
);
}
/**
* Display the current page of the given wizard as this wizard's current page
*
* @param Wizard $wizard The wizard
*/
protected function createWizard(Wizard $wizard)
{
$isFirstPage = $this->isFirstPage($wizard);
$isLastPage = $this->isLastPage($wizard);
$currentSubPage = $wizard->getCurrentPage();
$isFirstSubPage = $wizard->isFirstPage($currentSubPage);
$isLastSubPage = $wizard->isLastPage($currentSubPage);
$currentSubPage->buildForm(); // Needs to get called manually as it's nothing that Zend knows about
$this->addSubForm($currentSubPage, $currentSubPage->getName());
if (!$isFirstPage || !$isFirstSubPage) {
$pages = $isFirstSubPage ? $this->getPages() : $wizard->getPages();
$currentStep = $isFirstSubPage ? $this->getProgress() : $wizard->getProgress();
$this->addElement(
'button',
'btn_return',
array(
'type' => 'submit',
'label' => t('Previous'),
'value' => $pages[$currentStep - 1]->getName()
)
);
}
$pages = $isLastSubPage ? $this->getPages() : $wizard->getPages();
$currentStep = $isLastSubPage ? $this->getProgress() : $wizard->getProgress();
$this->addElement(
'button',
'btn_advance',
array(
'type' => 'submit',
'label' => $isLastPage && $isLastSubPage ? t('Install') : t('Next'),
'value' => $isLastPage && $isLastSubPage ? 'install' : $pages[$currentStep + 1]->getName()
)
);
}
}

View File

@ -29,6 +29,9 @@ class Parsedown
function text($text)
{
# make sure no definitions are set
$this->Definitions = array();
# standardize line breaks
$text = str_replace("\r\n", "\n", $text);
$text = str_replace("\r", "\n", $text);
@ -48,9 +51,6 @@ class Parsedown
# trim line breaks
$markup = trim($markup, "\n");
# clean up
$this->definitions = array();
return $markup;
}
@ -58,6 +58,8 @@ class Parsedown
# Setters
#
private $breaksEnabled;
function setBreaksEnabled($breaksEnabled)
{
$this->breaksEnabled = $breaksEnabled;
@ -65,13 +67,11 @@ class Parsedown
return $this;
}
private $breaksEnabled;
#
# Blocks
# Lines
#
protected $blockMarkers = array(
protected $BlockTypes = array(
'#' => array('Atx'),
'*' => array('Rule', 'List'),
'+' => array('List'),
@ -87,24 +87,31 @@ class Parsedown
'8' => array('List'),
'9' => array('List'),
':' => array('Table'),
'<' => array('Markup'),
'<' => array('Comment', 'Markup'),
'=' => array('Setext'),
'>' => array('Quote'),
'[' => array('Reference'),
'_' => array('Rule'),
'`' => array('FencedCode'),
'|' => array('Table'),
'~' => array('FencedCode'),
);
protected $definitionMarkers = array(
# ~
protected $DefinitionTypes = array(
'[' => array('Reference'),
);
# ~
protected $unmarkedBlockTypes = array(
'CodeBlock',
);
#
# Blocks
#
private function lines(array $lines)
{
$CurrentBlock = null;
@ -134,7 +141,7 @@ class Parsedown
$Line = array('body' => $line, 'indent' => $indent, 'text' => $text);
# Multiline block types define "addTo" methods.
# ~
if (isset($CurrentBlock['incomplete']))
{
@ -161,17 +168,15 @@ class Parsedown
$marker = $text[0];
# Definitions
if (isset($this->definitionMarkers[$marker]))
if (isset($this->DefinitionTypes[$marker]))
{
foreach ($this->definitionMarkers[$marker] as $definitionType)
foreach ($this->DefinitionTypes[$marker] as $definitionType)
{
$Definition = $this->{'identify'.$definitionType}($Line, $CurrentBlock);
if (isset($Definition))
{
$this->definitions[$definitionType][$Definition['id']] = $Definition['data'];
$this->Definitions[$definitionType][$Definition['id']] = $Definition['data'];
continue 2;
}
@ -182,9 +187,9 @@ class Parsedown
$blockTypes = $this->unmarkedBlockTypes;
if (isset($this->blockMarkers[$marker]))
if (isset($this->BlockTypes[$marker]))
{
foreach ($this->blockMarkers[$marker] as $blockType)
foreach ($this->BlockTypes[$marker] as $blockType)
{
$blockTypes []= $blockType;
}
@ -195,23 +200,19 @@ class Parsedown
foreach ($blockTypes as $blockType)
{
# Block types define "identify" methods.
$Block = $this->{'identify'.$blockType}($Line, $CurrentBlock);
if (isset($Block))
{
$Block['type'] = $blockType;
if ( ! isset($Block['identified'])) # »
if ( ! isset($Block['identified']))
{
$Elements []= $CurrentBlock['element'];
$Block['identified'] = true;
}
# Multiline block types define "addTo" methods.
if (method_exists($this, 'addTo'.$blockType))
{
$Block['incomplete'] = true;
@ -225,7 +226,7 @@ class Parsedown
# ~
if ($CurrentBlock['type'] === 'Paragraph' and ! isset($CurrentBlock['interrupted']))
if (isset($CurrentBlock) and ! isset($CurrentBlock['type']) and ! isset($CurrentBlock['interrupted']))
{
$CurrentBlock['element']['text'] .= "\n".$text;
}
@ -233,15 +234,9 @@ class Parsedown
{
$Elements []= $CurrentBlock['element'];
$CurrentBlock = array(
'type' => 'Paragraph',
'identified' => true,
'element' => array(
'name' => 'p',
'text' => $text,
'handler' => 'line',
),
);
$CurrentBlock = $this->buildParagraph($Line);
$CurrentBlock['identified'] = true;
}
}
@ -296,15 +291,22 @@ class Parsedown
}
#
# Rule
# Code
protected function identifyRule($Line)
protected function identifyCodeBlock($Line)
{
if (preg_match('/^(['.$Line['text'][0].'])([ ]{0,2}\1){2,}[ ]*$/', $Line['text']))
if ($Line['indent'] >= 4)
{
$text = substr($Line['body'], 4);
$Block = array(
'element' => array(
'name' => 'hr'
'name' => 'pre',
'handler' => 'element',
'text' => array(
'name' => 'code',
'text' => $text,
),
),
);
@ -312,104 +314,72 @@ class Parsedown
}
}
#
# Reference
protected function identifyReference($Line)
protected function addToCodeBlock($Line, $Block)
{
if (preg_match('/^\[(.+?)\]:[ ]*<?(\S+?)>?(?:[ ]+["\'(](.+)["\')])?[ ]*$/', $Line['text'], $matches))
if ($Line['indent'] >= 4)
{
$Definition = array(
'id' => strtolower($matches[1]),
'data' => array(
'url' => $matches[2],
),
);
if (isset($matches[3]))
if (isset($Block['interrupted']))
{
$Definition['data']['title'] = $matches[3];
$Block['element']['text']['text'] .= "\n";
unset($Block['interrupted']);
}
return $Definition;
}
}
$Block['element']['text']['text'] .= "\n";
#
# Setext
$text = substr($Line['body'], 4);
protected function identifySetext($Line, array $Block = null)
{
if ( ! isset($Block) or $Block['type'] !== 'Paragraph' or isset($Block['interrupted']))
{
return;
}
if (chop($Line['text'], $Line['text'][0]) === '')
{
$Block['element']['name'] = $Line['text'][0] === '=' ? 'h1' : 'h2';
$Block['element']['text']['text'] .= $text;
return $Block;
}
}
#
# Markup
protected function identifyMarkup($Line)
protected function completeCodeBlock($Block)
{
if (preg_match('/^<(\w[\w\d]*)(?:[ ][^>\/]*)?(\/?)[ ]*>/', $Line['text'], $matches))
{
if (in_array($matches[1], $this->textLevelElements))
{
return;
}
$text = $Block['element']['text']['text'];
$text = htmlspecialchars($text, ENT_NOQUOTES, 'UTF-8');
$Block['element']['text']['text'] = $text;
return $Block;
}
#
# Comment
protected function identifyComment($Line)
{
if (isset($Line['text'][3]) and $Line['text'][3] === '-' and $Line['text'][2] === '-' and $Line['text'][1] === '!')
{
$Block = array(
'element' => $Line['body'],
);
if ($matches[2] or $matches[1] === 'hr' or preg_match('/<\/'.$matches[1].'>[ ]*$/', $Line['text']))
if (preg_match('/-->$/', $Line['text']))
{
$Block['closed'] = true;
}
else
{
$Block['depth'] = 0;
$Block['start'] = '<'.$matches[1].'>';
$Block['end'] = '</'.$matches[1].'>';
}
return $Block;
}
}
protected function addToMarkup($Line, array $Block)
protected function addToComment($Line, array $Block)
{
if (isset($Block['closed']))
{
return;
}
if (stripos($Line['text'], $Block['start']) !== false) # opening tag
{
$Block['depth'] ++;
}
$Block['element'] .= "\n" . $Line['body'];
if (stripos($Line['text'], $Block['end']) !== false) # closing tag
if (preg_match('/-->$/', $Line['text']))
{
if ($Block['depth'] > 0)
{
$Block['depth'] --;
}
else
{
$Block['closed'] = true;
}
$Block['closed'] = true;
}
$Block['element'] .= "\n".$Line['body'];
return $Block;
}
@ -610,12 +580,106 @@ class Parsedown
}
}
#
# Rule
protected function identifyRule($Line)
{
if (preg_match('/^(['.$Line['text'][0].'])([ ]{0,2}\1){2,}[ ]*$/', $Line['text']))
{
$Block = array(
'element' => array(
'name' => 'hr'
),
);
return $Block;
}
}
#
# Setext
protected function identifySetext($Line, array $Block = null)
{
if ( ! isset($Block) or isset($Block['type']) or isset($Block['interrupted']))
{
return;
}
if (chop($Line['text'], $Line['text'][0]) === '')
{
$Block['element']['name'] = $Line['text'][0] === '=' ? 'h1' : 'h2';
return $Block;
}
}
#
# Markup
protected function identifyMarkup($Line)
{
if (preg_match('/^<(\w[\w\d]*)(?:[ ][^>\/]*)?(\/?)[ ]*>/', $Line['text'], $matches))
{
if (in_array($matches[1], $this->textLevelElements))
{
return;
}
$Block = array(
'element' => $Line['body'],
);
if ($matches[2] or $matches[1] === 'hr' or preg_match('/<\/'.$matches[1].'>[ ]*$/', $Line['text']))
{
$Block['closed'] = true;
}
else
{
$Block['depth'] = 0;
$Block['name'] = $matches[1];
}
return $Block;
}
}
protected function addToMarkup($Line, array $Block)
{
if (isset($Block['closed']))
{
return;
}
if (preg_match('/<'.$Block['name'].'([ ][^\/]+)?>/', $Line['text'])) # opening tag
{
$Block['depth'] ++;
}
if (stripos($Line['text'], '</'.$Block['name'].'>') !== false) # closing tag
{
if ($Block['depth'] > 0)
{
$Block['depth'] --;
}
else
{
$Block['closed'] = true;
}
}
$Block['element'] .= "\n".$Line['body'];
return $Block;
}
#
# Table
protected function identifyTable($Line, array $Block = null)
{
if ( ! isset($Block) or $Block['type'] !== 'Paragraph' or isset($Block['interrupted']))
if ( ! isset($Block) or isset($Block['type']) or isset($Block['interrupted']))
{
return;
}
@ -766,57 +830,42 @@ class Parsedown
}
#
# Code
# Definitions
#
protected function identifyCodeBlock($Line)
protected function identifyReference($Line)
{
if ($Line['indent'] >= 4)
if (preg_match('/^\[(.+?)\]:[ ]*<?(\S+?)>?(?:[ ]+["\'(](.+)["\')])?[ ]*$/', $Line['text'], $matches))
{
$text = substr($Line['body'], 4);
$Block = array(
'element' => array(
'name' => 'pre',
'handler' => 'element',
'text' => array(
'name' => 'code',
'text' => $text,
),
$Definition = array(
'id' => strtolower($matches[1]),
'data' => array(
'url' => $matches[2],
),
);
return $Block;
}
}
protected function addToCodeBlock($Line, $Block)
{
if ($Line['indent'] >= 4)
{
if (isset($Block['interrupted']))
if (isset($matches[3]))
{
$Block['element']['text']['text'] .= "\n";
unset($Block['interrupted']);
$Definition['data']['title'] = $matches[3];
}
$Block['element']['text']['text'] .= "\n";
$text = substr($Line['body'], 4);
$Block['element']['text']['text'] .= $text;
return $Block;
return $Definition;
}
}
protected function completeCodeBlock($Block)
#
# ~
#
protected function buildParagraph($Line)
{
$text = $Block['element']['text']['text'];
$text = htmlspecialchars($text, ENT_NOQUOTES, 'UTF-8');
$Block['element']['text']['text'] = $text;
$Block = array(
'element' => array(
'name' => 'p',
'text' => $Line['text'],
'handler' => 'line',
),
);
return $Block;
}
@ -825,7 +874,7 @@ class Parsedown
# ~
#
private function element(array $Element)
protected function element(array $Element)
{
$markup = '<'.$Element['name'];
@ -860,7 +909,7 @@ class Parsedown
return $markup;
}
private function elements(array $Elements)
protected function elements(array $Elements)
{
$markup = '';
@ -873,7 +922,7 @@ class Parsedown
$markup .= "\n";
if (is_string($Element)) # because of markup
if (is_string($Element)) # because of Markup
{
$markup .= $Element;
@ -892,7 +941,7 @@ class Parsedown
# Spans
#
protected $spanMarkers = array(
protected $SpanTypes = array(
'!' => array('Link'), # ?
'&' => array('Ampersand'),
'*' => array('Emphasis'),
@ -905,8 +954,14 @@ class Parsedown
'\\' => array('EscapeSequence'),
);
# ~
protected $spanMarkerList = '*_!&[</`~\\';
#
# ~
#
public function line($text)
{
$markup = '';
@ -915,17 +970,19 @@ class Parsedown
$markerPosition = 0;
while ($markedExcerpt = strpbrk($remainder, $this->spanMarkerList))
while ($excerpt = strpbrk($remainder, $this->spanMarkerList))
{
$marker = $markedExcerpt[0];
$marker = $excerpt[0];
$markerPosition += strpos($remainder, $marker);
foreach ($this->spanMarkers[$marker] as $spanType)
$Excerpt = array('text' => $excerpt, 'context' => $text);
foreach ($this->SpanTypes[$marker] as $spanType)
{
$handler = 'identify'.$spanType;
$Span = $this->$handler($markedExcerpt, $text);
$Span = $this->$handler($Excerpt);
if ( ! isset($Span))
{
@ -950,7 +1007,7 @@ class Parsedown
$markup .= $this->readPlainText($plainText);
$markup .= isset($Span['element']) ? $this->element($Span['element']) : $Span['markup'];
$markup .= isset($Span['markup']) ? $Span['markup'] : $this->element($Span['element']);
$text = substr($text, $Span['position'] + $Span['extent']);
@ -961,7 +1018,7 @@ class Parsedown
continue 2;
}
$remainder = substr($markedExcerpt, 1);
$remainder = substr($excerpt, 1);
$markerPosition ++;
}
@ -975,14 +1032,14 @@ class Parsedown
# ~
#
protected function identifyUrl($excerpt, $text)
protected function identifyUrl($Excerpt)
{
if ( ! isset($excerpt[1]) or $excerpt[1] !== '/')
if ( ! isset($Excerpt['text'][1]) or $Excerpt['text'][1] !== '/')
{
return;
}
if (preg_match('/\bhttps?:[\/]{2}[^\s]+\b\/*/ui', $text, $matches, PREG_OFFSET_CAPTURE))
if (preg_match('/\bhttps?:[\/]{2}[^\s<]+\b\/*/ui', $Excerpt['context'], $matches, PREG_OFFSET_CAPTURE))
{
$url = str_replace(array('&', '<'), array('&amp;', '&lt;'), $matches[0][0]);
@ -1000,9 +1057,9 @@ class Parsedown
}
}
protected function identifyAmpersand($excerpt)
protected function identifyAmpersand($Excerpt)
{
if ( ! preg_match('/^&#?\w+;/', $excerpt))
if ( ! preg_match('/^&#?\w+;/', $Excerpt['text']))
{
return array(
'markup' => '&amp;',
@ -1011,14 +1068,14 @@ class Parsedown
}
}
protected function identifyStrikethrough($excerpt)
protected function identifyStrikethrough($Excerpt)
{
if ( ! isset($excerpt[1]))
if ( ! isset($Excerpt['text'][1]))
{
return;
}
if ($excerpt[1] === $excerpt[0] and preg_match('/^~~(?=\S)(.+?)(?<=\S)~~/', $excerpt, $matches))
if ($Excerpt['text'][1] === '~' and preg_match('/^~~(?=\S)(.+?)(?<=\S)~~/', $Excerpt['text'], $matches))
{
return array(
'extent' => strlen($matches[0]),
@ -1031,12 +1088,12 @@ class Parsedown
}
}
protected function identifyEscapeSequence($excerpt)
protected function identifyEscapeSequence($Excerpt)
{
if (in_array($excerpt[1], $this->specialCharacters))
if (isset($Excerpt['text'][1]) and in_array($Excerpt['text'][1], $this->specialCharacters))
{
return array(
'markup' => $excerpt[1],
'markup' => $Excerpt['text'][1],
'extent' => 2,
);
}
@ -1050,9 +1107,9 @@ class Parsedown
);
}
protected function identifyUrlTag($excerpt)
protected function identifyUrlTag($Excerpt)
{
if (strpos($excerpt, '>') !== false and preg_match('/^<(https?:[\/]{2}[^\s]+?)>/i', $excerpt, $matches))
if (strpos($Excerpt['text'], '>') !== false and preg_match('/^<(https?:[\/]{2}[^\s]+?)>/i', $Excerpt['text'], $matches))
{
$url = str_replace(array('&', '<'), array('&amp;', '&lt;'), $matches[1]);
@ -1069,9 +1126,9 @@ class Parsedown
}
}
protected function identifyEmailTag($excerpt)
protected function identifyEmailTag($Excerpt)
{
if (strpos($excerpt, '>') !== false and preg_match('/^<(\S+?@\S+?)>/', $excerpt, $matches))
if (strpos($Excerpt['text'], '>') !== false and preg_match('/^<(\S+?@\S+?)>/', $Excerpt['text'], $matches))
{
return array(
'extent' => strlen($matches[0]),
@ -1086,9 +1143,9 @@ class Parsedown
}
}
protected function identifyTag($excerpt)
protected function identifyTag($Excerpt)
{
if (strpos($excerpt, '>') !== false and preg_match('/^<\/?\w.*?>/', $excerpt, $matches))
if (strpos($Excerpt['text'], '>') !== false and preg_match('/^<\/?\w.*?>/', $Excerpt['text'], $matches))
{
return array(
'markup' => $matches[0],
@ -1097,11 +1154,11 @@ class Parsedown
}
}
protected function identifyInlineCode($excerpt)
protected function identifyInlineCode($Excerpt)
{
$marker = $excerpt[0];
$marker = $Excerpt['text'][0];
if (preg_match('/^('.$marker.'+)[ ]*(.+?)[ ]*(?<!'.$marker.')\1(?!'.$marker.')/', $excerpt, $matches))
if (preg_match('/^('.$marker.'+)[ ]*(.+?)[ ]*(?<!'.$marker.')\1(?!'.$marker.')/', $Excerpt['text'], $matches))
{
$text = $matches[2];
$text = htmlspecialchars($text, ENT_NOQUOTES, 'UTF-8');
@ -1116,25 +1173,25 @@ class Parsedown
}
}
protected function identifyLink($excerpt)
protected function identifyLink($Excerpt)
{
$extent = $excerpt[0] === '!' ? 1 : 0;
$extent = $Excerpt['text'][0] === '!' ? 1 : 0;
if (strpos($excerpt, ']') and preg_match('/\[((?:[^][]|(?R))*)\]/', $excerpt, $matches))
if (strpos($Excerpt['text'], ']') and preg_match('/\[((?:[^][]|(?R))*)\]/', $Excerpt['text'], $matches))
{
$Link = array('text' => $matches[1], 'label' => strtolower($matches[1]));
$extent += strlen($matches[0]);
$substring = substr($excerpt, $extent);
$substring = substr($Excerpt['text'], $extent);
if (preg_match('/^\s*\[(.+?)\]/', $substring, $matches))
if (preg_match('/^\s*\[([^][]+)\]/', $substring, $matches))
{
$Link['label'] = strtolower($matches[1]);
if (isset($this->definitions['Reference'][$Link['label']]))
if (isset($this->Definitions['Reference'][$Link['label']]))
{
$Link += $this->definitions['Reference'][$Link['label']];
$Link += $this->Definitions['Reference'][$Link['label']];
$extent += strlen($matches[0]);
}
@ -1143,9 +1200,9 @@ class Parsedown
return;
}
}
elseif (isset($this->definitions['Reference'][$Link['label']]))
elseif (isset($this->Definitions['Reference'][$Link['label']]))
{
$Link += $this->definitions['Reference'][$Link['label']];
$Link += $this->Definitions['Reference'][$Link['label']];
if (preg_match('/^[ ]*\[\]/', $substring, $matches))
{
@ -1175,7 +1232,7 @@ class Parsedown
$url = str_replace(array('&', '<'), array('&amp;', '&lt;'), $Link['url']);
if ($excerpt[0] === '!')
if ($Excerpt['text'][0] === '!')
{
$Element = array(
'name' => 'img',
@ -1208,20 +1265,20 @@ class Parsedown
);
}
protected function identifyEmphasis($excerpt)
protected function identifyEmphasis($Excerpt)
{
if ( ! isset($excerpt[1]))
if ( ! isset($Excerpt['text'][1]))
{
return;
}
$marker = $excerpt[0];
$marker = $Excerpt['text'][0];
if ($excerpt[1] === $marker and preg_match($this->strongRegex[$marker], $excerpt, $matches))
if ($Excerpt['text'][1] === $marker and preg_match($this->StrongRegex[$marker], $Excerpt['text'], $matches))
{
$emphasis = 'strong';
}
elseif (preg_match($this->emRegex[$marker], $excerpt, $matches))
elseif (preg_match($this->EmRegex[$marker], $Excerpt['text'], $matches))
{
$emphasis = 'em';
}
@ -1313,7 +1370,7 @@ class Parsedown
# Fields
#
protected $definitions;
protected $Definitions;
#
# Read-only
@ -1322,12 +1379,12 @@ class Parsedown
'\\', '`', '*', '_', '{', '}', '[', ']', '(', ')', '>', '#', '+', '-', '.', '!',
);
protected $strongRegex = array(
protected $StrongRegex = array(
'*' => '/^[*]{2}((?:[^*]|[*][^*]*[*])+?)[*]{2}(?![*])/s',
'_' => '/^__((?:[^_]|_[^_]*_)+?)__(?!_)/us',
);
protected $emRegex = array(
protected $EmRegex = array(
'*' => '/^[*]((?:[^*]|[*][*][^*]+?[*][*])+?)[*](?![*])/s',
'_' => '/^_((?:[^_]|__[^_]*__)+?)_(?!_)\b/us',
);

View File

@ -1,4 +1,4 @@
RELEASE=1.0.0-rc.4
RELEASE=1.0.0
FILENAME=parsedown-$RELEASE
DESTINATION=.
wget -O ${FILENAME}.tar.gz https://github.com/erusev/parsedown/archive/${RELEASE}.tar.gz

View File

@ -266,7 +266,7 @@ def("DOMPDF_ENABLE_PHP", false);
*
* @var bool
*/
def("DOMPDF_ENABLE_JAVASCRIPT", true);
def("DOMPDF_ENABLE_JAVASCRIPT", false;
/**
* Enable remote file access
@ -285,7 +285,7 @@ def("DOMPDF_ENABLE_JAVASCRIPT", true);
*
* @var bool
*/
def("DOMPDF_ENABLE_REMOTE", false);
def("DOMPDF_ENABLE_REMOTE", true);
/**
* The debug output log

View File

@ -58,8 +58,7 @@ class Monitoring_ShowController extends Controller
{
if ($this->getRequest()->getActionName() === 'host') {
$this->view->object = new Host($this->getRequest());
} elseif ($this->getRequest()->getActionName() === 'service'
|| $this->getRequest()->getActionName() === 'services' ) {
} elseif ($this->getRequest()->getActionName() === 'service') {
$this->view->object = new Service($this->getRequest());
} else {
// TODO: Well... this could be done better

View File

@ -1,9 +1,7 @@
<div class="controls">
<?= $this->tabs->render($this); ?>
<div style="margin: 1em" class="dontprint">
<!--<?= $this->filterBox->render($this); ?>-->
Sort by <?= $this->sortControl->render($this); ?>
<!--<?= $this->selectionToolbar('single'); ?>-->
</div>
<?= $this->paginationControl($history, null, null, array('preserve' => $this->preserve)); ?>
</div>

View File

@ -2,7 +2,7 @@
<div class="controls">
<?= $this->tabs; ?>
<div style="margin: 1em;" class="dontprint">
<!--<?= $this->filterBox; ?>-->Sort by <?= $this->sortControl->render($this); ?>
<!--<?= $this->filterBox ?>-->Sort by <?= $this->sortControl ?>
</div>
<?= $this->partial(
'pivottablePagination.phtml',
@ -15,7 +15,7 @@
</div>
<?php endif ?>
<div class="content" data-base-target="_next">
<table class="pivot servicestates">
<table class="pivot servicestates">
<?php
$hasHeader = false;
$pivotData = $this->pivot->toArray();
@ -23,57 +23,57 @@ $hostFilter = implode(',', array_keys($pivotData));
?>
<?php foreach ($pivotData as $host_name => $serviceStates): ?>
<?php if (!$hasHeader): ?>
<thead>
<tr>
<th>&nbsp;</th>
<th colspan="<?= count($serviceStates); ?>">
<div>
<thead>
<tr>
<th>&nbsp;</th>
<th colspan="<?= count($serviceStates); ?>">
<div>
<?php foreach (array_keys($serviceStates) as $service_description): ?>
<span>
<a href="<?= $this->href(
'monitoring/list/services',
array(
'service_description' => $service_description,
'host_name' => $hostFilter
)
); ?>">
<abbr title="<?= $service_description; ?>">
<?= strlen($service_description) > 18 ? substr($service_description, 0, 18) . '...' : $service_description; ?>
</abbr>
</a>
</span>
<span>
<a href="<?= $this->href(
'monitoring/list/services',
array(
'service_description' => $service_description,
'host_name' => $hostFilter
)
); ?>">
<abbr title="<?= $service_description; ?>"><?=
strlen($service_description) > 18 ?
substr($service_description, 0, 18) . '...' :
$service_description
?></abbr>
</a>
</span>
<?php endforeach ?>
</div>
</th>
</tr>
</thead>
<tbody>
</div>
</th>
</tr>
</thead>
<tbody>
<?php $hasHeader = true; ?>
<?php endif ?>
<tr>
<th>
<a href="<?= $this->href('monitoring/show/host', array('host' => $host_name)); ?>">
<?= $host_name; ?>
</a>
</th>
<tr>
<th>
<a href="<?=
$this->href('monitoring/show/host', array('host' => $host_name))
?>"><?= $host_name ?></a>
</th>
<?php foreach (array_values($serviceStates) as $service): ?>
<?php if ($service !== null): ?>
<td>
<a href="<?= $this->href(
'monitoring/show/service',
array(
'host' => $service->host_name,
'service' => $service->service_description
)
); ?>" title="<?= $this->escape($service->service_output); ?>" class="state_<?= $this->monitoringState($service, 'service'); ?> <?= $service->service_handled ? 'handled' : ''; ?>"></a>
<td>
<a href="<?= $this->href('monitoring/show/service', array(
'host' => $service->host_name,
'service' => $service->service_description
)) ?>" title="<?= $this->escape($service->service_output)
?>" class="state_<?= $this->monitoringState($service, 'service') ?> <?= $service->service_handled ? 'handled' : '' ?>"></a>
</td>
<?php else: ?>
<td>
&middot;
<td>&middot;</td>
<?php endif ?>
</td>
<?php endforeach ?>
</tr>
</tr>
<?php endforeach ?>
</tbody>
</table>
</tbody>
</table>
</div>

View File

@ -9,20 +9,16 @@ if (!$this->compact): ?>
Sort by <?= $this->sortControl ?>
</div>
<?= $this->paginationControl($services, null, null, array('preserve' => $this->preserve));?>
<?= $this->selectionToolbar('multi', $this->href('monitoring/multi/service', $query)); ?>
<?= $this->paginationControl($services, null, null, array('preserve' => $this->preserve)) ?>
<?= $this->selectionToolbar('multi', $this->href('monitoring/multi/service', $query)) ?>
</div>
<div class="content">
<?php endif ?>
<table
data-base-target="_next"
<table data-base-target="_next"
class="action multiselect <?php if ($this->compact): ?> compact<?php endif ?>" style="table-layout: auto;"
data-icinga-multiselect-url="<?= $this->href("/monitoring/multi/service") ?>"
data-icinga-multiselect-data="service,host"
>
data-icinga-multiselect-data="service,host">
<tbody>
<?php
@ -84,7 +80,7 @@ foreach ($services as $service):
<?php endif ?>
<?php endif ?>
<?php if ($service->service_icon_image): ?>
<?php if ($service->service_icon_image && ! preg_match('/[\'"]/', $service->service_icon_image)): ?>
<?= $this->icon($this->resolveMacros($service->service_icon_image, $service)) ?>
<?php endif ?>
<a href="<?= $serviceLink ?>"><?= $service->service_display_name ?></a><?php if ($this->showHost): ?> on <a href="<?= $hostLink ?>"><?= $service->host_name; ?>

View File

@ -0,0 +1,7 @@
<?php if (! $object->check_source) return ?>
<tr>
<th><?= $this->translate('Check Source') ?></th>
<td>
<?= $this->escape($object->check_source) ?>
</td>
</tr>

View File

@ -6,7 +6,7 @@ if ($object->is_flapping) {
'Flapping',
$this->icon('flapping.png', 'Flapping'),
sprintf(
'Currently flapping witgh a %.2f%% state change rate',
'Currently flapping with a %.2f%% state change rate',
$object->percent_state_change
)
);

View File

@ -13,6 +13,7 @@
<?= $this->render('show/components/downtime.phtml') ?>
<?= $this->render('show/components/flapping.phtml') ?>
<?= $this->render('show/components/perfdata.phtml') ?>
<?= $this->render('show/components/checksource.phtml') ?>
<?= $this->render('show/components/actions.phtml') ?>
<?= $this->render('show/components/command.phtml') ?>
<?= $this->render('show/components/hostgroups.phtml') ?>

View File

@ -13,6 +13,7 @@
<?= $this->render('show/components/downtime.phtml') ?>
<?= $this->render('show/components/flapping.phtml') ?>
<?= $this->render('show/components/perfdata.phtml') ?>
<?= $this->render('show/components/checksource.phtml') ?>
<?= $this->render('show/components/actions.phtml') ?>
<?= $this->render('show/components/command.phtml') ?>
<?= $this->render('show/components/servicegroups.phtml') ?>

View File

@ -113,9 +113,9 @@ class ContactgroupQuery extends IdoQuery
+-------------------------+-------------+------------+------------------------+
*/
$this->select->join(
// array('scg' => $this->prefix . 'service_contactgroups'),
array('scg' => $scgSub),
$this->baseQuery->distinct()->join(
array('scg' => $this->prefix . 'service_contactgroups'),
// array('scg' => $scgSub),
'scg.contactgroup_object_id = cg.contactgroup_object_id',
array()
)->join(

View File

@ -14,11 +14,23 @@ class CustomvarQuery extends IdoQuery
'service_host_name' => 'cvo.name1 COLLATE latin1_general_ci',
'service_description' => 'cvo.name2 COLLATE latin1_general_ci',
'contact_name' => 'cvo.name1 COLLATE latin1_general_ci',
'object_type' => "CASE cvo.objecttype_id WHEN 1 THEN 'host' WHEN 2 THEN 'service' WHEN 10 THEN 'contact' ELSE 'invalid' END"
'object_type' => "CASE cvo.objecttype_id WHEN 1 THEN 'host' WHEN 2 THEN 'service' WHEN 10 THEN 'contact' ELSE 'invalid' END",
'object_type_id' => 'cvo.objecttype_id'
// 'object_type' => "CASE cvo.objecttype_id WHEN 1 THEN 'host' WHEN 2 THEN 'service' WHEN 3 THEN 'hostgroup' WHEN 4 THEN 'servicegroup' WHEN 5 THEN 'hostescalation' WHEN 6 THEN 'serviceescalation' WHEN 7 THEN 'hostdependency' WHEN 8 THEN 'servicedependency' WHEN 9 THEN 'timeperiod' WHEN 10 THEN 'contact' WHEN 11 THEN 'contactgroup' WHEN 12 THEN 'command' ELSE 'other' END"
),
);
public function where($expression, $parameters = null)
{
$types = array('host' => 1, 'service' => 2, 'contact' => 10);
if ($expression === 'object_type') {
parent::where('object_type_id', $types[$parameters]);
} else {
parent::where($expression, $parameters);
}
return $this;
}
protected function joinBaseTables()
{
$this->select->from(

View File

@ -32,6 +32,8 @@ namespace Icinga\Module\Monitoring\Backend\Ido\Query;
use Icinga\Logger\Logger;
use Icinga\Data\Db\Query;
use Icinga\Exception\ProgrammingError;
use Icinga\Application\Icinga;
use Icinga\Web\Session;
/**
* Base class for Ido Queries
@ -181,6 +183,18 @@ abstract class IdoQuery extends Query
*/
protected $allowCustomVars = false;
/**
* Current IDO version. This is bullshit and needs to be moved somewhere
* else. As someone decided that we need no Backend-specific connection
* class unfortunately there is no better place right now. And as of the
* 'check_source' patch we need a quick fix immediately. So here you go.
*
* TODO: Fix this.
*
* @var string
*/
protected static $idoVersion;
/**
* Return true when the column is an aggregate column
*
@ -578,4 +592,29 @@ abstract class IdoQuery extends Query
$this->columns = $this->resolveColumns($columns);
return $this;
}
// TODO: Move this away, see note related to $idoVersion var
protected function getIdoVersion()
{
if (self::$idoVersion === null) {
$session = null;
if (Icinga::app()->isWeb()) {
// TODO: Once we have version per connection we should choose a
// namespace based on resource name
$session = Session::getSession()->getNamespace('monitoring/ido');
if (isset($session->version)) {
self::$idoVersion = $session->version;
return self::$idoVersion;
}
}
self::$idoVersion = $this->db->fetchOne(
$this->db->select()->from($this->prefix . 'dbversion', 'version')
);
if ($session !== null) {
$session->version = self::$idoVersion;
$session->write(); // <- WHY? I don't want to care about this!
}
}
return self::$idoVersion;
}
}

View File

@ -52,6 +52,7 @@ class StatusQuery extends IdoQuery
'host_output' => 'hs.output',
'host_long_output' => 'hs.long_output',
'host_perfdata' => 'hs.perfdata',
'host_check_source' => 'hs.check_source',
'host_acknowledged' => 'hs.problem_has_been_acknowledged',
'host_in_downtime' => 'CASE WHEN (hs.scheduled_downtime_depth = 0) THEN 0 ELSE 1 END',
'host_handled' => 'CASE WHEN (hs.problem_has_been_acknowledged + hs.scheduled_downtime_depth) > 0 THEN 1 ELSE 0 END',
@ -181,6 +182,7 @@ class StatusQuery extends IdoQuery
'service_output' => 'ss.output',
'service_long_output' => 'ss.long_output',
'service_perfdata' => 'ss.perfdata',
'service_check_source' => 'ss.check_source',
'service_acknowledged' => 'ss.problem_has_been_acknowledged',
'service_in_downtime' => 'CASE WHEN (ss.scheduled_downtime_depth = 0 OR ss.scheduled_downtime_depth IS NULL) THEN 0 ELSE 1 END',
'service_handled' => 'CASE WHEN (ss.problem_has_been_acknowledged + ss.scheduled_downtime_depth + COALESCE(hs.current_state, 0)) > 0 THEN 1 ELSE 0 END',
@ -303,6 +305,10 @@ class StatusQuery extends IdoQuery
protected function joinBaseTables()
{
if (version_compare($this->getIdoVersion(), '1.10.0', '<')) {
$this->columnMap['hoststatus']['host_check_source'] = '(NULL)';
$this->columnMap['servicestatus']['service_check_source'] = '(NULL)';
}
$this->select->from(array('ho' => $this->prefix . 'objects'), array())
->join(
array('hs' => $this->prefix . 'hoststatus'),

View File

@ -30,6 +30,7 @@ class StatusQuery extends StatusdatQuery
'host_output' => 'host.status.plugin_output',
'host_long_output' => 'host.status.long_plugin_output',
'host_perfdata' => 'host.status.performance_data',
'host_check_source' => 'host.status.check_source',
'host_acknowledged' => 'host.status.problem_has_been_acknowledged',
'host_last_state_change' => 'host.status.last_state_change',
'host_last_hard_state' => 'host.status.last_hard_state',
@ -82,6 +83,7 @@ class StatusQuery extends StatusdatQuery
'service_output' => 'service.status.output',
'service_long_output' => 'service.status.long_output',
'service_perfdata' => 'service.status.perfdata',
'service_check_source' => 'service.status.check_source',
'service_acknowledged' => 'service.status.problem_has_been_acknowledged',
'service_last_state_change' => 'service.status.last_state_change',
'service_check_command' => 'service.status.check_command',

View File

@ -29,8 +29,8 @@
namespace Icinga\Module\Monitoring;
use Icinga\File\Csv;
use Icinga\Web\Controller\ActionController;
use Icinga\File\Csv;
/**
* Base class for all monitoring action controller

View File

@ -62,6 +62,7 @@ class HostStatus extends DataView
'host_long_output',
'host_check_command',
'host_perfdata',
'host_check_source',
'host_passive_checks_enabled',
'host_passive_checks_enabled_changed',
'host_obsessing',

View File

@ -90,6 +90,7 @@ class ServiceStatus extends DataView
'host_ipv4',
'host_severity',
'host_perfdata',
'host_check_source',
'host_active_checks_enabled',
'host_passive_checks_enabled',
'host_last_hard_state',
@ -102,6 +103,7 @@ class ServiceStatus extends DataView
'service_hard_state',
'service_problem',
'service_perfdata',
'service_check_source',
'service_active_checks_enabled',
'service_active_checks_enabled_changed',
'service_passive_checks_enabled',

View File

@ -33,6 +33,7 @@ abstract class AbstractObject
public $customvars = array();
public $events = array();
protected $view;
private $properties = array();
private $request = null;
@ -251,11 +252,6 @@ abstract class AbstractObject
return $this->$expandedName;
}
public function getRequest()
{
return $this->request;
}
public static function fromRequest(Request $request)
{
if ($request->has('service') && $request->has('host')) {

View File

@ -9,7 +9,6 @@ class Host extends AbstractObject
{
public $type = 'host';
public $prefix = 'host_';
private $view = null;
protected function applyObjectFilter(Query $query)
{
@ -28,7 +27,48 @@ class Host extends AbstractObject
protected function getProperties()
{
$this->view = HostStatus::fromRequest($this->getRequest());
$this->view = HostStatus::fromRequest($this->request, array(
'host_name',
'host_alias',
'host_address',
'host_state',
'host_state_type',
'host_handled',
'host_in_downtime',
'host_acknowledged',
'host_last_state_change',
'host_last_notification',
'host_last_check',
'host_next_check',
'host_check_execution_time',
'host_check_latency',
'host_check_source',
'host_output',
'host_long_output',
'host_check_command',
'host_perfdata',
'host_passive_checks_enabled',
'host_passive_checks_enabled_changed',
'host_obsessing',
'host_obsessing_changed',
'host_notifications_enabled',
'host_notifications_enabled_changed',
'host_event_handler_enabled',
'host_event_handler_enabled_changed',
'host_flap_detection_enabled',
'host_flap_detection_enabled_changed',
'host_active_checks_enabled',
'host_active_checks_enabled_changed',
'host_current_check_attempt',
'host_max_check_attempts',
'host_current_notification_number',
'host_percent_state_change',
'host_is_flapping',
'host_action_url',
'host_notes_url',
'host_modified_host_attributes',
'host_problem'
));
return $this->view->getQuery()->fetchRow();
}
}

View File

@ -9,7 +9,6 @@ class Service extends AbstractObject
{
public $type = 'service';
public $prefix = 'service_';
private $view = null;
protected function applyObjectFilter(Query $query)
{
@ -29,7 +28,90 @@ class Service extends AbstractObject
protected function getProperties()
{
$this->view = ServiceStatus::fromRequest($this->getRequest());
$this->view = ServiceStatus::fromRequest($this->request, array(
'host_name',
'host_state',
'host_state_type',
'host_last_state_change',
'host_address',
'host_problem',
'host_handled',
'service_description',
'service_display_name',
'service_state',
'service_in_downtime',
'service_acknowledged',
'service_handled',
'service_unhandled',
'service_output',
'service_last_state_change',
'service_icon_image',
'service_long_output',
'service_is_flapping',
'service_state_type',
'service_severity',
'service_last_check',
'service_notifications_enabled',
'service_notifications_enabled_changed',
'service_action_url',
'service_notes_url',
'service_last_check',
'service_next_check',
'service_attempt',
'service_last_notification',
'service_check_command',
'service_check_source',
'service_current_notification_number',
'host_icon_image',
'host_acknowledged',
'host_output',
'host_long_output',
'host_in_downtime',
'host_is_flapping',
'host_last_check',
'host_notifications_enabled',
'host_unhandled_service_count',
'host_action_url',
'host_notes_url',
'host_last_comment',
'host_display_name',
'host_alias',
'host_ipv4',
'host_severity',
'host_perfdata',
'host_active_checks_enabled',
'host_passive_checks_enabled',
'host_last_hard_state',
'host_last_hard_state_change',
'host_last_time_up',
'host_last_time_down',
'host_last_time_unreachable',
'host_modified_host_attributes',
'host',
'service',
'service_hard_state',
'service_problem',
'service_perfdata',
'service_active_checks_enabled',
'service_active_checks_enabled_changed',
'service_passive_checks_enabled',
'service_passive_checks_enabled_changed',
'service_last_hard_state',
'service_last_hard_state_change',
'service_last_time_ok',
'service_last_time_warning',
'service_last_time_critical',
'service_last_time_unknown',
'service_current_check_attempt',
'service_max_check_attempts',
'service_obsessing',
'service_obsessing_changed',
'service_event_handler_enabled',
'service_event_handler_enabled_changed',
'service_flap_detection_enabled',
'service_flap_detection_enabled_changed',
'service_modified_service_attributes',
));
return $this->view->getQuery()->fetchRow();
}
}

57
packages/rhel/README Normal file
View File

@ -0,0 +1,57 @@
Requirements
============
Disabled SELinux for sending commands via external command pipe
provided by Icinga (2) Core.
# setenforce 0
Webinterface Login
==================
The default credentials using the internal MySQL database are
icingaadmin:icinga
Internal MySQL DB Setup
=======================
# mysql -u root -p
CREATE USER `icingaweb`@`localhost` IDENTIFIED BY 'icingaweb';
CREATE DATABASE `icingaweb`;
GRANT ALL PRIVILEGES ON `icingaweb`.* TO `icingaweb`@`localhost`;
FLUSH PRIVILEGES;
quit
# mysql icingaweb < /usr/share/doc/icingaweb2-*/schema/accounts.mysql.sql
# mysql icingaweb < /usr/share/doc/icingaweb2-*/schema/preferences.mysql.sql
Modules
=======
The monitoring module is enabled by default.
Backend configuration
=====================
/etc/icingaweb/resources.ini
contains the database backend information. By default
the Icinga IDO DB is used by the monitoring module in
/etc/icingaweb/modules/monitoring/backends.ini
The external command pipe is required for sending commands
and configured for Icinga 2 in
/etc/icingaweb/modules/monitoring/instances.ini
Support
=======
Please use one of the listed support channels at https://support.icinga.org

View File

@ -0,0 +1,12 @@
Alias /icingaweb /usr/share/icingaweb/public
<Directory "/usr/share/icingaweb/public">
Options -Indexes
AllowOverride All
Order allow,deny
Allow from all
EnableSendfile Off
</Directory>

View File

@ -0,0 +1,7 @@
RewriteEngine on
RewriteBase /icingaweb
RewriteCond %{REQUEST_FILENAME} -s [OR]
RewriteCond %{REQUEST_FILENAME} -l [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^.*$ - [NC,L]
RewriteRule ^.*$ index.php [NC,L]

View File

@ -0,0 +1,5 @@
<?php
$_ENV['ICINGAWEB_CONFIGDIR'] = '/etc/icingaweb';
require_once dirname(__DIR__). '/library/Icinga/Application/webrouter.php';

View File

@ -0,0 +1,96 @@
div.wizard {
div.header {
padding: 0.6em 0 0 1em;
height: 3em;
position: fixed;
top: 0;
left: 0;
right: 0;
color: #eee;
background-color: #555;
background-image: linear-gradient(top, #777, #555);
background-image: -o-linear-gradient(top, #777, #555);
background-image: -ms-linear-gradient(top, #777, #555);
background-image: -webkit-linear-gradient(top, #777, #555);
h1 {
margin: 0 3.5em;
display: inline-block;
font-size: 2em;
}
}
div.sidebar {
width: 13em;
position: fixed;
top: 3.6em;
left: 0;
bottom: 0;
background-color: #999;
box-shadow: inset -0.5em 0 0.5em -0.5em #555;
-moz-box-shadow: inset -0.5em 0 0.5em -0.5em #555;
-webkit-box-shadow: inset -0.5em 0 0.5em -0.5em #555;
& > ul {
margin: 0;
padding: 0;
list-style: none;
& > li {
color: #f5f5f5;
font-size: 1.1em;
padding: 0.5em;
margin-left: 0.5em;
text-shadow: #555 -1px 1px 0px;
border-bottom: 1px solid #888;
&.active {
color: black;
margin-left: 0;
padding-left: 1em;
text-shadow: none;
background-color: white;
}
&.complete {
color: green;
}
&.pending {
color: red;
}
&.install {
border-bottom: 0;
}
ul {
margin: 0;
padding: 0;
list-style: none;
li.child {
font-size: 0.9em;
padding: 0.4em 0.8em 0;
&.active {
font-weight: bold;
}
}
}
}
}
}
div.panel {
padding: 1em;
position: fixed;
top: 3.6em;
left: 13em;
right: 0;
bottom: 0;
}
}

View File

@ -26,14 +26,18 @@
background-color: white;
}
.container {
background-color: white;
}
#col1.impact, #col2.impact, #col3.impact {
background-color: #ddd;
transition: background-color 2s 1s linear;
-moz-transition: background-color 2s 1s linear;
-o-transition: background-color 2s 1s linear;
-webkit-transition: background-color 2s 1s linear;
.controls {
background-color: #ddd;
transition: background-color 2s 1s linear;
-moz-transition: background-color 2s 1s linear;
-o-transition: background-color 2s 1s linear;
-webkit-transition: background-color 2s 1s linear;
}
}

View File

@ -46,13 +46,21 @@ ul.tabs > li.active > a:focus {
color: #555;
}
ul.tabs li.active a, ul.tabs li.dropdown:hover, ul.tabs li.dropdown.hover {
ul.tabs li.dropdown > a{
padding: 0 0.4em;
}
ul.tabs li.active a, ul.tabs li.dropdown:hover a, ul.tabs li.dropdown.hover a {
background-color: white;
color: #333;
}
.impact ul.tabs li.active a, .impact ul.tabs li.dropdown:hover {
background: white;
.impact ul.tabs li.active a, .impact ul.tabs li.dropdown:hover, .impact ul.tabs li.dropdown.hover a {
background-color: #ddd;
transition: background-color 2s 1s linear;
-moz-transition: background-color 2s 1s linear;
-o-transition: background-color 2s 1s linear;
-webkit-transition: background-color 2s 1s linear;
}
ul.tabs li a:hover {
@ -74,13 +82,16 @@ ul.dropdown-menu {
/* Dropdown tabs after the fourth title should be right-aligned */
ul.tabs li:nth-child(n+5) ul.dropdown-menu {
width: 13em;
margin-left: -9em;
margin-left: -11em;
}
ul.dropdown-menu {
box-shadow: 0.2em 0.2em 0.3em -0.2em #555;
-moz-box-shadow: 0.2em 0.2em 0.3em -0.2em #555;
-webkit-box-shadow: 0.2em 0.2em 0.3em -0.2em #555;
box-shadow: 0.2em 0.2em 0.3em -0.2em #555;
border-radius: 0 0 3px 3px;
-moz-border-radius: 0 0 3px 3px;
-webkit-border-radius: 0 0 3px 3px;
}
ul.dropdown-menu li {

View File

@ -9,6 +9,8 @@
Icinga.Events = function (icinga) {
this.icinga = icinga;
this.searchValue = '';
};
Icinga.Events.prototype = {
@ -74,6 +76,12 @@
// replace all sparklines
$('span.sparkline', el).sparkline('html', { enableTagOptions: true });
var searchField = $('#menu input.search', el);
// Remember initial search field value if any
if (searchField.length && searchField.val().length) {
this.searchValue = searchField.val();
}
},
/**
@ -108,7 +116,7 @@
// We support an 'autosubmit' class on dropdown form elements
$(document).on('change', 'form select.autosubmit', { self: this }, this.autoSubmitForm);
$(document).on('keyup', '#menu input.search', {self: this}, this.autoSubmitForm);
$(document).on('keyup', '#menu input.search', {self: this}, this.autoSubmitSearch);
$(document).on('mouseenter', '.historycolorgrid td', this.historycolorgridHover);
$(document).on('mouseleave', '.historycolorgrid td', this.historycolorgidUnhover);
@ -190,7 +198,8 @@
dropdownLeave: function () {
var $li = $(this);
setTimeout(function () {
if (! $li.is('li:hover') && ! $li.find(':focus')) {
// TODO: make this behave well together with keyboard navigation
if (! $li.is('li:hover') /*&& ! $li.find('a:focus')*/) {
$li.removeClass('hover');
}
}, 300);
@ -232,6 +241,15 @@
$(this).removeClass('hover');
},
autoSubmitSearch: function(event) {
var self = event.data.self;
if ($('#menu input.search').val() === self.searchValue) {
return;
}
self.searchValue = $('#menu input.search').val();
return self.autoSubmitForm(event);
},
autoSubmitForm: function (event) {
return event.data.self.submitForm(event, true);
},

View File

@ -118,6 +118,9 @@
if (id) {
this.requests[id] = req;
}
if (! autorefresh) {
req.$target.addClass('impact');
}
this.icinga.ui.refreshDebug();
return req;
},

View File

@ -664,8 +664,8 @@
'<span sparkTitle="' + title +
'" sparkWidth="' + width +
'" sparkHeight="' + height +
'" sparkType="pie" sparkWidth="20" sparkSliceColors="[' +
colors + ']" sparkHeight="20" values="' +
'" sparkType="pie" sparkSliceColors="[' +
colors + ']" values="' +
values + '" class="sparkline"></span>'
);
},