From 192a635599975cdb5b80ebbd54ef347dedcb5947 Mon Sep 17 00:00:00 2001 From: fbsanchez Date: Mon, 25 Jan 2021 19:29:22 +0100 Subject: [PATCH] WIP setup.hdb --- .../godmode/wizards/Wizard.main.php | 2 - pandora_console/include/functions_ui.php | 14 +- pandora_console/include/lib/Core/Config.php | 70 +++++-- .../include/lib/Core/DBMantainer.php | 194 +++++++++++++++++- pandora_console/include/styles/pandora.css | 4 + pandora_console/include/styles/setup.css | 5 + 6 files changed, 265 insertions(+), 24 deletions(-) create mode 100644 pandora_console/include/styles/setup.css diff --git a/pandora_console/godmode/wizards/Wizard.main.php b/pandora_console/godmode/wizards/Wizard.main.php index 6783ba20e1..3485dec627 100644 --- a/pandora_console/godmode/wizards/Wizard.main.php +++ b/pandora_console/godmode/wizards/Wizard.main.php @@ -32,8 +32,6 @@ global $config; require_once $config['homedir'].'/vendor/autoload.php'; require_once $config['homedir'].'/include/class/HTML.class.php'; -use \HTML; - /** * Global Wizard generic class. Needs to be inherited. * diff --git a/pandora_console/include/functions_ui.php b/pandora_console/include/functions_ui.php index cc72d93f5f..3ec6eec22c 100755 --- a/pandora_console/include/functions_ui.php +++ b/pandora_console/include/functions_ui.php @@ -3935,7 +3935,19 @@ function ui_toggle( /** * Simplified way of ui_toggle ussage. * - * @param array $data Arguments. + * @param array $data Arguments: + * - content + * - name + * - title + * - id + * - hidden_default + * - return + * - toggle_class + * - container_class + * - main_class + * - img_a + * - img_b + * - clean. * * @return string HTML code with toggle content. */ diff --git a/pandora_console/include/lib/Core/Config.php b/pandora_console/include/lib/Core/Config.php index cda3581ed7..51b9f09c63 100644 --- a/pandora_console/include/lib/Core/Config.php +++ b/pandora_console/include/lib/Core/Config.php @@ -29,8 +29,8 @@ // Begin. namespace PandoraFMS\Core; -require_once __DIR__.'/../../include/config.php'; -require_once __DIR__.'/../../include/functions_config.php'; +require_once __DIR__.'/../../config.php'; +require_once __DIR__.'/../../functions_config.php'; /** * Config class to operate console configuration. @@ -38,21 +38,57 @@ require_once __DIR__.'/../../include/functions_config.php'; final class Config { + /** + * History database settings (tconfig). + * + * @var array + */ + private static $settings = []; + + + /** + * Load history database settings. + */ + private static function loadHistoryDBSettings() + { + if (self::$settings === null) { + $data = \db_get_all_rows_filter('tconfig', [], false, 'AND', true); + self::$settings = array_reduce( + $data, + function ($carry, $item) { + $carry[$item['token']] = $item['value']; + }, + [] + ); + } + } + /** * Retrieve configuration token. * - * @param string $token Token to retrieve. - * @param mixed $default Default value if not found. + * @param string $token Token to retrieve. + * @param mixed $default Default value if not found. + * @param boolean $history_db Search for token in history_db. * * @return mixed Configuration token. */ - public static function get(string $token, $default=null) - { - global $config; + public static function get( + string $token, + $default=null, + bool $history_db=false + ) { + if ($history_db === true) { + self::loadHistoryDBSettings(); + if (isset(self::$settings[$token]) === true) { + return self::$settings[$token]; + } + } else { + global $config; - if (isset($config[$token]) === true) { - return $config[$token]; + if (isset($config[$token]) === true) { + return $config[$token]; + } } return $default; @@ -63,15 +99,21 @@ final class Config /** * Set configuration token. * - * @param string $token Token to set. - * @param mixed $value Value to be. + * @param string $token Token to set. + * @param mixed $value Value to be. + * @param boolean $history_db Save to history_db settings. * * @return void */ - public static function set(string $token, $value) + public static function set(string $token, $value, bool $history_db=false) { - if (self::get($token) === null) { - config_update_value($token, $value); + if ($history_db !== false) { + if (self::get($token, null, $history_db) === null) { + } + } else { + if (self::get($token) === null) { + config_update_value($token, $value); + } } } diff --git a/pandora_console/include/lib/Core/DBMantainer.php b/pandora_console/include/lib/Core/DBMantainer.php index 1e8b6d80c3..d08a34bbd7 100644 --- a/pandora_console/include/lib/Core/DBMantainer.php +++ b/pandora_console/include/lib/Core/DBMantainer.php @@ -34,6 +34,12 @@ namespace PandoraFMS\Core; */ final class DBMantainer { + const ESSENTIAL_TABLES = [ + 'tagente_datos', + 'tagente_datos_string', + 'tevento', + 'tconfig', + ]; /** * Database user. @@ -105,6 +111,13 @@ final class DBMantainer */ private $lastError; + /** + * Connected to engine and database. + * + * @var boolean + */ + private $ready; + /** * Initialize DBMaintainer object. @@ -146,11 +159,11 @@ final class DBMantainer $this->host, $this->user, $this->pass, - $this->name, + null, $this->port ); - if ($dbc->connect_error === false) { + if ((bool) $dbc->connect_error === true) { $this->dbh = null; $this->connected = false; $this->lastError = $dbc->connect_errno.': '.$dbc->connect_error; @@ -160,10 +173,16 @@ final class DBMantainer $dbc->set_charset($this->charset); } - $this->connected = true; - $this->lastError = null; - } + if ($this->dbh->select_db($this->name) === false) { + $this->lastError = $this->dbh->errno.': '.$this->dbh->error; + $this->ready = false; + } else { + $this->lastError = null; + $this->ready = true; + } + $this->connected = true; + } } @@ -182,6 +201,100 @@ final class DBMantainer } + /** + * Retrieve all rows from given query in array format. + * + * @param string $query Query. + * + * @return array Results. + */ + private function getAllRows(string $query) + { + if ($this->ready !== true) { + $this->lastError = $this->dbh->errno.': '.$this->dbh->error; + return []; + } + + $rs = $this->dbh->query($query); + + $results = []; + + do { + $row = $rs->fetch_array(MYSQLI_ASSOC); + if ((bool) $row !== false) { + $results[] = $row; + } + } while ((bool) $row !== false); + + return $results; + } + + + /** + * Verifies schema against running db. + * + * @return boolean Success or not. + */ + public function verifySchema() + { + if ($this->ready !== true) { + return false; + } + + $missing_essential_tables = $this->verifyTables(); + + return !(bool) count($missing_essential_tables); + } + + + /** + * Verifies tables against running db. + * + * @return boolean Applied or not. + */ + public function verifyTables() + { + global $config; + + $t = \db_get_all_rows_sql( + sprintf( + 'SHOW TABLES FROM %s', + $config['dbname'] + ) + ); + + $tables = []; + foreach ($t as $v) { + $tables[] = array_shift($v); + } + + $t = $this->getAllRows( + sprintf( + 'SHOW TABLES FROM %s', + $this->name + ) + ); + $myTables = []; + foreach ($t as $k => $v) { + $myTables[] = array_shift($v); + } + + $differences = array_diff($tables, $myTables); + + if (count($differences) > 0) { + $this->lastError = sprintf( + 'Warning, following tables does not exist in target: %s', + join(', ', $differences) + ); + } + + // Exclude extension tables. + $differences = array_intersect($differences, self::ESSENTIAL_TABLES); + + return $differences; + } + + /** * Install PandoraFMS database schema in current target. * @@ -197,8 +310,33 @@ final class DBMantainer return true; } - $this->lastError = 'Pending installation'; - return false; + if ($this->ready !== true) { + // Not ready, create database in target. + $rc = $this->dbh->query( + sprintf( + 'CREATE DATABASE %s', + $this->name + ) + ); + + if ($rc === false) { + $this->lastError = $this->dbh->errno.': '.$this->dbh->error; + return false; + } + + if ($this->dbh->select_db($this->name) === false) { + $this->lastError = $this->dbh->errno.': '.$this->dbh->error; + return false; + } + + // Already connected and ready to execute commands. + $this->ready = true; + } else if ($this->verifySchema() === true) { + $this->installed = true; + return true; + } + + return $this->applyDump(Config::get('homedir', '').'/pandoradb.sql'); } @@ -247,4 +385,46 @@ final class DBMantainer } + /** + * This function keeps same functionality as install.php:parse_mysqli_dump. + * + * @param string $path Path where SQL dump file is stored. + * + * @return boolean Success or not. + */ + private function applyDump(string $path) + { + if (file_exists($path) === true) { + $file_content = file($path); + $query = ''; + foreach ($file_content as $sql_line) { + if (trim($sql_line) !== '' + && strpos($sql_line, '-- ') === false + ) { + $query .= $sql_line; + if ((bool) preg_match("/;[\040]*\$/", $sql_line) === true) { + $result = $this->dbh->query($query); + if ((bool) $result === false) { + $this->lastError = $this->dbh->errnum.': '; + $this->lastERror .= $this->dbh->error; + return false; + } + + $query = ''; + } + } + } + + return true; + } + + // File does not exist. + $this->lastError = sprintf( + 'File %s does not exist', + $path + ); + return false; + } + + } diff --git a/pandora_console/include/styles/pandora.css b/pandora_console/include/styles/pandora.css index f3a6959cba..a1b21bd24b 100644 --- a/pandora_console/include/styles/pandora.css +++ b/pandora_console/include/styles/pandora.css @@ -478,6 +478,10 @@ select:-internal-list-box { width: 290px; max-width: 290px; } +.w600px { + width: 600px; + max-width: 600px; +} .mw120px { min-width: 120px; } diff --git a/pandora_console/include/styles/setup.css b/pandora_console/include/styles/setup.css new file mode 100644 index 0000000000..331bc7aa2e --- /dev/null +++ b/pandora_console/include/styles/setup.css @@ -0,0 +1,5 @@ +span.subtitle { + font-size: 1.3em; + font-weight: normal; + font-family: "lato-bolder"; +}