From 66bad65550ed26f14fed967be14b2578a6e961f4 Mon Sep 17 00:00:00 2001 From: Daniel Barbero Date: Fri, 11 Oct 2019 14:55:20 +0200 Subject: [PATCH 01/11] refactoriced diagnostics pandoraFMS --- pandora_console/godmode/menu.php | 6 +- .../include/class/Diagnostics.class.php | 312 ++++++++++++++++++ pandora_console/tools/diagnostics.php | 71 ++++ 3 files changed, 386 insertions(+), 3 deletions(-) create mode 100644 pandora_console/include/class/Diagnostics.class.php create mode 100644 pandora_console/tools/diagnostics.php diff --git a/pandora_console/godmode/menu.php b/pandora_console/godmode/menu.php index 7175081912..edf7be1873 100644 --- a/pandora_console/godmode/menu.php +++ b/pandora_console/godmode/menu.php @@ -339,13 +339,13 @@ if (check_acl($config['id_user'], 0, 'PM') || check_acl($config['id_user'], 0, ' $sub = []; if (check_acl($config['id_user'], 0, 'PM')) { - // Audit //meter en extensiones + // Audit //meter en extensiones. $sub['godmode/admin_access_logs']['text'] = __('System audit log'); $sub['godmode/admin_access_logs']['id'] = 'System audit log'; $sub['godmode/setup/links']['text'] = __('Links'); $sub['godmode/setup/links']['id'] = 'Links'; - $sub['extras/pandora_diag']['text'] = __('Diagnostic info'); - $sub['extras/pandora_diag']['id'] = 'Diagnostic info'; + $sub['tools/diagnostics']['text'] = __('Diagnostic info'); + $sub['tools/diagnostics']['id'] = 'Diagnostic info'; $sub['godmode/setup/news']['text'] = __('Site news'); $sub['godmode/setup/news']['id'] = 'Site news'; $sub['godmode/setup/file_manager']['text'] = __('File manager'); diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php new file mode 100644 index 0000000000..f38a21e8d8 --- /dev/null +++ b/pandora_console/include/class/Diagnostics.class.php @@ -0,0 +1,312 @@ +getStatusInfo(); + + /* + * Print table in this case info. + */ + + $this->printTable($statusInfo); + + /* + * PHP setup. + */ + + $phpSetup = $this->getPHPSetup(); + + /* + * Print table in this case PHP SETUP. + */ + + $this->printTable($phpSetup); + + /* + * Database size stats. + */ + + $dataBaseSizeStats = $this->getDatabaseSizeStats(); + + /* + * Print table in this case Database size stats. + */ + + $this->printTable($dataBaseSizeStats); + } + + + /** + * Info status pandoraFms. + * + * @return string + */ + public function getStatusInfo(): string + { + global $config; + global $build_version; + global $pandora_version; + + $sql = sprintf( + "SELECT `key`, `value` + FROM `tupdate_settings` + WHERE `key` = '%s' + OR `key` = '%s' + OR `key` = '%s'", + 'current_update', + 'customer_key', + 'updating_code_path' + ); + + $values_key = db_get_all_rows_sql($sql); + $values_key = array_reduce( + $values_key, + function ($carry, $item) { + if ($item['key'] === 'customer_key') { + $customer = substr($item['value'], 0, 5); + $customer .= '...'; + $customer .= substr($item['value'], -5); + $item['value'] = $customer; + } + + $carry[$item['key']] = $item['value']; + return $carry; + } + ); + + $result = [ + 'error' => false, + 'data' => [ + 'buildVersion' => [ + 'name' => __('Pandora FMS Build'), + 'value' => $build_version, + ], + 'version' => [ + 'name' => __('Pandora FMS Version'), + 'value' => $pandora_version, + ], + 'mr' => [ + 'name' => __('Minor Release'), + 'value' => $config['MR'], + ], + 'homeDir' => [ + 'name' => __('Homedir'), + 'value' => $config['homedir'], + ], + 'homeUrl' => [ + 'name' => __('HomeUrl'), + 'value' => $config['homeurl'], + ], + 'isEnterprise' => [ + 'name' => __('Enterprise installed'), + 'value' => (enterprise_installed()) ? __('true') : __('false'), + ], + 'customerKey' => [ + 'name' => __('Update Key'), + 'value' => $values_key['customer_key'], + ], + 'updatingCode' => [ + 'name' => __('Updating code path'), + 'value' => $values_key['updating_code_path'], + ], + 'currentUpdate' => [ + 'name' => __('Current Update #'), + 'value' => $values_key['current_update'], + ], + + ], + ]; + + return json_encode($result); + } + + + /** + * PHP Status. + * + * @return string + */ + public function getPHPSetup(): string + { + global $config; + + $result = [ + 'error' => false, + 'data' => [ + 'phpVersion' => [ + 'name' => __('PHP Version'), + 'value' => phpversion(), + ], + 'maxExecutionTime' => [ + 'name' => __('PHP Max execution time'), + 'value' => ini_get('max_execution_time'), + ], + 'maxInputTime' => [ + 'name' => __('PHP Max input time'), + 'value' => ini_get('max_input_time'), + ], + 'memoryLimit' => [ + 'name' => __('PHP Memory limit'), + 'value' => ini_get('memory_limit'), + ], + 'sessionLifetime' => [ + 'name' => __('Session cookie lifetime'), + 'value' => ini_get('session.cookie_lifetime'), + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Database size stats. + * + * @return string + */ + public function getDatabaseSizeStats(): string + { + global $config; + + $countAgents = db_get_value_sql('SELECT COUNT(*) FROM tagente'); + $countModules = db_get_value_sql('SELECT COUNT(*) FROM tagente_modulo'); + $countGroups = db_get_value_sql('SELECT COUNT(*) FROM tgrupo'); + $countModuleData = db_get_value_sql( + 'SELECT COUNT(*) FROM tagente_datos' + ); + $countAgentAccess = db_get_value_sql( + 'SELECT COUNT(*) FROM tagent_access' + ); + $countEvents = db_get_value_sql('SELECT COUNT(*) FROM tevento'); + + if (enterprise_installed() === true) { + $countTraps = db_get_value_sql('SELECT COUNT(*) FROM ttrap'); + } + + $countUsers = db_get_value_sql('SELECT COUNT(*) FROM tusuario'); + $countSessions = db_get_value_sql('SELECT COUNT(*) FROM tsesion'); + + $result = [ + 'error' => false, + 'data' => [ + 'countAgents' => [ + 'name' => __('Total agentsy'), + 'value' => $countAgents, + ], + 'countModules' => [ + 'name' => __('Total modules'), + 'value' => $countModules, + ], + 'countGroups' => [ + 'name' => __('Total groups'), + 'value' => $countGroups, + ], + 'countModuleData' => [ + 'name' => __('Total module data records'), + 'value' => $countModuleData, + ], + 'countAgentAccess' => [ + 'name' => __('Total agent access record'), + 'value' => $countAgentAccess, + ], + 'countEvents' => [ + 'name' => __('Total events'), + 'value' => $countEvents, + ], + 'countTraps' => [ + 'name' => __('Total traps'), + 'value' => $countTraps, + ], + 'countUsers' => [ + 'name' => __('Total users'), + 'value' => $countUsers, + ], + 'countSessions' => [ + 'name' => __('Total sessions'), + 'value' => $countSessions, + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Paint table. + * + * @param string $statusInfo Json width status info. + * + * @return void + */ + public function printTable(string $statusInfo): void + { + global $config; + + hd($statusInfo); + } + + +} diff --git a/pandora_console/tools/diagnostics.php b/pandora_console/tools/diagnostics.php new file mode 100644 index 0000000000..ad97d8b742 --- /dev/null +++ b/pandora_console/tools/diagnostics.php @@ -0,0 +1,71 @@ + '[Diagnostics]'.$e->getMessage() ]); + exit; + } else { + echo '[Diagnostics]'.$e->getMessage(); + } + + // Stop this execution, but continue 'globally'. + return; +} + +// AJAX controller. +if (is_ajax()) { + $method = get_parameter('method'); + + if (method_exists($cs, $method) === true) { + if ($cs->ajaxMethod($method) === true) { + $cs->{$method}(); + } else { + $cs->error('Unavailable method.'); + } + } else { + $cs->error('Method not found. ['.$method.']'); + } + + // Stop any execution. + exit; +} else { + // Run. + $cs->run(); +} From 13a72426cdc9cb011414b34da6556ad12ca002af Mon Sep 17 00:00:00 2001 From: Daniel Barbero Martin Date: Mon, 14 Oct 2019 17:21:38 +0200 Subject: [PATCH 02/11] fixed diagnostics --- .../include/class/Diagnostics.class.php | 900 ++++++++++++++++++ 1 file changed, 900 insertions(+) diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index f38a21e8d8..211ae3ea9a 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -94,6 +94,132 @@ class Diagnostics */ $this->printTable($dataBaseSizeStats); + + /* + * Database health status. + */ + + $databaseHealthStatus = $this->getDatabaseHealthStatus(); + + /* + * Print table in this case Database health status. + */ + + $this->printTable($databaseHealthStatus); + + /* + * Database health status. + */ + + $getDatabaseStatusInfo = $this->getDatabaseStatusInfo(); + + /* + * Print table in this case Database status info. + */ + + $this->printTable($getDatabaseStatusInfo); + + if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { + /* + * System Info. + */ + + $getSystemInfo = $this->getSystemInfo(); + + /* + * Print table in this case System Info. + */ + + $this->printTable($getSystemInfo); + } + + /* + * System Info. + */ + + $getMySQLPerformanceMetrics = $this->getMySQLPerformanceMetrics(); + + /* + * Print table in this case System Info. + */ + + $this->printTable($getMySQLPerformanceMetrics); + + /* + * Tables fragmentation in the Pandora FMS database. + */ + + $getTablesFragmentation = $this->getTablesFragmentation(); + + /* + * Print table in this case Tables fragmentation in + * the Pandora FMS database. + */ + + $this->printTable($getTablesFragmentation); + + /* + * Tables fragmentation in the Pandora FMS database. + */ + + $getPandoraFMSLogsDates = $this->getPandoraFMSLogsDates(); + + /* + * Print table in this case Tables fragmentation in + * the Pandora FMS database. + */ + + $this->printTable($getPandoraFMSLogsDates); + + /* + * Pandora FMS Licence Information. + */ + + $getLicenceInformation = $this->getLicenceInformation(); + + /* + * Print table in this case Pandora FMS Licence Information. + */ + + $this->printTable($getLicenceInformation); + + /* + * Status of the attachment folder. + */ + + $getAttachmentFolder = $this->getAttachmentFolder(); + + /* + * Print table in this case Status of the attachment folder. + */ + + $this->printTable($getAttachmentFolder); + + /* + * Information from the tagente_datos table. + */ + + $getInfoTagenteDatos = $this->getInfoTagenteDatos(); + + /* + * Print table in this case Information from the tagente_datos table. + */ + + $this->printTable($getInfoTagenteDatos); + + if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { + /* + * Pandora FMS server threads. + */ + + $getServerThreads = $this->getServerThreads(); + + /* + * Print table in this case Pandora FMS server threads. + */ + + $this->printTable($getServerThreads); + } } @@ -294,6 +420,735 @@ class Diagnostics } + /** + * Database health status. + * + * @return string + */ + public function getDatabaseHealthStatus(): string + { + global $config; + + // Count agents unknowns. + $sqlUnknownAgents = 'SELECT COUNT( DISTINCT tagente.id_agente) + FROM tagente_estado, tagente, tagente_modulo + WHERE tagente.disabled = 0 + AND tagente_modulo.id_agente_modulo = tagente_estado.id_agente_modulo + AND tagente_modulo.disabled = 0 + AND tagente_estado.id_agente = tagente.id_agente + AND tagente_estado.estado = 3'; + $unknownAgents = db_get_sql($sqlUnknownAgents); + + // Count modules not initialize. + $sqlNotInitAgents = 'SELECT COUNT(tagente_estado.estado) + FROM tagente_estado + WHERE tagente_estado.estado = 4'; + $notInitAgents = db_get_sql($sqlNotInitAgents); + + $dateDbMantenaince = $config['db_maintance']; + + $currentTime = time(); + + $pandoraDbLastRun = __('Pandora DB has never been executed'); + if ($dateDbMantenaince !== false) { + $difference = ($currentTime - $dateDbMantenaince); + $pandoraDbLastRun = human_time_comparation($difference); + $pandoraDbLastRun .= ' '.__('Ago'); + } + + $result = [ + 'error' => false, + 'data' => [ + 'unknownAgents' => [ + 'name' => __('Total unknown agents'), + 'value' => $unknownAgents, + ], + 'notInitAgents' => [ + 'name' => __('Total not-init modules'), + 'value' => $notInitAgents, + ], + 'pandoraDbLastRun' => [ + 'name' => __('PandoraDB Last run'), + 'value' => $pandoraDbLastRun, + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Database status info. + * + * @return string + */ + public function getDatabaseStatusInfo(): string + { + global $config; + + // Size BBDD. + $dbSizeSql = db_get_value_sql( + 'SELECT ROUND(SUM(data_length+index_length)/1024/1024,3) + FROM information_schema.TABLES' + ); + + // Add unit size. + $dbSize = $dbSizeSql.' M'; + + $result = [ + 'error' => false, + 'data' => [ + 'dbSchemeFirstVersion' => [ + 'name' => __('DB Schema Version (first installed)'), + 'value' => $config['db_scheme_first_version'], + ], + 'dbSchemeVersion' => [ + 'name' => __('DB Schema Version (actual)'), + 'value' => $config['db_scheme_version'], + ], + 'dbSchemeBuild' => [ + 'name' => __('DB Schema Build'), + 'value' => $config['db_scheme_build'], + ], + 'dbSize' => [ + 'name' => __('DB Size'), + 'value' => $dbSize, + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Database status info. + * + * @return string + */ + public function getSystemInfo(): string + { + global $config; + + $cpuModelName = 'cat /proc/cpuinfo | grep "model name" | tail -1 | cut -f 2 -d ":"'; + $cpuProcessor = 'cat /proc/cpuinfo | grep "processor" | wc -l'; + $ramMemTotal = 'cat /proc/meminfo | grep "MemTotal"'; + + $result = [ + 'error' => false, + 'data' => [ + 'cpuInfo' => [ + 'name' => __('CPU'), + 'value' => exec($cpuModelName).' x '.exec($cpuProcessor), + ], + 'ramInfo' => [ + 'name' => __('RAM'), + 'value' => exec($ramMemTotal), + ], + ], + ]; + + return json_encode($result); + } + + + /** + * MySQL Performance metrics. + * + * @return string + */ + public function getMySQLPerformanceMetrics(): string + { + global $config; + + $variablesMsql = db_get_all_rows_sql('SHOW variables'); + $variablesMsql = array_reduce( + $variablesMsql, + function ($carry, $item) { + $bytes = 1048576; + $mega = 1024; + switch ($item['Variable_name']) { + case 'innodb_log_file_size': + $name = __('InnoDB log file size'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 64) ? 1 : 0; + $message = __('Min. Recommended Value').' 64M'; + break; + + case 'innodb_log_buffer_size': + $name = __('InnoDB log buffer size'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 16) ? 1 : 0; + $message = __('Min. Recommended Value').' 16M'; + break; + + case 'innodb_flush_log_at_trx_commit': + $name = __('InnoDB flush log at trx-commit'); + $value = $item['Value']; + $status = (($item['Value'] / $bytes) >= 0) ? 1 : 0; + $message = __('Min. Recommended Value').' 0'; + break; + + case 'max_allowed_packet': + $name = __('Maximun allowed packet'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 32) ? 1 : 0; + $message = __('Min. Recommended Value').' 32'; + break; + + case 'innodb_buffer_pool_size': + if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { + $min = shell_exec( + "cat /proc/meminfo | grep -i total | head -1 | awk '{print $(NF-1)*0.4/1024}'" + ); + } + + $name = __('InnoDB buffer pool size'); + $value = ($item['Value'] / $mega); + $status = (($item['Value'] / $bytes) >= $min) ? 1 : 0; + $message = __('Min. Recommended Value').' '.$min; + break; + + case 'sort_buffer_size': + $name = __('Sort buffer size'); + $value = number_format(($item['Value'] / $mega), 2); + $status = (($item['Value'] / $bytes) >= 32) ? 1 : 0; + $message = __('Min. Recommended Value').' 32'; + break; + + case 'join_buffer_size': + $name = __('Join buffer size'); + $value = ($item['Value'] / $mega); + $status = (($item['Value'] / $bytes) >= 265) ? 1 : 0; + $message = __('Min. Recommended Value 265'); + break; + + case 'query_cache_type': + $name = __('Query cache type'); + $value = $item['Value']; + $status = ($item['Value'] === 'ON') ? 1 : 0; + $message = __('Recommended ON'); + break; + + case 'query_cache_size': + $name = __('Query cache size'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 24) ? 1 : 0; + $message = __('Min. Recommended Value').' 24'; + break; + + case 'query_cache_limit': + $name = __('Query cache limit'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 2) ? 1 : 0; + $message = __('Min. Recommended Value').' 2'; + break; + + case 'innodb_lock_wait_timeout': + $name = __('InnoDB lock wait timeout'); + $value = $item['Value']; + $status = (($item['Value'] / $bytes) >= 120) ? 1 : 0; + $message = __('Min. Recommended Value').' 120'; + break; + + case 'thread_cache_size': + $name = __('Thread cache size'); + $value = $item['Value']; + $status = (($item['Value'] / $bytes) >= 8) ? 1 : 0; + $message = __('Min. Recommended Value').' 8'; + break; + + case 'thread_stack': + $name = __('Thread stack'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 256) ? 1 : 0; + $message = __('Min. Recommended Value').' 256'; + break; + + case 'max_connections': + $name = __('Maximun connections'); + $value = $item['Value']; + $status = (($item['Value'] / $bytes) >= 150) ? 1 : 0; + $message = __('Min. Recommended Value').' 150'; + break; + + case 'key_buffer_size': + $name = __('Key buffer size'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 256) ? 1 : 0; + $message = __('Min. Recommended Value').' 256'; + break; + + case 'read_buffer_size': + $name = __('Read buffer size'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 32) ? 1 : 0; + $message = __('Min. Recommended Value').' 32'; + break; + + case 'read_rnd_buffer_size': + $name = __('Read rnd-buffer size'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 32) ? 1 : 0; + $message = __('Min. Recommended Value').' 32'; + break; + + case 'query_cache_min_res_unit': + $name = __('Query cache min-res-unit'); + $value = ($item['Value'] / $bytes); + $status = (($item['Value'] / $bytes) >= 2) ? 1 : 0; + $message = __('Min. Recommended Value').' 2'; + break; + + case 'innodb_file_per_table': + $name = __('InnoDB file per table'); + $value = $item['Value']; + $status = (($item['Value'] / $bytes) >= 1) ? 1 : 0; + $message = __('Min. Recommended Value').' 1'; + break; + + default: + $name = ''; + $value = 0; + break; + } + + if (empty($name) !== true) { + $carry[$item['Variable_name']] = [ + 'name' => $name, + 'value' => $value, + 'status' => $status, + 'message' => $message, + ]; + } + + return $carry; + }, + [] + ); + + $result = [ + 'error' => false, + 'data' => $variablesMsql, + ]; + + return json_encode($result); + } + + + /** + * Tables fragmentation in the Pandora FMS database. + * + * @return string + */ + public function getTablesFragmentation(): string + { + global $config; + + // Estimated fragmentation percentage as maximum. + $tFragmentationMax = 10; + + // Extract the fragmentation value. + $tFragmentationValue = db_get_sql( + sprintf( + "SELECT (data_free/(index_length+data_length)) as frag_ratio + FROM information_schema.tables + WHERE DATA_FREE > 0 + AND table_name='tagente_datos' + AND table_schema='%s'", + $config['dbname'] + ) + ); + + // Check if it meets the fragmentation value. + $status_tables_frag = ''; + if ($tFragmentationValue > $tFragmentationMax) { + $tFragmentationMsg = __( + 'Table fragmentation is higher than recommended. They should be defragmented.' + ); + $tFragmentationStatus = 0; + } else { + $tFragmentationMsg = __('Table fragmentation is correct.'); + $tFragmentationStatus = 1; + } + + $result = [ + 'error' => false, + 'data' => [ + 'tablesFragmentationMax' => [ + 'name' => __( + 'Tables fragmentation (maximum recommended value)' + ), + 'value' => $tFragmentationMax.'%', + ], + 'tablesFragmentationValue' => [ + 'name' => __('Tables fragmentation (current value)'), + 'value' => number_format($tFragmentationValue, 2).'%', + ], + 'tablesFragmentationStatus' => [ + 'name' => __('Table fragmentation status'), + 'value' => $status_tables_frag, + 'status' => $tFragmentationStatus, + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Pandora FMS logs dates. + * + * @return string + */ + public function getPandoraFMSLogsDates(): string + { + global $config; + + $unit = 'M'; + + $pathServerLogs = 'var/log/pandora/pandora_server.log'; + $servers = $this->getLogInfo($pathServerLogs); + + $pathErrLogs = 'var/log/pandora/pandora_server.error'; + $errors = $this->getLogInfo($pathErrLogs); + + $pathConsoleLogs = $config['homedir'].'/pandora_console.log'; + $console = $this->getLogInfo($pathConsoleLogs); + + $result = [ + 'error' => false, + 'data' => [ + 'sizeServerLog' => [ + 'name' => __('Size server logs (current value)'), + 'value' => $servers['value'].' '.$unit, + ], + 'statusServerLog' => [ + 'name' => __('Status server logs'), + 'value' => $servers['message'], + 'status' => $servers['status'], + ], + 'sizeErrorLog' => [ + 'name' => __('Size error logs (current value)'), + 'value' => $errors['value'].' '.$unit, + ], + 'statusErrorLog' => [ + 'name' => __('Status error logs'), + 'value' => $errors['message'], + 'status' => $errors['status'], + ], + 'sizeConsoleLog' => [ + 'name' => __('Size console logs (current value)'), + 'value' => $console['value'].' '.$unit, + ], + 'statusConsoleLog' => [ + 'name' => __('Status console logs'), + 'value' => $console['message'], + 'status' => $console['status'], + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Pandora FMS Licence Information. + * + * @return string + */ + public function getLicenceInformation(): string + { + global $config; + + // Extract customer key. + $sql = sprintf( + "SELECT `value` + FROM `tupdate_settings` + WHERE `key` = '%s'", + 'customer_key' + ); + $customerKey = db_get_value_sql($sql); + + // Extract Info license. + $license = enterprise_hook('license_get_info'); + + // Agent Capacity. + $agentCount = db_get_value_sql('SELECT count(*) FROM tagente'); + $agentsCapacity = __('License capacity is less than 90 percent'); + $agentsCapacitySt = 1; + if ($agentCount > ($license['limit'] * 90 / 100)) { + $agentsCapacity = __('License capacity exceeds 90 percent'); + $agentsCapacitySt = 0; + } + + // Modules average. + $modulesCount = db_get_value_sql('SELECT count(*) FROM tagente_modulo'); + $average = ($modulesCount / $agentCount); + $averageMsg = __( + 'The average of modules per agent is more than 40. You can have performance problems' + ); + $averageSt = 0; + if ($average <= 40) { + $averageMsg = __( + 'The average of modules per agent is less than 40' + ); + $averageSt = 1; + } + + // Modules Networks average. + $totalNetworkModules = db_get_value_sql( + 'SELECT count(*) + FROM tagente_modulo + WHERE id_tipo_modulo + BETWEEN 6 AND 18' + ); + $totalModuleIntervalTime = db_get_value_sql( + 'SELECT SUM(module_interval) + FROM tagente_modulo + WHERE id_tipo_modulo + BETWEEN 6 AND 18' + ); + $averageTime = number_format( + ((int) $totalModuleIntervalTime / (int) $totalNetworkModules), + 3 + ); + $moduleNetworkmsg = __( + sprintf( + 'The system is not overloaded (average time %d)', + $average_time + ) + ); + $moduleNetworkst = 1; + if ($average_time === 0) { + $moduleNetworkmsg = __('The system has no load'); + $moduleNetworkst = 0; + } else if ($averageTime < 180) { + $moduleNetworkmsg = __( + sprintf( + 'The system is overloaded (average time %d) and a very fine configuration is required', + $average_time + ) + ); + $moduleNetworkst = 0; + } + + $result = [ + 'error' => false, + 'data' => [ + 'customerKey' => [ + 'name' => __('Customer key'), + 'value' => $customerKey, + ], + 'customerExpires' => [ + 'name' => __('Support expires'), + 'value' => $license['expiry_date'], + ], + 'customerLimit' => [ + 'name' => __('Platform Limit'), + 'value' => $license['limit'].' '.__('Agents'), + ], + 'customerPfCount' => [ + 'name' => __('Current Platform Count'), + 'value' => $license['count'].' '.__('Agents'), + ], + 'customerPfCountEnabled' => [ + 'name' => __('Current Platform Count (enabled: items)'), + 'value' => $license['count_enabled'].' '.__('Agents'), + ], + 'customerPfCountDisabled' => [ + 'name' => __('Current Platform Count (disabled: items)'), + 'value' => $license['count_disabled'].' '.__('Agents'), + ], + 'customerMode' => [ + 'name' => __('License Mode'), + 'value' => $license['license_mode'], + ], + 'customerNMS' => [ + 'name' => __('Network Management System'), + 'value' => ($license['nms'] > 0) ? __('On') : __('Off'), + ], + 'customerSatellite' => [ + 'name' => __('Satellite'), + 'value' => ($license['dhpm'] > 0) ? __('On') : __('Off'), + ], + 'customerLicenseTo' => [ + 'name' => __('Licensed to'), + 'value' => $license['licensed_to'], + ], + 'customerCapacity' => [ + 'name' => __('Status of agents capacity'), + 'value' => $agentsCapacity, + 'status' => $agentsCapacitySt, + ], + 'customerAverage' => [ + 'name' => __('Status of average modules per agent'), + 'value' => $averageMsg, + 'status' => $averageSt, + ], + + 'customerAverageNetwork' => [ + 'name' => __('Interval average of the network modules'), + 'value' => $moduleNetworkmsg, + 'status' => $moduleNetworkst, + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Status of the attachment folder. + * + * @return string + */ + public function getAttachmentFolder(): string + { + global $config; + + // Count files in attachment. + $attachmentFiles = count( + glob( + $config['homedir'].'/attachment/{*.*}', + GLOB_BRACE + ) + ); + + // Check status attachment. + $attachmentMsg = __( + 'The attached folder contains more than 700 files.' + ); + $attachmentSt = 0; + if ($attachmentFiles <= 700) { + $attachmentMsg = __( + 'The attached folder contains less than 700 files.' + ); + $attachmentSt = 1; + } + + $result = [ + 'error' => false, + 'data' => [ + 'attachFiles' => [ + 'name' => __('Total files in the attached folder'), + 'value' => $attachmentFiles, + ], + 'attachStatus' => [ + 'name' => __('Status of the attachment folder'), + 'value' => $attachmentMsg, + 'status' => $attachmentSt, + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Information from the tagente_datos table. + * + * @return string + */ + public function getInfoTagenteDatos(): string + { + global $config; + + $agentDataCount = db_get_value_sql( + 'SELECT COUNT(*) + FROM tagente_datos' + ); + + $taMsg = __( + 'The tagente_datos table contains too much data. A historical database is recommended.' + ); + $taStatus = 0; + if ($agentDataCount <= 3000000) { + $taMsg = __( + 'The tagente_datos table contains an acceptable amount of data.' + ); + $taStatus = 1; + } + + /* + $times = db_get_all_rows_sql('SELECT datos FROM tagente_datos WHERE id_agente_modulo = 29 ORDER BY utimestamp DESC LIMIT 2'); + hd($times); + if ($times[0]['datos'] > ($times[1]['datos'] * 1.2)) { + __('The execution time could be degrading. For a more extensive information of this data consult the Execution Time graph'); + } else { + __('The execution time is correct. For more information about this data, check the Execution Time graph'); + } + */ + + $result = [ + 'error' => false, + 'data' => [ + 'agentDataCount' => [ + 'name' => __('Total data in tagente_datos table'), + 'value' => $agentDataCount, + ], + 'agentDataStatus' => [ + 'name' => __('Tagente_datos table status'), + 'value' => $taMsg, + 'status' => $taStatus, + ], + 'agentDataExecution' => [ + 'name' => __('Execution time degradation when executing a count'), + 'value' => 1, + ], + ], + ]; + + return json_encode($result); + } + + + /** + * Pandora FMS server threads. + * + * @return string + */ + public function getServerThreads(): string + { + global $config; + + $totalServerThreads = shell_exec( + 'ps -T aux | grep pandora_server | grep -v grep | wc -l' + ); + $percentageThreadsRam = shell_exec( + "ps axo pmem,cmd | grep pandora_server | awk '{sum+=$1} END {print sum}'" + ); + $percentageThreadsCpu = shell_exec( + "ps axo pcpu,cmd | grep pandora_server | awk '{sum+=$1} END {print sum}'" + ); + + $result = [ + 'error' => false, + 'data' => [ + 'totalServerThreads' => [ + 'name' => __('Total server threads'), + 'value' => $totalServerThreads, + ], + 'percentageThreadsRam' => [ + 'name' => __('Percentage of threads used by the RAM'), + 'value' => $percentageThreadsRam.' %', + ], + 'percentageThreadsCpu' => [ + 'name' => __('Percentage of threads used by the CPU'), + 'value' => $percentageThreadsCpu.' %', + ], + ], + ]; + + return json_encode($result); + } + + /** * Paint table. * @@ -309,4 +1164,49 @@ class Diagnostics } + /** + * Private function for Info size path. + * + * @param string $path Route file. + * + * @return array With values size file and message and status. + */ + private function getLogInfo(string $path): array + { + global $config; + + // Vars. + $mega = 1048576; + $tenMega = 10485760; + + $result = [ + 'value' => 0, + 'message' => '', + 'status' => 0, + ]; + + if (is_file($path) === true) { + $fileSize = filesize($path); + $sizeServerLog = number_format($fileSize); + $sizeServerLog = (0 + str_replace(',', '', $sizeServerLog)); + + $value = number_format(($fileSize / $mega), 3); + $message = __('You have more than 10 MB of logs'); + $status = 0; + if ($sizeServerLog <= $tenMega) { + $message = __('You have less than 10 MB of logs'); + $status = 1; + } + + $result = [ + 'value' => $value, + 'message' => $message, + 'status' => $status, + ]; + } + + return $result; + } + + } From 4e56f6751ac9955926a9ef1508df6877af3215e5 Mon Sep 17 00:00:00 2001 From: Daniel Barbero Martin Date: Thu, 17 Oct 2019 15:17:28 +0200 Subject: [PATCH 03/11] Continue work diagnostics --- .../include/class/Diagnostics.class.php | 873 +++++++++++++----- pandora_console/include/functions.php | 4 +- pandora_console/include/functions_ui.php | 22 +- pandora_console/include/javascript/pandora.js | 25 +- pandora_console/include/styles/pandora.css | 46 + 5 files changed, 752 insertions(+), 218 deletions(-) diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index 211ae3ea9a..320c62fc3f 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -4,7 +4,7 @@ * * @category Console Class * @package Pandora FMS - * @subpackage Supervisor + * @subpackage Diagnostics * @version 1.0.0 * @license See below * @@ -37,16 +37,81 @@ require_once $config['homedir'].'/include/functions_io.php'; class Diagnostics { + /** + * Ajax controller page. + * + * @var string + */ + public $ajaxController; + /** - * Constructor. + * Constructor * - * @return class This object + * @param string $page Page. + * + * @return void */ - public function __construct() + public function __construct(string $page) { - echo 'hola'; - return $this; + global $config; + + // Check access. + check_login(); + + // Check Acl. + if (!check_acl($config['id_user'], 0, 'PM')) { + db_pandora_audit( + 'ACL Violation', + 'Trying to access diagnostic info' + ); + + if (is_ajax()) { + echo json_encode(['error' => 'noaccess']); + } + + include 'general/noaccess.php'; + exit; + } + + $this->ajaxController = $page; + } + + + /** + * Allowed methods to be called using AJAX request. + * + * @var array + */ + public $AJAXMethods = [ + 'getStatusInfo', + 'getPHPSetup', + 'getDatabaseSizeStats', + 'getDatabaseHealthStatus', + 'getDatabaseStatusInfo', + 'getSystemInfo', + 'getMySQLPerformanceMetrics', + 'getTablesFragmentation', + 'getPandoraFMSLogsDates', + 'getLicenceInformation', + 'getAttachmentFolder', + 'getInfoTagenteDatos', + 'getServerThreads', + 'datatablesDraw', + 'getChartAjax', + ]; + + + /** + * Checks if target method is available to be called using AJAX. + * + * @param string $method Target method. + * + * @return boolean True allowed, false not. + */ + public function ajaxMethod(string $method):bool + { + return in_array($method, $this->AJAXMethods); } @@ -59,167 +124,218 @@ class Diagnostics { global $config; + $textPdf = ''; + $textPdf .= html_print_image( + 'images/pdf.png', + true, + ['title' => __('PDF Report')] + ); + $textPdf .= ''; + + $textCsv = ''; + $textCsv .= html_print_image( + 'images/csv.png', + true, + ['title' => __('Csv Report')] + ); + $textCsv .= ''; + + $buttonsHeader = [ + 'diagnosticsPdf' => [ + 'text' => $textPdf, + 'active' => false, + ], + 'diagnosticsCsv' => [ + 'text' => $textCsv, + 'active' => false, + ], + ]; + + // Header. + ui_print_page_header( + __('Pandora FMS Diagnostic tool'), + 'images/gm_massive_operations.png', + false, + 'diagnostic_tool_tab', + true, + $buttonsHeader, + true + ); + /* * Info status pandoraFms. - */ - - $statusInfo = $this->getStatusInfo(); - - /* - * Print table in this case info. - */ - - $this->printTable($statusInfo); - - /* * PHP setup. - */ - - $phpSetup = $this->getPHPSetup(); - - /* - * Print table in this case PHP SETUP. - */ - - $this->printTable($phpSetup); - - /* * Database size stats. - */ - - $dataBaseSizeStats = $this->getDatabaseSizeStats(); - - /* - * Print table in this case Database size stats. - */ - - $this->printTable($dataBaseSizeStats); - - /* * Database health status. - */ - - $databaseHealthStatus = $this->getDatabaseHealthStatus(); - - /* - * Print table in this case Database health status. - */ - - $this->printTable($databaseHealthStatus); - - /* - * Database health status. - */ - - $getDatabaseStatusInfo = $this->getDatabaseStatusInfo(); - - /* - * Print table in this case Database status info. - */ - - $this->printTable($getDatabaseStatusInfo); - - if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { - /* - * System Info. - */ - - $getSystemInfo = $this->getSystemInfo(); - - /* - * Print table in this case System Info. - */ - - $this->printTable($getSystemInfo); - } - - /* + * Database status info. * System Info. - */ - - $getMySQLPerformanceMetrics = $this->getMySQLPerformanceMetrics(); - - /* - * Print table in this case System Info. - */ - - $this->printTable($getMySQLPerformanceMetrics); - - /* + * MySQL Performance metrics. * Tables fragmentation in the Pandora FMS database. - */ - - $getTablesFragmentation = $this->getTablesFragmentation(); - - /* - * Print table in this case Tables fragmentation in - * the Pandora FMS database. - */ - - $this->printTable($getTablesFragmentation); - - /* - * Tables fragmentation in the Pandora FMS database. - */ - - $getPandoraFMSLogsDates = $this->getPandoraFMSLogsDates(); - - /* - * Print table in this case Tables fragmentation in - * the Pandora FMS database. - */ - - $this->printTable($getPandoraFMSLogsDates); - - /* + * Pandora FMS logs dates. * Pandora FMS Licence Information. - */ - - $getLicenceInformation = $this->getLicenceInformation(); - - /* - * Print table in this case Pandora FMS Licence Information. - */ - - $this->printTable($getLicenceInformation); - - /* * Status of the attachment folder. - */ - - $getAttachmentFolder = $this->getAttachmentFolder(); - - /* - * Print table in this case Status of the attachment folder. - */ - - $this->printTable($getAttachmentFolder); - - /* * Information from the tagente_datos table. + * Pandora FMS server threads. */ - $getInfoTagenteDatos = $this->getInfoTagenteDatos(); + foreach ($this->AJAXMethods as $key => $method) { + switch ($method) { + case 'getStatusInfo': + $title = __('Info status pandoraFms'); + break; + + case 'getPHPSetup': + $title = __('PHP setup'); + break; + + case 'getDatabaseSizeStats': + $title = __('Database size stats'); + break; + + case 'getDatabaseHealthStatus': + $title = __('Database health status'); + break; + + case 'getDatabaseStatusInfo': + $title = __('Database status info'); + break; + + case 'getSystemInfo': + $title = __('System Info'); + break; + + case 'getMySQLPerformanceMetrics': + $title = __('MySQL Performance metrics'); + break; + + case 'getTablesFragmentation': + $title = __( + 'Tables fragmentation in the Pandora FMS database' + ); + break; + + case 'getPandoraFMSLogsDates': + $title = __('Pandora FMS logs dates'); + break; + + case 'getLicenceInformation': + $title = __('Pandora FMS Licence Information'); + break; + + case 'getAttachmentFolder': + $title = __('Status of the attachment folder'); + break; + + case 'getInfoTagenteDatos': + $title = __('Information from the tagente_datos table'); + break; + + case 'getServerThreads': + $title = __('Pandora FMS server threads'); + break; + + default: + // Not possible. + $title = ''; + break; + } + + if ($method !== 'datatablesDraw' && $method !== 'getChartAjax') { + echo '
'; + $this->printData($method, $title); + echo '
'; + } + } /* - * Print table in this case Information from the tagente_datos table. + * Agent id with name Master Server. */ - $this->printTable($getInfoTagenteDatos); + $agentIdMasterServer = $this->getAgentIdMasterServer(); - if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { - /* - * Pandora FMS server threads. - */ - - $getServerThreads = $this->getServerThreads(); + if ($agentIdMasterServer !== 0) { + $agentMonitoring = [ + 'chartAgentsUnknown' => [ + 'title' => __( + 'Graph of the Agents Unknown module.' + ), + 'nameModule' => 'Agents_Unknown', + 'idAgent' => $agentIdMasterServer, + ], + 'chartDatabaseMain' => [ + 'title' => __( + 'Graph of the Database Maintenance module.' + ), + 'nameModule' => 'Database Maintenance', + 'idAgent' => $agentIdMasterServer, + ], + 'chartFreeDiskSpoolDir' => [ + 'title' => __( + 'Graph of the Free Disk Spool Dir module.' + ), + 'nameModule' => 'FreeDisk_SpoolDir', + 'idAgent' => $agentIdMasterServer, + ], + 'chartFreeRAM' => [ + 'title' => __('Graph of the Free RAM module.'), + 'nameModule' => 'Free_RAM', + 'idAgent' => $agentIdMasterServer, + ], + 'chartQueuedModules' => [ + 'title' => __( + 'Graph of the Queued Modules module.' + ), + 'nameModule' => 'Queued_Modules', + 'idAgent' => $agentIdMasterServer, + ], + 'chartStatus' => [ + 'title' => __('Graph of the Status module.'), + 'nameModule' => 'Status', + 'idAgent' => $agentIdMasterServer, + ], + 'chartSystemLoadAVG' => [ + 'title' => __( + 'Graph of the System Load AVG module.' + ), + 'nameModule' => 'System_Load_AVG', + 'idAgent' => $agentIdMasterServer, + ], + 'chartExecutionTime' => [ + 'title' => __( + 'Graph of the Execution Time module.' + ), + 'nameModule' => 'Execution_time', + 'idAgent' => $agentIdMasterServer, + ], + ]; /* - * Print table in this case Pandora FMS server threads. + * Print table graps: + * Graph of the Agents Unknown module. + * Graph of the Database Maintenance module. + * Graph of the Free Disk Spool Dir module. + * Graph of the Free RAM module. + * Graph of the Queued Modules module. + * Graph of the Status module. + * Graph of the System Load AVG module. + * Graph of the Execution Time module. */ - $this->printTable($getServerThreads); + echo '
'; + echo __('Graphs modules that represent the self-monitoring system'); + echo '
'; + echo '
'; + foreach ($agentMonitoring as $key => $value) { + $this->printDataCharts($value); + } + + echo '
'; } + + echo ''; + } @@ -531,23 +647,26 @@ class Diagnostics { global $config; - $cpuModelName = 'cat /proc/cpuinfo | grep "model name" | tail -1 | cut -f 2 -d ":"'; - $cpuProcessor = 'cat /proc/cpuinfo | grep "processor" | wc -l'; - $ramMemTotal = 'cat /proc/meminfo | grep "MemTotal"'; + $result = []; + if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { + $cpuModelName = 'cat /proc/cpuinfo | grep "model name" | tail -1 | cut -f 2 -d ":"'; + $cpuProcessor = 'cat /proc/cpuinfo | grep "processor" | wc -l'; + $ramMemTotal = 'cat /proc/meminfo | grep "MemTotal"'; - $result = [ - 'error' => false, - 'data' => [ - 'cpuInfo' => [ - 'name' => __('CPU'), - 'value' => exec($cpuModelName).' x '.exec($cpuProcessor), + $result = [ + 'error' => false, + 'data' => [ + 'cpuInfo' => [ + 'name' => __('CPU'), + 'value' => exec($cpuModelName).' x '.exec($cpuProcessor), + ], + 'ramInfo' => [ + 'name' => __('RAM'), + 'value' => exec($ramMemTotal), + ], ], - 'ramInfo' => [ - 'name' => __('RAM'), - 'value' => exec($ramMemTotal), - ], - ], - ]; + ]; + } return json_encode($result); } @@ -562,13 +681,20 @@ class Diagnostics { global $config; - $variablesMsql = db_get_all_rows_sql('SHOW variables'); + $variablesMsql = db_get_all_rows_sql('SHOW VARIABLES'); $variablesMsql = array_reduce( $variablesMsql, function ($carry, $item) { $bytes = 1048576; $mega = 1024; switch ($item['Variable_name']) { + case 'sql_mode': + $name = __('Sql mode'); + $value = ($item['Value']); + $status = (empty($item['Value']) === true) ? 1 : 0; + $message = __('Must be empty'); + break; + case 'innodb_log_file_size': $name = __('InnoDB log file size'); $value = ($item['Value'] / $bytes); @@ -594,20 +720,16 @@ class Diagnostics $name = __('Maximun allowed packet'); $value = ($item['Value'] / $bytes); $status = (($item['Value'] / $bytes) >= 32) ? 1 : 0; - $message = __('Min. Recommended Value').' 32'; + $message = __('Min. Recommended Value').' 32M'; break; case 'innodb_buffer_pool_size': - if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { - $min = shell_exec( - "cat /proc/meminfo | grep -i total | head -1 | awk '{print $(NF-1)*0.4/1024}'" - ); - } - $name = __('InnoDB buffer pool size'); $value = ($item['Value'] / $mega); - $status = (($item['Value'] / $bytes) >= $min) ? 1 : 0; - $message = __('Min. Recommended Value').' '.$min; + $status = (($item['Value'] / $mega) >= 250) ? 1 : 0; + $message = __( + 'It has to be 40% of the server memory not recommended to be greater or less' + ); break; case 'sort_buffer_size': @@ -634,22 +756,22 @@ class Diagnostics case 'query_cache_size': $name = __('Query cache size'); $value = ($item['Value'] / $bytes); - $status = (($item['Value'] / $bytes) >= 24) ? 1 : 0; - $message = __('Min. Recommended Value').' 24'; + $status = (($item['Value'] / $bytes) >= 32) ? 1 : 0; + $message = __('Min. Recommended Value').' 32MB'; break; case 'query_cache_limit': $name = __('Query cache limit'); $value = ($item['Value'] / $bytes); - $status = (($item['Value'] / $bytes) >= 2) ? 1 : 0; - $message = __('Min. Recommended Value').' 2'; + $status = (($item['Value'] / $bytes) >= 256) ? 1 : 0; + $message = __('Min. Recommended Value').' 256K'; break; case 'innodb_lock_wait_timeout': $name = __('InnoDB lock wait timeout'); $value = $item['Value']; - $status = (($item['Value'] / $bytes) >= 120) ? 1 : 0; - $message = __('Min. Recommended Value').' 120'; + $status = (($item['Value'] / $bytes) >= 90) ? 1 : 0; + $message = __('Min. Recommended Value').' 90s'; break; case 'thread_cache_size': @@ -663,14 +785,14 @@ class Diagnostics $name = __('Thread stack'); $value = ($item['Value'] / $bytes); $status = (($item['Value'] / $bytes) >= 256) ? 1 : 0; - $message = __('Min. Recommended Value').' 256'; + $message = __('Min. Recommended Value').' 256K'; break; case 'max_connections': $name = __('Maximun connections'); $value = $item['Value']; - $status = (($item['Value'] / $bytes) >= 150) ? 1 : 0; - $message = __('Min. Recommended Value').' 150'; + $status = (($item['Value'] / $bytes) >= 90) ? 1 : 0; + $message = __('Min. Recommended Value').' 90'; break; case 'key_buffer_size': @@ -698,14 +820,14 @@ class Diagnostics $name = __('Query cache min-res-unit'); $value = ($item['Value'] / $bytes); $status = (($item['Value'] / $bytes) >= 2) ? 1 : 0; - $message = __('Min. Recommended Value').' 2'; + $message = __('Min. Recommended Value').' 2k'; break; case 'innodb_file_per_table': $name = __('InnoDB file per table'); $value = $item['Value']; - $status = (($item['Value'] / $bytes) >= 1) ? 1 : 0; - $message = __('Min. Recommended Value').' 1'; + $status = ($item['Value'] === 'ON') ? 1 : 0; + $message = __('Recommended ON'); break; default: @@ -912,10 +1034,15 @@ class Diagnostics WHERE id_tipo_modulo BETWEEN 6 AND 18' ); - $averageTime = number_format( - ((int) $totalModuleIntervalTime / (int) $totalNetworkModules), - 3 - ); + + $averageTime = 0; + if ($totalModuleIntervalTime !== false) { + $averageTime = number_format( + ((int) $totalModuleIntervalTime / (int) $totalNetworkModules), + 3 + ); + } + $moduleNetworkmsg = __( sprintf( 'The system is not overloaded (average time %d)', @@ -1075,32 +1202,18 @@ class Diagnostics $taStatus = 1; } - /* - $times = db_get_all_rows_sql('SELECT datos FROM tagente_datos WHERE id_agente_modulo = 29 ORDER BY utimestamp DESC LIMIT 2'); - hd($times); - if ($times[0]['datos'] > ($times[1]['datos'] * 1.2)) { - __('The execution time could be degrading. For a more extensive information of this data consult the Execution Time graph'); - } else { - __('The execution time is correct. For more information about this data, check the Execution Time graph'); - } - */ - $result = [ 'error' => false, 'data' => [ - 'agentDataCount' => [ + 'agentDataCount' => [ 'name' => __('Total data in tagente_datos table'), 'value' => $agentDataCount, ], - 'agentDataStatus' => [ + 'agentDataStatus' => [ 'name' => __('Tagente_datos table status'), 'value' => $taMsg, 'status' => $taStatus, ], - 'agentDataExecution' => [ - 'name' => __('Execution time degradation when executing a count'), - 'value' => 1, - ], ], ]; @@ -1117,6 +1230,10 @@ class Diagnostics { global $config; + if (strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') { + return []; + } + $totalServerThreads = shell_exec( 'ps -T aux | grep pandora_server | grep -v grep | wc -l' ); @@ -1130,7 +1247,7 @@ class Diagnostics $result = [ 'error' => false, 'data' => [ - 'totalServerThreads' => [ + [ 'name' => __('Total server threads'), 'value' => $totalServerThreads, ], @@ -1150,17 +1267,252 @@ class Diagnostics /** - * Paint table. + * Agent Id whit name is equal to Server Name. * - * @param string $statusInfo Json width status info. - * - * @return void + * @return integer Id agent module. */ - public function printTable(string $statusInfo): void + public function getAgentIdMasterServer(): int { global $config; - hd($statusInfo); + $serverName = db_get_value_sql( + 'SELECT `name` + FROM tserver + WHERE `name` IS NOT NULL + AND `master` > 0 + ORDER BY `master` DESC' + ); + $agentId = (int) db_get_value_sql( + sprintf( + 'SELECT id_agente + FROM tagente + WHERE nombre = "%s"', + $serverName + ) + ); + + if (isset($agentId) === false || is_numeric($agentId) === false) { + $agentId = 0; + } + + return $agentId; + } + + + /** + * Graph. + * + * @param integer $id Id agent. + * @param string $name Name module. + * @param boolean $image Chart interactive or only image. + * @param boolean $base64 Image or base64. + * + * @return string + */ + public function getChart( + int $id, + string $name, + bool $image=false, + bool $base64=false + ): string { + global $config; + + include_once $config['homedir'].'/include/functions_graph.php'; + $data = modules_get_agentmodule_id($name, $id); + $params = [ + 'agent_module_id' => $data['id_agente_modulo'], + 'period' => SECONDS_1MONTH, + 'date' => time(), + 'height' => '200', + 'only_image' => $image, + 'return_img_base_64' => $base64, + ]; + + return grafico_modulo_sparse($params); + } + + + /** + * Check pandoradb installed. + * + * @return string + */ + public function checkPandoraDB(): string + { + global $config; + $result = ''; + + if (isset($config['db_maintenance']) === false) { + $result .= '(*) '; + $result .= __( + 'Please check your Pandora Server setup and make sure that the database maintenance daemon is running.' + ); + $result .= ' '; + $result .= __( + 'It\' is very important to keep the database up-to-date to get the best performance and results in Pandora' + ); + } + + return $result; + } + + + /** + * Draw table. + * + * @param string $method Method. + * @param string $title Title. + * + * @return void + */ + public function printData(string $method, string $title): void + { + global $config; + + if (is_ajax()) { + // TODO: Call method. + echo $method; + } else { + // Datatables list. + try { + $columns = [ + [ + 'class' => 'datatables-td-title', + 'text' => 'name', + ], + [ + 'class' => 'datatables-td-max', + 'text' => 'value', + ], + 'message', + ]; + + $columnNames = [ + [ + 'style' => 'display:none;', + 'text' => '', + ], + [ + 'style' => 'display:none', + 'text' => '', + ], + [ + 'style' => 'display:none', + 'text' => '', + ], + ]; + + $tableId = $method.'_'.uniqid(); + // Load datatables user interface. + ui_print_datatable( + [ + 'id' => $tableId, + 'class' => 'info_table caption_table', + 'style' => 'width: 100%', + 'columns' => $columns, + 'column_names' => $columnNames, + 'ajax_data' => [ + 'method' => 'datatablesDraw', + 'name' => $method, + ], + 'ajax_url' => $this->ajaxController, + 'paging' => 0, + 'no_sortable_columns' => [-1], + 'caption' => $title, + ] + ); + } catch (Exception $e) { + echo $e->getMessage(); + } + } + } + + + /** + * Prepare params for getCarts. + * + * @return void + */ + public function getChartAjax():void + { + global $config; + + $params = json_decode( + io_safe_output(get_parameter('params', '')), + true + ); + + $return = ''; + if (isset($params['idAgent']) === true + && empty($params['idAgent']) === false + && isset($params['nameModule']) + && empty($params['nameModule']) === false + ) { + $return = $this->getChart( + $params['idAgent'], + $params['nameModule'] + ); + } + + exit($return); + } + + + /** + * Paint table with charts. + * + * @param array $params Info charts. + * + * @return void + */ + public function printDataCharts(array $params): void + { + global $config; + + if (!$params) { + $params = get_parameter('params'); + } + + if (is_ajax()) { + // TODO: Call method. + echo $method; + } else { + // Datatables list. + try { + $id = str_replace( + ' ', + '', + io_safe_output($params['nameModule']) + ); + echo '
'; + $settings = [ + 'type' => 'POST', + 'dataType' => 'html', + 'url' => ui_get_full_url( + 'ajax.php', + false, + false, + false + ), + 'data' => [ + 'page' => $this->ajaxController, + 'method' => 'getChartAjax', + 'params' => json_encode($params), + ], + ]; + + ?> + + getMessage(); + } + } } @@ -1209,4 +1561,107 @@ class Diagnostics } + /** + * Transforms a json object into a Datatables format. + * + * @return void + */ + public function datatablesDraw() + { + $method = get_parameter('name', ''); + if (method_exists($this, $method) === true) { + $data = json_decode($this->{$method}(), true); + } + + if (isset($data) === true && is_array($data) === true) { + $items = $data['data']; + $dataReduce = array_reduce( + array_keys($data['data']), + function ($carry, $key) use ($items) { + // Transforms array of arrays $data into an array + // of objects, making a post-process of certain fields. + if (isset($items[$key]['status']) === true) { + $acumValue = $items[$key]['value']; + if ($items[$key]['status'] === 1) { + $items[$key]['value'] = html_print_image( + 'images/exito.png', + true, + [ + 'title' => __('Succesfuly'), + 'style' => 'width:15px;', + ] + ); + } else { + $items[$key]['value'] = html_print_image( + 'images/error_1.png', + true, + [ + 'title' => __('Error'), + 'style' => 'width:15px;', + ] + ); + } + + $items[$key]['value'] .= ' '.$acumValue; + } + + // FIX for customer key. + if ($key === 'customerKey') { + $spanValue = ''.$items[$key]['value'].''; + $items[$key]['value'] = $spanValue; + } + + if (isset($items[$key]['message']) === false) { + $items[$key]['message'] = ''; + } + + $carry[] = (object) $items[$key]; + return $carry; + } + ); + } + + // Datatables format: RecordsTotal && recordsfiltered. + echo json_encode( + [ + 'data' => $dataReduce, + 'recordsTotal' => count($dataReduce), + 'recordsFiltered' => count($dataReduce), + ] + ); + } + + + /** + * Transforms a json object into a Datatables format. + * + * @return void + */ + public function exportPDF() + { + // TODO: TO BE CONTINUED. + $pdf = new PDFTranslator(); + + // Set font from font defined in report. + $pdf->custom_font = $report['custom_font']; + + $product_name = io_safe_output(get_product_name()); + $pdf->setMetadata( + __('Diagnostics Info'), + $product_name.' Enteprise', + $product_name, + __('Automated %s report for user defined report', $product_name) + ); + + $filename = ''; + + if ($filename !== '') { + $pdfObject->writePDFfile($filename); + } else { + $pdfObject->showPDF(); + } + + } + + } diff --git a/pandora_console/include/functions.php b/pandora_console/include/functions.php index 70eb7b8728..4ce47bac09 100644 --- a/pandora_console/include/functions.php +++ b/pandora_console/include/functions.php @@ -3881,11 +3881,11 @@ function generator_chart_to_pdf($type_graph_pdf, $params, $params_combined=false $img_content = join("\n", $result); if ($params['return_img_base_64']) { - // To be used in alerts + // To be used in alerts. $width_img = 500; return $img_content; } else { - // to be used in PDF files + // to be used in PDF files. $config['temp_images'][] = $img_path; return ''; } diff --git a/pandora_console/include/functions_ui.php b/pandora_console/include/functions_ui.php index 577e8e11ff..0c20dcafe8 100755 --- a/pandora_console/include/functions_ui.php +++ b/pandora_console/include/functions_ui.php @@ -2996,6 +2996,10 @@ function ui_print_datatable(array $parameters) $parameters['default_pagination'] = $config['block_size']; } + if (!isset($parameters['paging'])) { + $parameters['paging'] = true; + } + $no_sortable_columns = []; if (isset($parameters['no_sortable_columns'])) { $no_sortable_columns = json_encode($parameters['no_sortable_columns']); @@ -3156,7 +3160,7 @@ function ui_print_datatable(array $parameters) $table = ''; - $table .= ''; + $table .= ''; if (isset($parameters['column_names']) && is_array($parameters['column_names']) @@ -3205,7 +3209,7 @@ function ui_print_datatable(array $parameters) }, processing: true, serverSide: true, - paging: true, + paging: '.$parameters['paging'].', pageLength: '.$parameters['default_pagination'].', searching: false, responsive: true, @@ -3305,10 +3309,18 @@ function ui_print_datatable(array $parameters) $("#'.$form_id.'_search_bt").click(function (){ dt_'.$table_id.'.draw().page(0) - }); - }); + });'; -'; + if (isset($parameters['caption']) === true + && empty($parameters['caption']) === false + ) { + $js .= '$("#'.$table_id.'").append("");'; + $js .= '$(".datatables_thead_tr").css("height", 0);'; + } + + $js .= '});'; + + $js .= ''; // Order. $err_msg = '
'; diff --git a/pandora_console/include/javascript/pandora.js b/pandora_console/include/javascript/pandora.js index 33ab956a1f..b38ff66a30 100644 --- a/pandora_console/include/javascript/pandora.js +++ b/pandora_console/include/javascript/pandora.js @@ -1,3 +1,6 @@ +/* global $ */ +/* exported load_modal */ + var ENTERPRISE_DIR = "enterprise"; /* Function to hide/unhide a specific Div id */ @@ -1872,8 +1875,6 @@ function logo_preview(icon_name, icon_path, incoming_options) { } // Advanced Form control. -/* global $ */ -/* exported load_modal */ function load_modal(settings) { var AJAX_RUNNING = 0; var data = new FormData(); @@ -1987,3 +1988,23 @@ function load_modal(settings) { } }); } + +/** + * Function for AJAX request. + * + * @param {string} id Id container append data. + * @param {json} settings Json with settings. + * + * @return {void} + */ +function ajaxRequest(id, settings) { + $.ajax({ + type: settings.type, + dataType: settings.html, + url: settings.url, + data: settings.data, + success: function(data) { + $("#" + id).append(data); + } + }); +} diff --git a/pandora_console/include/styles/pandora.css b/pandora_console/include/styles/pandora.css index 459cc5c54d..71afe6b6f3 100644 --- a/pandora_console/include/styles/pandora.css +++ b/pandora_console/include/styles/pandora.css @@ -5903,3 +5903,49 @@ table.table_modal_alternate tr td:first-child { .flot-text { width: 101%; } + +.title-self-monitoring, +.caption_table caption { + text-align: center; + font-size: 1.5em; + font-weight: bolder; + color: #fff; + background: #282828; + padding: 8px; +} + +.datatables-td-title { + width: 25% !important; + font-weight: bolder; +} + +.datatables-td-max { + display: flex; + flex-direction: row; + flex-wrap: wrap; +} + +.datatables-td-max img { + margin-right: 10px; +} + +.datatables-td-max span { + width: 400px; + display: inline-block; + word-wrap: break-word; +} + +.container-self-monitoring { + display: flex; + flex-direction: row; + flex-wrap: wrap; +} + +.element-self-monitoring { + flex: 2 1 600px; +} + +.footer-self-monitoring { + margin: 30px; + font-style: italic; +} From b8d03e98c383e11096d876b28e7bd87ad4ebadad Mon Sep 17 00:00:00 2001 From: Daniel Barbero Date: Fri, 18 Oct 2019 15:23:23 +0200 Subject: [PATCH 04/11] pdf diagnostic --- .../include/class/Diagnostics.class.php | 35 +++++++------------ 1 file changed, 13 insertions(+), 22 deletions(-) diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index 320c62fc3f..afb41c016b 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -124,7 +124,10 @@ class Diagnostics { global $config; - $textPdf = ''; + $urlPdf = ui_get_full_url(false, false, false, false); + $urlPdf .= 'enterprise/operation/reporting/reporting_viewer_pdf.php'; + $textPdf = ''; + $textPdf .= html_print_image( 'images/pdf.png', true, @@ -1639,28 +1642,16 @@ class Diagnostics */ public function exportPDF() { + global $config; + // TODO: TO BE CONTINUED. - $pdf = new PDFTranslator(); - - // Set font from font defined in report. - $pdf->custom_font = $report['custom_font']; - - $product_name = io_safe_output(get_product_name()); - $pdf->setMetadata( - __('Diagnostics Info'), - $product_name.' Enteprise', - $product_name, - __('Automated %s report for user defined report', $product_name) - ); - - $filename = ''; - - if ($filename !== '') { - $pdfObject->writePDFfile($filename); - } else { - $pdfObject->showPDF(); - } - + enterprise_include_once('/include/class/Pdf.class.php'); + $pdf = new Pdf([]); + $pdf->setMetadata('el titulo', 'daniel', 'pepe', 'el sujeto'); + $pdf->setHeaderHTML('esto es el codigo html del header'); + $pdf->writeHTML('esto es el html del contenido'); + $pdf->setFooterHTML('esto es el footer'); + $pdf->writePDFfile(); } From e37af1598a5d155d2f401e56bdc467e322273137 Mon Sep 17 00:00:00 2001 From: Daniel Barbero Date: Mon, 21 Oct 2019 18:11:04 +0200 Subject: [PATCH 05/11] continue feedback diagnostics --- pandora_console/general/header.php | 68 ++- .../include/class/Diagnostics.class.php | 454 +++++++++++++----- pandora_console/include/functions_ui.php | 2 +- pandora_console/include/styles/pandora.css | 7 + pandora_console/tools/diagnostics.php | 4 +- 5 files changed, 416 insertions(+), 119 deletions(-) diff --git a/pandora_console/general/header.php b/pandora_console/general/header.php index 99bb38cc21..fa90cd9659 100644 --- a/pandora_console/general/header.php +++ b/pandora_console/general/header.php @@ -328,9 +328,26 @@ if ($config['menu_type'] == 'classic') { $header_autorefresh_counter .= $autorefresh_additional; $header_autorefresh_counter .= ''; + // Button for feedback pandora. + if (enterprise_installed()) { + $header_feedback = '
'; + $header_feedback .= ''; + $header_feedback .= html_print_image( + '/images/icono_warning.png', + true, + [ + 'title' => __('Feedback'), + 'id' => 'feedback-header', + 'alt' => __('Feedback'), + 'style' => 'cursor: pointer; width: 28px;', + ] + ); + $header_feedback .= '
'; + } + // Support. - if (defined('PANDORA_ENTERPRISE')) { + if (enterprise_installed()) { $header_support_link = 'https://support.artica.es/'; } else { $header_support_link = 'https://pandorafms.com/forums/'; @@ -388,9 +405,9 @@ if ($config['menu_type'] == 'classic') { echo '
'.$config['custom_title_header'].''.$config['custom_subtitle_header'].'
'.$header_searchbar.'
-
'.$header_chat, $header_autorefresh, $header_autorefresh_counter, $header_discovery, $servers_list, $header_support, $header_docu, $header_user, $header_logout.'
'; +
'.$header_chat, $header_autorefresh, $header_autorefresh_counter, $header_discovery, $servers_list, $header_feedback, $header_support, $header_docu, $header_user, $header_logout.'
'; ?> - + @@ -612,6 +629,44 @@ if ($config['menu_type'] == 'classic') { var fixed_header = ; var new_chat = ; + + /** + * Loads modal from AJAX to add feedback. + */ + function show_feedback() { + + var btn_ok_text = ''; + var btn_cancel_text = ''; + var title = ''; + var url = ''; + + console.log('entra'); + + load_modal({ + target: $('#modal-feedback-form'), + form: 'modal_form_feedback', + url: '', + modal: { + title: title, + ok: btn_ok_text, + cancel: btn_cancel_text, + }, + onshow: { + page: url, + method: 'formFeedback', + }, + onsubmit: { + page: url, + method: 'createdScheduleFeedbackTask', + } + }); + + } + $(document).ready (function () { // Check new notifications on a periodic way @@ -661,7 +716,12 @@ if ($config['menu_type'] == 'classic') { $("#ui_close_dialog_titlebar").click(function () { $("#agent_access").css("display",""); }); - + + // Feedback. + $("#feedback-header").click(function () { + show_feedback(); + }); + function blinkpubli(){ $(".publienterprise").delay(100).fadeTo(300,0.2).delay(100).fadeTo(300,1, blinkpubli); } diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index afb41c016b..9a5cc4190a 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -30,11 +30,12 @@ global $config; require_once $config['homedir'].'/include/functions_db.php'; require_once $config['homedir'].'/include/functions_io.php'; +require_once $config['homedir'].'/godmode/wizards/Wizard.main.php'; /** * Base class Diagnostics. */ -class Diagnostics +class Diagnostics extends Wizard { /** @@ -44,15 +45,21 @@ class Diagnostics */ public $ajaxController; + /** + * Print Html or Pdf view. + * + * @var boolean + */ + public $pdf; + /** - * Constructor + * Constructor. * - * @param string $page Page. - * - * @return void + * @param string $page Page. + * @param boolean $pdf PDF View. */ - public function __construct(string $page) + public function __construct(string $page, bool $pdf) { global $config; @@ -75,6 +82,7 @@ class Diagnostics } $this->ajaxController = $page; + $this->pdf = $pdf; } @@ -99,6 +107,8 @@ class Diagnostics 'getServerThreads', 'datatablesDraw', 'getChartAjax', + 'formFeedback', + 'createdScheduleFeedbackTask', ]; @@ -165,23 +175,58 @@ class Diagnostics true ); - /* - * Info status pandoraFms. - * PHP setup. - * Database size stats. - * Database health status. - * Database status info. - * System Info. - * MySQL Performance metrics. - * Tables fragmentation in the Pandora FMS database. - * Pandora FMS logs dates. - * Pandora FMS Licence Information. - * Status of the attachment folder. - * Information from the tagente_datos table. - * Pandora FMS server threads. - */ + // Print all Methods Diagnostic Info. + echo $this->printMethodsDiagnostigsInfo(); - foreach ($this->AJAXMethods as $key => $method) { + // Print all charts Monitoring. + echo $this->printCharts(); + + echo ''; + + } + + + /** + * Print Methods: + * Info status pandoraFms. + * PHP setup. + * Database size stats. + * Database health status. + * Database status info. + * System Info. + * MySQL Performance metrics. + * Tables fragmentation in the Pandora FMS database. + * Pandora FMS logs dates. + * Pandora FMS Licence Information. + * Status of the attachment folder. + * Information from the tagente_datos table. + * Pandora FMS server threads. + * + * @return string Html. + */ + public function printMethodsDiagnostigsInfo():string + { + $infoMethods = [ + 'getStatusInfo', + 'getPHPSetup', + 'getDatabaseSizeStats', + 'getDatabaseHealthStatus', + 'getDatabaseStatusInfo', + 'getSystemInfo', + 'getMySQLPerformanceMetrics', + 'getTablesFragmentation', + 'getPandoraFMSLogsDates', + 'getLicenceInformation', + 'getAttachmentFolder', + 'getInfoTagenteDatos', + 'getServerThreads', + ]; + + $return = ''; + + foreach ($infoMethods as $key => $method) { switch ($method) { case 'getStatusInfo': $title = __('Info status pandoraFms'); @@ -243,19 +288,37 @@ class Diagnostics break; } - if ($method !== 'datatablesDraw' && $method !== 'getChartAjax') { - echo '
'; - $this->printData($method, $title); - echo '
'; - } + $return .= '
'; + $return .= $this->printData($method, $title); + $return .= '
'; } + return $return; + } + + + /** + * Print table graps: + * Graph of the Agents Unknown module. + * Graph of the Database Maintenance module. + * Graph of the Free Disk Spool Dir module. + * Graph of the Free RAM module. + * Graph of the Queued Modules module. + * Graph of the Status module. + * Graph of the System Load AVG module. + * Graph of the Execution Time module. + * + * @return string + */ + public function printCharts() + { /* * Agent id with name Master Server. */ $agentIdMasterServer = $this->getAgentIdMasterServer(); + $result = ''; if ($agentIdMasterServer !== 0) { $agentMonitoring = [ 'chartAgentsUnknown' => [ @@ -312,33 +375,18 @@ class Diagnostics ], ]; - /* - * Print table graps: - * Graph of the Agents Unknown module. - * Graph of the Database Maintenance module. - * Graph of the Free Disk Spool Dir module. - * Graph of the Free RAM module. - * Graph of the Queued Modules module. - * Graph of the Status module. - * Graph of the System Load AVG module. - * Graph of the Execution Time module. - */ - - echo '
'; - echo __('Graphs modules that represent the self-monitoring system'); - echo '
'; - echo '
'; + $return .= '
'; + $return .= __('Graphs modules that represent the self-monitoring system'); + $return .= '
'; + $return .= '
'; foreach ($agentMonitoring as $key => $value) { - $this->printDataCharts($value); + $return .= $this->printDataCharts($value); } - echo '
'; + $return .= '
'; } - echo ''; - + return $return; } @@ -1366,15 +1414,15 @@ class Diagnostics * @param string $method Method. * @param string $title Title. * - * @return void + * @return string Return html. */ - public function printData(string $method, string $title): void + public function printData(string $method, string $title): string { global $config; if (is_ajax()) { // TODO: Call method. - echo $method; + $result = $method; } else { // Datatables list. try { @@ -1407,27 +1455,57 @@ class Diagnostics $tableId = $method.'_'.uniqid(); // Load datatables user interface. - ui_print_datatable( - [ - 'id' => $tableId, - 'class' => 'info_table caption_table', - 'style' => 'width: 100%', - 'columns' => $columns, - 'column_names' => $columnNames, - 'ajax_data' => [ - 'method' => 'datatablesDraw', - 'name' => $method, - ], - 'ajax_url' => $this->ajaxController, - 'paging' => 0, - 'no_sortable_columns' => [-1], - 'caption' => $title, - ] - ); + if ($this->pdf === false) { + $result = ui_print_datatable( + [ + 'id' => $tableId, + 'class' => 'info_table caption_table', + 'style' => 'width: 100%', + 'columns' => $columns, + 'column_names' => $columnNames, + 'ajax_data' => [ + 'method' => 'datatablesDraw', + 'name' => $method, + ], + 'ajax_url' => $this->ajaxController, + 'paging' => 0, + 'no_sortable_columns' => [-1], + 'caption' => $title, + 'print' => true, + ] + ); + } else { + $data = json_decode( + $this->datatablesDraw($method, true), + true + ); + + $table = new stdClass(); + $table->width = '100%'; + $table->class = ''; + $table->head = []; + $table->head_colspan[0] = 3; + $table->head[0] = $title; + $table->data = []; + + if (isset($data) === true && is_array($data) === true) { + $i = 0; + foreach ($data['data'] as $key => $value) { + $table->data[$i][0] = $value['name']; + $table->data[$i][1] = $value['value']; + $table->data[$i][2] = $value['message']; + $i++; + } + } + + $result = html_print_table($table, true); + } } catch (Exception $e) { - echo $e->getMessage(); + $result = $e->getMessage(); } } + + return $result; } @@ -1466,9 +1544,9 @@ class Diagnostics * * @param array $params Info charts. * - * @return void + * @return string Html. */ - public function printDataCharts(array $params): void + public function printDataCharts(array $params): string { global $config; @@ -1478,7 +1556,7 @@ class Diagnostics if (is_ajax()) { // TODO: Call method. - echo $method; + $return = $method; } else { // Datatables list. try { @@ -1487,35 +1565,49 @@ class Diagnostics '', io_safe_output($params['nameModule']) ); - echo '
'; - $settings = [ - 'type' => 'POST', - 'dataType' => 'html', - 'url' => ui_get_full_url( - 'ajax.php', - false, - false, - false - ), - 'data' => [ - 'page' => $this->ajaxController, - 'method' => 'getChartAjax', - 'params' => json_encode($params), - ], - ]; - ?> - - pdf === false) { + $return = '
'; + $settings = [ + 'type' => 'POST', + 'dataType' => 'html', + 'url' => ui_get_full_url( + 'ajax.php', + false, + false, + false + ), + 'data' => [ + 'page' => $this->ajaxController, + 'method' => 'getChartAjax', + 'params' => json_encode($params), + ], + ]; + + ?> + + '; + $return .= $this->getChart( + $params['idAgent'], + $params['nameModule'], + true, + false + ); + $return .= ''; + } } catch (Exception $e) { - echo $e->getMessage(); + $return = $e->getMessage(); } } + + return $return; } @@ -1565,13 +1657,21 @@ class Diagnostics /** - * Transforms a json object into a Datatables format. + * Undocumented function * - * @return void + * @param string|null $method Method data requested. + * @param boolean $return Type return. + * + * @return string|null */ - public function datatablesDraw() - { - $method = get_parameter('name', ''); + public function datatablesDraw( + ?string $method=null, + bool $return=false + ):?string { + if (isset($method) === false) { + $method = get_parameter('name', ''); + } + if (method_exists($this, $method) === true) { $data = json_decode($this->{$method}(), true); } @@ -1624,34 +1724,162 @@ class Diagnostics ); } - // Datatables format: RecordsTotal && recordsfiltered. - echo json_encode( + $result = json_encode( [ 'data' => $dataReduce, 'recordsTotal' => count($dataReduce), 'recordsFiltered' => count($dataReduce), ] ); + + // Datatables format: RecordsTotal && recordsfiltered. + if ($return === false) { + echo $result; + return null; + } else { + return $result; + } + } + + + public function createdScheduleFeedbackTask() + { + global $config; + + $email = 'daniel.barbero@artica.es'; + $subject = 'PandoraFMS Report '.$config['pandora_uid']; + $text = get_parameter('what-happened', ''); + $type = get_parameter('include-installation-data', ''); + + $idUserTask = db_get_value( + 'id', + 'tuser_task', + 'function_name', + 'cron_task_feedback_send_mail' + ); + + $parameters = [ + 0 => '0', + 1 => $email, + 2 => $subject, + 3 => $text, + 4 => $type, + 'first_execution' => strtotime('now'), + ]; + + $values = [ + 'id_usuario' => $config['id_user'], + 'id_user_task' => $idUserTask, + 'args' => serialize($parameters), + 'scheduled' => 'no', + 'id_grupo' => 0, + ]; + + $result = db_process_sql_insert('tuser_task_scheduled', $values); } /** - * Transforms a json object into a Datatables format. + * Print Diagnostics PDF report. * * @return void */ - public function exportPDF() + public static function exportPDF($filename=false) { global $config; - // TODO: TO BE CONTINUED. enterprise_include_once('/include/class/Pdf.class.php'); $pdf = new Pdf([]); - $pdf->setMetadata('el titulo', 'daniel', 'pepe', 'el sujeto'); - $pdf->setHeaderHTML('esto es el codigo html del header'); - $pdf->writeHTML('esto es el html del contenido'); - $pdf->setFooterHTML('esto es el footer'); - $pdf->writePDFfile(); + $diagnostics = new Diagnostics('tools/diagnostics', true); + $product_name = io_safe_output(get_product_name()); + $pdf->setMetadata( + __('Diagnostics Info'), + $product_name.' Enteprise', + $product_name, + __( + 'Automated %s report for user defined report', + $product_name + ) + ); + $pdf->setHeaderHTML(__('Diagnostics Info')); + + $pdf->addHTML( + $diagnostics->printMethodsDiagnostigsInfo() + ); + + $pdf->addHTML( + $diagnostics->printCharts() + ); + + $pdf->setFooterHTML(); + $pdf->writePDFfile($filename); + } + + + /** + * Print Diagnostics Form feedback. + * + * @return void + */ + public function formFeedback(): void + { + $form = [ + 'action' => '#', + 'id' => 'modal_form_feedback', + 'onsubmit' => 'return false;', + 'class' => 'modal', + ]; + + $inputs = []; + + $inputs[] = [ + 'label' => __('What happened').'?', + 'id' => 'div-what-happened', + 'class' => 'flex-row', + 'arguments' => [ + 'name' => 'what-happened', + 'type' => 'textarea', + 'value' => '', + 'return' => true, + 'rows' => 1, + 'columns' => 1, + 'size' => 25, + ], + ]; + + $inputs[] = [ + 'label' => __('Your email'), + 'class' => 'flex-row-baseline', + 'arguments' => [ + 'name' => 'email', + 'id' => 'email', + 'type' => 'text', + 'return' => true, + 'size' => 40, + ], + ]; + + $inputs[] = [ + 'label' => __('include installation data'), + 'class' => 'flex-row-vcenter', + 'arguments' => [ + 'name' => 'include-installation-data', + 'id' => 'include-installation-data', + 'type' => 'switch', + 'return' => true, + 'value' => 1, + ], + ]; + + exit( + $this->printForm( + [ + 'form' => $form, + 'inputs' => $inputs, + ], + true + ) + ); } diff --git a/pandora_console/include/functions_ui.php b/pandora_console/include/functions_ui.php index 0c20dcafe8..2a264bf0c1 100755 --- a/pandora_console/include/functions_ui.php +++ b/pandora_console/include/functions_ui.php @@ -3336,7 +3336,7 @@ function ui_print_datatable(array $parameters) $output = $include.$output; // Print datatable if needed. - if (!(isset($parameters['print']) && $parameters['print'] === false)) { + if (isset($parameters['print']) === false || $parameters['print'] === false) { echo $output; } diff --git a/pandora_console/include/styles/pandora.css b/pandora_console/include/styles/pandora.css index 71afe6b6f3..06ac52dad8 100644 --- a/pandora_console/include/styles/pandora.css +++ b/pandora_console/include/styles/pandora.css @@ -544,6 +544,13 @@ select:-internal-list-box { align-items: baseline; } +.flex-row-vcenter { + display: flex; + flex-direction: row; + flex-wrap: wrap; + align-items: center; +} + .nowrap { flex-wrap: nowrap; } diff --git a/pandora_console/tools/diagnostics.php b/pandora_console/tools/diagnostics.php index ad97d8b742..30be89efc4 100644 --- a/pandora_console/tools/diagnostics.php +++ b/pandora_console/tools/diagnostics.php @@ -32,11 +32,13 @@ global $config; require_once $config['homedir'].'/include/class/Diagnostics.class.php'; $ajaxPage = 'tools/diagnostics'; +$pdf = false; + // Control call flow. try { // User access and validation is being processed on class constructor. - $cs = new Diagnostics($ajaxPage); + $cs = new Diagnostics($ajaxPage, $pdf); } catch (Exception $e) { if (is_ajax()) { echo json_encode(['error' => '[Diagnostics]'.$e->getMessage() ]); From f06a55c6bba8d18c812f6e7532234dd18c8c961c Mon Sep 17 00:00:00 2001 From: Daniel Barbero Martin Date: Wed, 23 Oct 2019 19:50:57 +0200 Subject: [PATCH 06/11] continue feedback mail --- pandora_console/extras/pandora_diag.php | 796 +----------------- pandora_console/general/header.php | 14 +- .../include/class/Diagnostics.class.php | 295 +++++-- pandora_console/include/functions_html.php | 34 +- pandora_console/include/javascript/pandora.js | 71 +- .../include/styles/diagnostics.css | 58 ++ pandora_console/include/styles/pandora.css | 46 - 7 files changed, 385 insertions(+), 929 deletions(-) create mode 100644 pandora_console/include/styles/diagnostics.css diff --git a/pandora_console/extras/pandora_diag.php b/pandora_console/extras/pandora_diag.php index eb9a199456..b047106679 100644 --- a/pandora_console/extras/pandora_diag.php +++ b/pandora_console/extras/pandora_diag.php @@ -1,796 +1,2 @@ - - $value) { - db_process_sql_update( - 'tupdate_settings', - [db_escape_key_identifier('value') => $value], - [db_escape_key_identifier('key') => $key] - ); - } - - ui_print_success_message(__('License updated')); -} - -ui_require_javascript_file_enterprise('load_enterprise'); -enterprise_include_once('include/functions_license.php'); -$license = enterprise_hook('license_get_info'); - -$rows = db_get_all_rows_in_table('tupdate_settings'); - -$settings = new StdClass; -foreach ($rows as $row) { - $settings->{$row['key']} = $row['value']; -} - -echo ''; - - -function render_info($table) -{ - global $console_mode; - - $info = db_get_sql("SELECT COUNT(*) FROM $table"); - render_row($info, "DB Table $table"); -} - - -function render_info_data($query, $label) -{ - global $console_mode; - - $info = db_get_sql($query); - render_row($info, $label); -} - - -function render_row($data, $label) -{ - global $console_mode; - - if ($console_mode == 1) { - echo $label; - echo '|'; - echo $data; - echo "\n"; - } else { - echo '
'; - echo "'; - echo "'; - echo ''; - } -} - - -function get_value_sum($arr) -{ - foreach ($arr as $clave) { - foreach ($clave as $valor) { - if (is_numeric($valor) === true) { - $result += $valor; - } - } - } - - return $result; -} - - -function execution_time() -{ - $times = db_get_all_rows_sql('SELECT datos FROM tagente_datos WHERE id_agente_modulo = 29 ORDER BY utimestamp DESC LIMIT 2'); - if ($times[0]['datos'] > ($times[1]['datos'] * 1.2)) { - return "Warning Status   The execution time could be degrading. For a more extensive information of this data consult the Execution Time graph"; - } else { - return "Normal Status   The execution time is correct. For more information about this data, check the Execution Time graph"; - } -} - - -function get_logs_size($file) -{ - $file_name = '/var'.$file.''; - $size_server_log = filesize($file_name); - return $size_server_log; - -} - - -function get_status_logs($path) -{ - $status_server_log = ''; - $size_server_log = number_format(get_logs_size($path)); - $size_server_log = (0 + str_replace(',', '', $size_server_log)); - if ($size_server_log <= 10485760) { - $status_server_log = "Normal Status   You have less than 10 MB of logs"; - } else { - $status_server_log = "Warning Status   You have more than 10 MB of logs"; - } - - return $status_server_log; -} - - -function percentage_modules_per_agent() -{ - $status_average_modules = ''; - $total_agents = db_get_value_sql('SELECT count(*) FROM tagente'); - $total_modules = db_get_value_sql('SELECT count(*) FROM tagente_modulo'); - $average_modules_per_agent = ($total_modules / $total_agents); - if ($average_modules_per_agent <= 40) { - $status_average_modules = "Normal Status   The average of modules per agent is less than 40"; - } else { - $status_average_modules = "Warning Status  The average of modules per agent is more than 40. You can have performance problems"; - } - - return $status_average_modules; -} - - -function license_capacity() -{ - $license = enterprise_hook('license_get_info'); - $license_limit = $license['limit']; - $status_license_capacity = ''; - $current_count = db_get_value_sql('SELECT count(*) FROM tagente'); - if ($current_count > ($license_limit * 90 / 100)) { - $status_license_capacity = "Warning Status   License capacity exceeds 90 percent"; - } else { - $status_license_capacity = "Normal Status   License capacity is less than 90 percent"; - } - - return $status_license_capacity; -} - - -function status_license_params($license_param) -{ - $status_license_par = ''; - if ($license_param <= 0) { - $status_license_par = 'OFF'; - } else { - $status_license_par = 'ON'; - } - - return $status_license_par; -} - - -function interval_average_of_network_modules() -{ - $total_network_modules = db_get_value_sql('SELECT count(*) FROM tagente_modulo WHERE id_tipo_modulo BETWEEN 6 AND 18'); - $total_module_interval_time = db_get_value_sql('SELECT SUM(module_interval) FROM tagente_modulo WHERE id_tipo_modulo BETWEEN 6 AND 18'); - $average_time = ((int) $total_module_interval_time / $total_network_modules); - - if ($average_time < 180) { - $status_average_modules = "Warning Status   The system is overloaded (average time $average_time) and a very fine configuration is required"; - } else { - $status_average_modules = "Normal Status   The system is not overloaded (average time $average_time) "; - } - - if ($average_time == 0) { - $status_average_modules = "Normal Status   The system has no load"; - } - - return $status_average_modules; -} - - -$attachment_total_files = count(glob($config['homedir'].'/attachment/{*.*}', GLOB_BRACE)); - - -function files_attachment_folder($total_files) -{ - if ($total_files <= 700) { - $status_total_files = "Normal Status   The attached folder contains less than 700 files."; - } else { - $status_total_files = "Warning Status   The attached folder contains more than 700 files."; - } - - return $status_total_files; -} - - -$tagente_datos_size = db_get_value_sql('SELECT COUNT(*) FROM tagente_datos'); - - -function status_tagente_datos($tagente_datos_size) -{ - if ($tagente_datos_size <= 3000000) { - $tagente_datos_size = "Normal Status   The tagente_datos table contains an acceptable amount of data."; - } else { - $tagente_datos_size = "Warning Status   The tagente_datos table contains too much data. A historical database is recommended."; - } - - return $tagente_datos_size; -} - - -function status_values($val_rec, $val) -{ - if ($val_rec <= $val) { - return $val." (Min. Recommended Value ".$val_rec.')'; - } else { - return $val." (Min. Recommended Value ".$val_rec.") Warning Status"; - } -} - - -$tables_fragmentation = db_get_sql( - "SELECT (data_free/(index_length+data_length)) -as frag_ratio from information_schema.tables where DATA_FREE > 0 and table_name='tagente_datos' and table_schema='pandora'" -); -$db_size = db_get_all_rows_sql( - 'SELECT table_schema, -ROUND(SUM(data_length+index_length)/1024/1024,3) -FROM information_schema.TABLES -GROUP BY table_schema;' -); - -if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { - $total_server_threads = shell_exec('ps -T aux | grep pandora_server | grep -v grep | wc -l'); - $percentage_threads_ram = shell_exec("ps axo pmem,cmd | grep pandora_server | awk '{sum+=$1} END {print sum}'"); - $percentage_threads_cpu = shell_exec("ps axo pcpu,cmd | grep pandora_server | awk '{sum+=$1} END {print sum}'"); - $innodb_buffer_pool_size_min_rec_value = shell_exec("cat /proc/meminfo | grep -i total | head -1 | awk '{print $(NF-1)*0.4/1024}'"); -} - -$path_server_logs = '/log/pandora/pandora_server.log'; -$path_err_logs = '/log/pandora/pandora_server.error'; -$path_console_logs = '/www/html/pandora_console/pandora_console.log'; -$innodb_log_file_size_min_rec_value = '64M'; -$innodb_log_buffer_size_min_rec_value = '16M'; -$innodb_flush_log_at_trx_commit_min_rec_value = 0; -$query_cache_limit_min_rec_value = 2; -$max_allowed_packet_min_rec_value = 32; -$innodb_buffer_pool_size_min_rec_value = shell_exec("cat /proc/meminfo | grep -i total | head -1 | awk '{print $(NF-1)*0.4/1024}'"); -$sort_buffer_size_min_rec_value = 32; -$join_buffer_size_min_rec_value = 265; -$query_cache_type_min_rec_value = 'ON'; -$query_cache_size_min_rec_value = 24; -$innodb_lock_wait_timeout_max_rec_value = 120; -$tables_fragmentation_max_rec_value = 10; -$thread_cache_size_max_rec_value = 8; -$thread_stack_min_rec_value = 256; -$max_connections_max_rec_value = 150; -$key_buffer_size_min_rec_value = 256; -$read_buffer_size_min_rec_value = 32; -$read_rnd_buffer_size_min_rec_value = 32; -$query_cache_min_res_unit_min_rec_value = 2; -$innodb_file_per_table_min_rec_value = 1; - - -function status_fragmentation_tables($tables_fragmentation_max_rec_value, $tables_fragmentation) -{ - $status_tables_frag = ''; - if ($tables_fragmentation > $tables_fragmentation_max_rec_value) { - $status_tables_frag = "Warning Status   Table fragmentation is higher than recommended. They should be defragmented."; - } else { - $status_tables_frag = "Normal Status   Table fragmentation is correct."; - } - - return $status_tables_frag; -} - - -$console_mode = 1; -if (!isset($argc)) { - $console_mode = 0; -} - -if ($console_mode == 1) { - echo "\nPandora FMS PHP diagnostic tool v3.2 (c) Artica ST 2009-2010 \n"; - - if ($argc == 1 || in_array($argv[1], ['--help', '-help', '-h', '-?'])) { - echo "\nThis command line script contains information about Pandora FMS database. - This program can only be executed from the console, and it needs a parameter, the - full path to Pandora FMS 'config.php' file. - - Usage: - php pandora_diag.php path_to_pandora_console - - Example: - php pandora_diag.php /var/www/pandora_console - -"; - exit; - } - - if (preg_match('/[^a-zA-Z0-9_\/\.]|(\/\/)|(\.\.)/', $argv[1])) { - echo "Invalid path: $argv[1]. Always use absolute paths."; - exit; - } - - include $argv[1].'/include/config.php'; -} else { - if (file_exists('../include/config.php')) { - include '../include/config.php'; - } - - // Not from console, this is a web session. - if ((!isset($config['id_user'])) || (!check_acl($config['id_user'], 0, 'PM'))) { - echo "

You don't have privileges to use diagnostic tool

"; - echo '

Please login with an administrator account before try to use this tool

'; - exit; - } - - // Header. - ui_print_page_header( - __('Pandora FMS Diagnostic tool'), - '', - false, - 'diagnostic_tool_tab', - true - ); - - echo "
'.$parameters['caption'].'
".$label; - echo '
".$data; - echo '
"; - echo "'; -} - -render_row($build_version, 'Pandora FMS Build'); -render_row($pandora_version, 'Pandora FMS Version'); -render_info_data("SELECT value FROM tconfig where token ='MR'", 'Minor Release'); -render_row($config['homedir'], 'Homedir'); -render_row($config['homeurl'], 'HomeUrl'); -render_info_data( - "SELECT `value` - FROM tconfig - WHERE `token` = 'enterprise_installed'", - 'Enterprise installed' -); - - $full_key = db_get_sql( - "SELECT value - FROM tupdate_settings - WHERE `key` = 'customer_key'" - ); - - $compressed_key = substr($full_key, 0, 5).'...'.substr($full_key, -5); - - render_row($compressed_key, 'Update Key'); - - render_info_data( - "SELECT value - FROM tupdate_settings - WHERE `key` = 'updating_code_path'", - 'Updating code path' - ); - - render_info_data( - "SELECT value - FROM tupdate_settings - WHERE `key` = 'current_update'", - 'Current Update #' - ); - - - echo "'; - - - render_row(phpversion(), 'PHP Version'); - - render_row(ini_get('max_execution_time').' seconds', 'PHP Max execution time'); - - render_row(ini_get('max_input_time').' seconds', 'PHP Max input time'); - - render_row(ini_get('memory_limit'), 'PHP Memory limit'); - - render_row(ini_get('session.cookie_lifetime'), 'Session cookie lifetime'); - - echo "'; - - render_info_data('SELECT COUNT(*) FROM tagente', 'Total agents'); - render_info_data('SELECT COUNT(*) FROM tagente_modulo', 'Total modules'); - render_info_data('SELECT COUNT(*) FROM tgrupo', 'Total groups'); - render_info_data('SELECT COUNT(*) FROM tagente_datos', 'Total module data records'); - render_info_data('SELECT COUNT(*) FROM tagent_access', 'Total agent access record'); - render_info_data('SELECT COUNT(*) FROM tevento', 'Total events'); - - if ($config['enterprise_installed']) { - render_info_data('SELECT COUNT(*) FROM ttrap', 'Total traps'); - } - - render_info_data('SELECT COUNT(*) FROM tusuario', 'Total users'); - render_info_data('SELECT COUNT(*) FROM tsesion', 'Total sessions'); - - echo "'; - - render_info_data( - 'SELECT COUNT( DISTINCT tagente.id_agente) - FROM tagente_estado, tagente, tagente_modulo - WHERE tagente.disabled = 0 - AND tagente_modulo.id_agente_modulo = tagente_estado.id_agente_modulo - AND tagente_modulo.disabled = 0 - AND tagente_estado.id_agente = tagente.id_agente - AND tagente_estado.estado = 3', - 'Total unknown agents' - ); - - render_info_data( - 'SELECT COUNT(tagente_estado.estado) - FROM tagente_estado - WHERE tagente_estado.estado = 4', - 'Total not-init modules' - ); - - - $last_run_difference = ''; - - $diferencia = (time() - date( - db_get_sql( - "SELECT `value` - FROM tconfig - WHERE `token` = 'db_maintance'" - ) - )); - - $last_run_difference_months = 0; - $last_run_difference_weeks = 0; - $last_run_difference_days = 0; - $last_run_difference_minutos = 0; - $last_run_difference_seconds = 0; - - while ($diferencia >= 2419200) { - $diferencia -= 2419200; - $last_run_difference_months++; - } - - while ($diferencia >= 604800) { - $diferencia -= 604800; - $last_run_difference_weeks++; - } - - while ($diferencia >= 86400) { - $diferencia -= 86400; - $last_run_difference_days++; - } - - while ($diferencia >= 3600) { - $diferencia -= 3600; - $last_run_difference_hours++; - } - - while ($diferencia >= 60) { - $diferencia -= 60; - $last_run_difference_minutes++; - } - - $last_run_difference_seconds = $diferencia; - - if ($last_run_difference_months > 0) { - $last_run_difference .= $last_run_difference_months.'month/s '; - } - - if ($last_run_difference_weeks > 0) { - $last_run_difference .= $last_run_difference_weeks.' week/s '; - } - - if ($last_run_difference_days > 0) { - $last_run_difference .= $last_run_difference_days.' day/s '; - } - - if ($last_run_difference_hours > 0) { - $last_run_difference .= $last_run_difference_hours.' hour/s '; - } - - if ($last_run_difference_minutes > 0) { - $last_run_difference .= $last_run_difference_minutes.' minute/s '; - } - - $last_run_difference .= $last_run_difference_seconds.' second/s ago'; - - render_row( - date( - 'Y/m/d H:i:s', - db_get_sql( - "SELECT `value` - FROM tconfig - WHERE `token` = 'db_maintance'" - ) - ).' ('.$last_run_difference.')'.' *', - 'PandoraDB Last run' - ); - - echo "'; - - switch ($config['dbtype']) { - case 'mysql': - render_info_data( - "SELECT `value` - FROM tconfig - WHERE `token` = 'db_scheme_first_version'", - 'DB Schema Version (first installed)' - ); - render_info_data( - "SELECT `value` - FROM tconfig - WHERE `token` = 'db_scheme_version'", - 'DB Schema Version (actual)' - ); - render_info_data( - "SELECT `value` - FROM tconfig - WHERE `token` = 'db_scheme_build'", - 'DB Schema Build' - ); - - render_row(get_value_sum($db_size).'M', 'DB Size'); - - - if (strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN') { - echo "'; - - $output = 'cat /proc/cpuinfo | grep "model name" | tail -1 | cut -f 2 -d ":"'; - $output2 = 'cat /proc/cpuinfo | grep "processor" | wc -l'; - - render_row(exec($output).' x '.exec($output2), 'CPU'); - - $output = 'cat /proc/meminfo | grep "MemTotal"'; - - render_row(exec($output), 'RAM'); - } - break; - - case 'postgresql': - render_info_data( - "SELECT \"value\" - FROM tconfig - WHERE \"token\" = 'db_scheme_version'", - 'DB Schema Version' - ); - render_info_data( - "SELECT \"value\" - FROM tconfig - WHERE \"token\" = 'db_scheme_build'", - 'DB Schema Build' - ); - render_info_data( - "SELECT \"value\" - FROM tconfig - WHERE \"token\" = 'enterprise_installed'", - 'Enterprise installed' - ); - render_row( - date( - 'Y/m/d H:i:s', - db_get_sql( - "SELECT \"value\" - FROM tconfig WHERE \"token\" = 'db_maintance'" - ) - ), - 'PandoraDB Last run' - ); - - render_info_data( - "SELECT value - FROM tupdate_settings - WHERE \"key\" = 'customer_key';", - 'Update Key' - ); - render_info_data( - "SELECT value - FROM tupdate_settings - WHERE \"key\" = 'updating_code_path'", - 'Updating code path' - ); - render_info_data( - "SELECT value - FROM tupdate_settings - WHERE \"key\" = 'current_update'", - 'Current Update #' - ); - break; - - case 'oracle': - render_info_data( - "SELECT value - FROM tconfig - WHERE token = 'db_scheme_version'", - 'DB Schema Version' - ); - render_info_data( - "SELECT value - FROM tconfig - WHERE token = 'db_scheme_build'", - 'DB Schema Build' - ); - render_info_data( - "SELECT value - FROM tconfig - WHERE token = 'enterprise_installed'", - 'Enterprise installed' - ); - render_row( - db_get_sql( - "SELECT value - FROM tconfig - WHERE token = 'db_maintance'" - ), - 'PandoraDB Last run' - ); - - render_info_data( - 'SELECT '.db_escape_key_identifier('value')." FROM tupdate_settings - WHERE \"key\" = 'customer_key'", - 'Update Key' - ); - render_info_data( - 'SELECT '.db_escape_key_identifier('value')." FROM tupdate_settings - WHERE \"key\" = 'updating_code_path'", - 'Updating code path' - ); - render_info_data( - 'SELECT '.db_escape_key_identifier('value')." FROM tupdate_settings - WHERE \"key\" = 'current_update'", - 'Current Update #' - ); - break; - } - - $innodb_log_file_size = (db_get_value_sql('SELECT @@innodb_log_file_size') / 1048576); - $innodb_log_buffer_size = (db_get_value_sql('SELECT @@innodb_log_buffer_size') / 1048576); - $innodb_flush_log_at_trx_commit = db_get_value_sql('SELECT @@innodb_flush_log_at_trx_commit'); - $max_allowed_packet = (db_get_value_sql('SELECT @@max_allowed_packet') / 1048576); - $innodb_buffer_pool_size = (db_get_value_sql('SELECT @@innodb_buffer_pool_size') / 1024); - $sort_buffer_size = number_format((db_get_value_sql('SELECT @@sort_buffer_size') / 1024), 2); - $join_buffer_size = (db_get_value_sql('SELECT @@join_buffer_size') / 1024); - $query_cache_type = db_get_value_sql('SELECT @@query_cache_type'); - $query_cache_size = (db_get_value_sql('SELECT @@query_cache_size') / 1048576); - $query_cache_limit = (db_get_value_sql('SELECT @@query_cache_limit') / 1048576); - $innodb_lock_wait_timeout = db_get_value_sql('SELECT @@innodb_lock_wait_timeout'); - $thread_cache_size = db_get_value_sql('SELECT @@thread_cache_size'); - $thread_stack = (db_get_value_sql('SELECT @@thread_stack') / 1024); - $max_connections = db_get_value_sql('SELECT @@max_connections'); - $key_buffer_size = (db_get_value_sql('SELECT @@key_buffer_size') / 1024); - $read_buffer_size = (db_get_value_sql('SELECT @@read_buffer_size') / 1024); - $read_rnd_buffer_size = (db_get_value_sql('SELECT @@read_rnd_buffer_size') / 1024); - $query_cache_min_res_unit = (db_get_value_sql('SELECT @@query_cache_min_res_unit') / 1024); - $innodb_file_per_table = db_get_value_sql('SELECT @@innodb_file_per_table'); - echo "'; - - render_row(status_values($innodb_log_file_size_min_rec_value, $innodb_log_file_size), 'InnoDB log file size ', 'InnoDB log file size '); - render_row(status_values($innodb_log_buffer_size_min_rec_value, $innodb_log_buffer_size), 'InnoDB log buffer size ', 'InnoDB log buffer size '); - render_row(status_values($innodb_flush_log_at_trx_commit_min_rec_value, $innodb_flush_log_at_trx_commit), 'InnoDB flush log at trx-commit ', 'InnoDB flush log at trx-commit '); - render_row(status_values($max_allowed_packet_min_rec_value, $max_allowed_packet), 'Maximun allowed packet ', 'Maximun allowed packet '); - render_row(status_values($innodb_buffer_pool_size_min_rec_value, $innodb_buffer_pool_size), 'InnoDB buffer pool size ', 'InnoDB buffer pool size '); - render_row(status_values($sort_buffer_size_min_rec_value, $sort_buffer_size), 'Sort buffer size ', 'Sort buffer size '); - render_row(status_values($join_buffer_size_min_rec_value, $join_buffer_size), 'Join buffer size ', 'Join buffer size '); - render_row(status_values($query_cache_type_min_rec_value, $query_cache_type), 'Query cache type ', 'Query cache type '); - render_row(status_values($query_cache_size_min_rec_value, $query_cache_size), 'Query cache size ', 'Query cache size '); - render_row(status_values($query_cache_limit_min_rec_value, $query_cache_limit), 'Query cache limit ', 'Query cache limit '); - render_row(status_values($innodb_lock_wait_timeout_max_rec_value, $innodb_lock_wait_timeout), 'InnoDB lock wait timeout ', 'InnoDB lock wait timeout '); - render_row(status_values($thread_cache_size_max_rec_value, $thread_cache_size), 'Thread cache size ', 'Thread cache size '); - render_row(status_values($thread_stack_min_rec_value, $thread_stack), 'Thread stack ', 'Thread stack '); - render_row(status_values($max_connections_max_rec_value, $max_connections), 'Maximum connections ', 'Maximun connections '); - render_row(status_values($key_buffer_size_min_rec_value, $key_buffer_size), 'Key buffer size ', 'Key buffer size '); - render_row(status_values($read_buffer_size_min_rec_value, $read_buffer_size), 'Read buffer size ', 'Read buffer size '); - render_row(status_values($read_rnd_buffer_size_min_rec_value, $read_rnd_buffer_size), 'Read rnd-buffer size ', 'Read rnd-buffer size '); - render_row(status_values($query_cache_min_res_unit_min_rec_value, $query_cache_min_res_unit), 'Query cache min-res-unit ', 'Query cache min-res-unit '); - render_row(status_values($innodb_file_per_table_min_rec_value, $innodb_file_per_table), 'InnoDB file per table ', 'InnoDB file per table '); - echo "'; - - - - render_row($tables_fragmentation_max_rec_value.'%', 'Tables fragmentation (maximum recommended value)'); - render_row(number_format($tables_fragmentation, 2).'%', 'Tables fragmentation (current value)'); - render_row(status_fragmentation_tables($tables_fragmentation_max_rec_value, $tables_fragmentation), 'Table fragmentation status'); - - echo "'; - - render_row(number_format((get_logs_size($path_server_logs) / 1048576), 3).'M', 'Size server logs (current value)'); - render_row(get_status_logs($path_server_logs), 'Status server logs'); - render_row(number_format((get_logs_size($path_err_logs) / 1048576), 3).'M', 'Size error logs (current value)'); - render_row(get_status_logs($path_err_logs), 'Status error logs'); - render_row(number_format((get_logs_size($path_console_logs) / 1048576), 3).'M', 'Size console logs (current value)'); - render_row(get_status_logs($path_console_logs), 'Status console logs'); - - echo "'; - - render_row(html_print_textarea('keys[customer_key]', 10, 255, $settings->customer_key, 'style="height:40px; width:450px;"', true), 'Customer key'); - render_row($license['expiry_date'], $license['expiry_caption']); - render_row($license['limit'].' agents', 'Platform Limit'); - render_row($license['count'].' agents', 'Current Platform Count'); - render_row($license['count_enabled'].' agents', 'Current Platform Count (enabled: items)'); - render_row($license['count_disabled'].' agents', 'Current Platform Count (disabled: items)'); - render_row($license['license_mode'], 'License Mode'); - render_row(status_license_params($license['nms']), 'Network Management System'); - render_row(status_license_params($license['dhpm']), 'Satellite'); - render_row($license['licensed_to'], 'Licensed to'); - render_row(license_capacity(), 'Status of agents capacity'); - render_row(percentage_modules_per_agent(), 'Status of average modules per agent'); - render_row(interval_average_of_network_modules(), 'Interval average of the network modules'); - - echo "'; - - render_row($attachment_total_files, 'Total files in the attached folder'); - render_row(files_attachment_folder($attachment_total_files), 'Status of the attachment folder'); - - echo "'; - - render_row($tagente_datos_size, 'Total data in tagente_datos table'); - render_row(status_tagente_datos($tagente_datos_size), 'Tangente_datos table status'); - render_row(execution_time(), 'Execution time degradation when executing a count'); - - echo "'; - - render_row($total_server_threads, 'Total server threads'); - render_row($percentage_threads_ram.'%', 'Percentage of threads used by the RAM'); - render_row($percentage_threads_cpu.'%', 'Percentage of threads used by the CPU'); - - echo "'; - - $server_name = db_get_value_sql('SELECT name FROM tserver WHERE master = 1'); - $agent_id = db_get_value_sql("SELECT id_agente FROM tagente WHERE nombre = '$server_name'"); - - $id_modules = agents_get_modules($agent_id); - - $id_modules = [ - modules_get_agentmodule_id('Agents_Unknown', $agent_id), - modules_get_agentmodule_id('Database Maintenance', $agent_id), - modules_get_agentmodule_id('FreeDisk_SpoolDir', $agent_id), - modules_get_agentmodule_id('Free_RAM', $agent_id), - modules_get_agentmodule_id('Queued_Modules', $agent_id), - modules_get_agentmodule_id('Status', $agent_id), - modules_get_agentmodule_id('System_Load_AVG', $agent_id), - modules_get_agentmodule_id('Execution_time', $agent_id), - ]; - - foreach ($id_modules as $id_module) { - $params = [ - 'agent_module_id' => $id_module['id_agente_modulo'], - 'period' => SECONDS_1MONTH, - 'date' => time(), - 'height' => '150', - ]; - render_row(grafico_modulo_sparse($params), 'Graph of the '.$id_module['nombre'].' module.'); - } - - if ($console_mode == 0) { - echo '
".__('Pandora status info').'
".__('PHP setup').'
".__('Database size stats').'
".__('Database sanity').'
".__('Database status info').'
".__('System info').'
".__('MySQL Performance metrics').' '.ui_print_help_icon('performance_metrics_tab', true).'
".__('Tables fragmentation in the Pandora FMS database').'
".__(' Pandora FMS logs dates').'
".__(' Pandora FMS Licence Information').'
".__(' Status of the attachment folder').'
".__(' Information from the tagente_datos table').'
".__(' Pandora FMS server threads').'
".__(' Graphs modules that represent the self-monitoring system').'
'; - } - - echo "
"; - - echo ''.__( - '(*) Please check your Pandora Server setup and make sure that the database maintenance daemon is running. It\' is very important to - keep the database up-to-date to get the best performance and results in Pandora' - ).'


'; +// remove file. diff --git a/pandora_console/general/header.php b/pandora_console/general/header.php index fa90cd9659..70978bbcb5 100644 --- a/pandora_console/general/header.php +++ b/pandora_console/general/header.php @@ -332,6 +332,7 @@ if ($config['menu_type'] == 'classic') { if (enterprise_installed()) { $header_feedback = '
'; $header_feedback .= ''; + $header_feedback .= ''; $header_feedback .= html_print_image( '/images/icono_warning.png', true, @@ -627,7 +628,7 @@ if ($config['menu_type'] == 'classic') { }); var fixed_header = ; - + var new_chat = ; /** @@ -644,8 +645,6 @@ if ($config['menu_type'] == 'classic') { var title = ''; var url = ''; - console.log('entra'); - load_modal({ target: $('#modal-feedback-form'), form: 'modal_form_feedback', @@ -662,9 +661,11 @@ if ($config['menu_type'] == 'classic') { onsubmit: { page: url, method: 'createdScheduleFeedbackTask', - } + dataType: 'json', + }, + ajax_callback: generalShowMsg, + idMsgCallback: 'msg-header', }); - } $(document).ready (function () { @@ -719,6 +720,9 @@ if ($config['menu_type'] == 'classic') { // Feedback. $("#feedback-header").click(function () { + // Clean DOM. + $("#feedback-header").empty(); + // Function charge Modal. show_feedback(); }); diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index 9a5cc4190a..5fdeafa934 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -59,8 +59,10 @@ class Diagnostics extends Wizard * @param string $page Page. * @param boolean $pdf PDF View. */ - public function __construct(string $page, bool $pdf) - { + public function __construct( + string $page='tools/diagnostics', + bool $pdf=false + ) { global $config; // Check access. @@ -105,6 +107,7 @@ class Diagnostics extends Wizard 'getAttachmentFolder', 'getInfoTagenteDatos', 'getServerThreads', + 'getShowEngine', 'datatablesDraw', 'getChartAjax', 'formFeedback', @@ -134,35 +137,7 @@ class Diagnostics extends Wizard { global $config; - $urlPdf = ui_get_full_url(false, false, false, false); - $urlPdf .= 'enterprise/operation/reporting/reporting_viewer_pdf.php'; - $textPdf = ''; - - $textPdf .= html_print_image( - 'images/pdf.png', - true, - ['title' => __('PDF Report')] - ); - $textPdf .= ''; - - $textCsv = ''; - $textCsv .= html_print_image( - 'images/csv.png', - true, - ['title' => __('Csv Report')] - ); - $textCsv .= ''; - - $buttonsHeader = [ - 'diagnosticsPdf' => [ - 'text' => $textPdf, - 'active' => false, - ], - 'diagnosticsCsv' => [ - 'text' => $textCsv, - 'active' => false, - ], - ]; + ui_require_css_file('diagnostics'); // Header. ui_print_page_header( @@ -170,8 +145,6 @@ class Diagnostics extends Wizard 'images/gm_massive_operations.png', false, 'diagnostic_tool_tab', - true, - $buttonsHeader, true ); @@ -184,7 +157,6 @@ class Diagnostics extends Wizard echo ''; - } @@ -224,6 +196,10 @@ class Diagnostics extends Wizard 'getServerThreads', ]; + if ($this->pdf === true) { + $infoMethods[] = 'getShowEngine'; + } + $return = ''; foreach ($infoMethods as $key => $method) { @@ -282,6 +258,10 @@ class Diagnostics extends Wizard $title = __('Pandora FMS server threads'); break; + case 'getShowEngine': + $title = __('SQL show engine innodb status'); + break; + default: // Not possible. $title = ''; @@ -376,7 +356,9 @@ class Diagnostics extends Wizard ]; $return .= '
'; - $return .= __('Graphs modules that represent the self-monitoring system'); + $return .= __( + 'Graphs modules that represent the self-monitoring system' + ); $return .= '
'; $return .= '
'; foreach ($agentMonitoring as $key => $value) { @@ -1298,7 +1280,7 @@ class Diagnostics extends Wizard $result = [ 'error' => false, 'data' => [ - [ + 'totalServerThreads' => [ 'name' => __('Total server threads'), 'value' => $totalServerThreads, ], @@ -1317,6 +1299,52 @@ class Diagnostics extends Wizard } + /** + * SQL show engine innodb status. + * + * @return string + */ + public function getShowEngine(): string + { + global $config; + + try { + // Trick to avoid showing error in case + // you don't have enough permissions. + $backup = error_reporting(); + error_reporting(0); + $innodb = db_get_all_rows_sql('show engine innodb status'); + error_reporting($backup); + } catch (Exception $e) { + $innodb['Status'] = $e->getMessage(); + } + + $result = []; + if (isset($innodb[0]['Status']) === true + && $innodb[0]['Status'] !== false + ) { + $lenght = strlen($innodb[0]['Status']); + + $data = []; + for ($i = 0; $i < $lenght; $i = ($i + 500)) { + $str = substr($innodb[0]['Status'], $i, ($i + 500)); + $data['showEngine-'.$i] = [ + 'name' => '', + 'value' => '
'.$str.'
', + ]; + } + + $result = [ + 'error' => false, + 'data' => $data, + 'id' => 'showEngine', + ]; + } + + return json_encode($result); + } + + /** * Agent Id whit name is equal to Server Name. * @@ -1482,13 +1510,26 @@ class Diagnostics extends Wizard $table = new stdClass(); $table->width = '100%'; - $table->class = ''; + $table->class = 'pdf-report'; + $table->style = []; + $table->style[0] = 'font-weight: bolder;'; + + // FIX tables break content. + if ($data['idTable'] === 'showEngine') { + $table->styleTable = 'page-break-inside: auto;'; + } else { + $table->autosize = 1; + } + $table->head = []; $table->head_colspan[0] = 3; $table->head[0] = $title; $table->data = []; - if (isset($data) === true && is_array($data) === true) { + if (isset($data) === true + && is_array($data) === true + && count($data) > 0 + ) { $i = 0; foreach ($data['data'] as $key => $value) { $table->data[$i][0] = $value['name']; @@ -1676,7 +1717,11 @@ class Diagnostics extends Wizard $data = json_decode($this->{$method}(), true); } - if (isset($data) === true && is_array($data) === true) { + $result = []; + if (isset($data) === true + && is_array($data) === true + && count($data) > 0 + ) { $items = $data['data']; $dataReduce = array_reduce( array_keys($data['data']), @@ -1711,6 +1756,17 @@ class Diagnostics extends Wizard // FIX for customer key. if ($key === 'customerKey') { $spanValue = ''.$items[$key]['value'].''; + if ($this->pdf === true) { + $spanValue = ''; + $spanValue .= wordwrap( + $items[$key]['value'], + 10, + "\n", + true + ); + $spanValue .= ''; + } + $items[$key]['value'] = $spanValue; } @@ -1722,34 +1778,37 @@ class Diagnostics extends Wizard return $carry; } ); - } - $result = json_encode( - [ + $result = [ 'data' => $dataReduce, 'recordsTotal' => count($dataReduce), 'recordsFiltered' => count($dataReduce), - ] - ); + 'idTable' => (isset($data['id']) === true) ? $data['id'] : '', + ]; + } // Datatables format: RecordsTotal && recordsfiltered. if ($return === false) { - echo $result; + echo json_encode($result); return null; } else { - return $result; + return json_encode($result); } } - public function createdScheduleFeedbackTask() + /** + * Create cron task form feedback. + * + * @return void Json result AJAX request. + */ + public function createdScheduleFeedbackTask():void { global $config; - $email = 'daniel.barbero@artica.es'; $subject = 'PandoraFMS Report '.$config['pandora_uid']; $text = get_parameter('what-happened', ''); - $type = get_parameter('include-installation-data', ''); + $attachment = get_parameter_switch('include_installation_data', 0); $idUserTask = db_get_value( 'id', @@ -1758,15 +1817,17 @@ class Diagnostics extends Wizard 'cron_task_feedback_send_mail' ); + // Params for send mail with cron. $parameters = [ 0 => '0', 1 => $email, 2 => $subject, 3 => $text, - 4 => $type, + 4 => $attachment, 'first_execution' => strtotime('now'), ]; + // Values insert task cron. $values = [ 'id_usuario' => $config['id_user'], 'id_user_task' => $idUserTask, @@ -1775,24 +1836,54 @@ class Diagnostics extends Wizard 'id_grupo' => 0, ]; - $result = db_process_sql_insert('tuser_task_scheduled', $values); + $result = db_process_sql_insert( + 'tuser_task_scheduled', + $values + ); + + $error = 1; + if ($result === false) { + $error = 0; + } + + $return = [ + 'error' => $error, + 'title' => [ + __('Failed'), + __('Success'), + ], + 'text' => [ + ui_print_error_message(__('Mal'), '', true), + ui_print_success_message(__('bien'), '', true), + ], + ]; + + exit(json_encode($return)); } /** * Print Diagnostics PDF report. * + * @param string|null $filename Filename. + * * @return void */ - public static function exportPDF($filename=false) + public function exportPDF(?string $filename=null):void { global $config; + $this->pdf = true; + enterprise_include_once('/include/class/Pdf.class.php'); - $pdf = new Pdf([]); - $diagnostics = new Diagnostics('tools/diagnostics', true); + $mpdf = new Pdf([]); + + // ADD style. + $mpdf->addStyle($config['homedir'].'/include/styles/diagnostics.css'); + + // ADD Metadata. $product_name = io_safe_output(get_product_name()); - $pdf->setMetadata( + $mpdf->setMetadata( __('Diagnostics Info'), $product_name.' Enteprise', $product_name, @@ -1801,18 +1892,24 @@ class Diagnostics extends Wizard $product_name ) ); - $pdf->setHeaderHTML(__('Diagnostics Info')); - $pdf->addHTML( - $diagnostics->printMethodsDiagnostigsInfo() + // ADD Header. + $mpdf->setHeaderHTML(__('Diagnostics Info')); + + // ADD content to report. + $mpdf->addHTML( + $this->printMethodsDiagnostigsInfo() ); - $pdf->addHTML( - $diagnostics->printCharts() + $mpdf->addHTML( + $this->printCharts() ); - $pdf->setFooterHTML(); - $pdf->writePDFfile($filename); + // ADD Footer. + $mpdf->setFooterHTML(); + + // Write html filename. + $mpdf->writePDFfile($filename); } @@ -1860,14 +1957,13 @@ class Diagnostics extends Wizard ]; $inputs[] = [ - 'label' => __('include installation data'), + 'label' => __('Include installation data'), 'class' => 'flex-row-vcenter', 'arguments' => [ - 'name' => 'include-installation-data', - 'id' => 'include-installation-data', - 'type' => 'switch', - 'return' => true, - 'value' => 1, + 'name' => 'include_installation_data', + 'id' => 'include_installation_data', + 'type' => 'switch', + 'value' => 1, ], ]; @@ -1883,4 +1979,67 @@ class Diagnostics extends Wizard } + /** + * Send Csv md5 files. + * + * @return string + */ + public function csvMd5Files():string + { + global $config; + + // Extract files. + $files = $this->recursiveDirValidation($config['homedir']); + + // Type divider. + $divider = html_entity_decode($config['csv_divider']); + + // BOM. + $result = pack('C*', 0xEF, 0xBB, 0xBF); + + $result .= __('Path').$divider.__('MD5')."\n"; + foreach ($files as $key => $value) { + $result .= $key.$divider.$value."\n"; + } + + return $result; + } + + + /** + * Function to return array with name file -> MD%. + * + * @param string $dir Directory. + * + * @return array Result all files in directory recursively. + */ + private function recursiveDirValidation(string $dir):array + { + $result = []; + + $dir_content = scandir($dir); + + // Dont check attachment. + if (strpos($dir, $config['homedir'].'/attachment') === false) { + if (is_array($dir_content) === true) { + foreach (scandir($dir) as $file) { + if ('.' === $file || '..' === $file) { + continue; + } + + if (is_dir($dir.'/'.$file) === true) { + $result += $this->recursiveDirValidation( + $dir.'/'.$file + ); + } else { + $result[$dir.'/'.$file] = md5_file($dir.'/'.$file); + } + } + } + } + + return $result; + } + + } diff --git a/pandora_console/include/functions_html.php b/pandora_console/include/functions_html.php index ab3aad9c7a..5ae28f8e27 100644 --- a/pandora_console/include/functions_html.php +++ b/pandora_console/include/functions_html.php @@ -1898,6 +1898,7 @@ function html_get_predefined_table($model='transparent', $columns=4) * $table->titlestyle - Title style * $table->titleclass - Title class * $table->styleTable - Table style + * $table->autosize - Autosize * $table->caption - Table title * @param bool Whether to return an output string or echo now * @@ -2008,6 +2009,12 @@ function html_print_table(&$table, $return=false) // $table->width = '80%'; } + if (isset($table->autosize) === true) { + $table->autosize = 'autosize = "1"'; + } else { + $table->autosize = ''; + } + if (empty($table->border)) { if (empty($table)) { $table = new stdClass(); @@ -2042,9 +2049,9 @@ function html_print_table(&$table, $return=false) $tableid = empty($table->id) ? 'table'.$table_count : $table->id; if (!empty($table->width)) { - $output .= 'width.'; '.$styleTable.' '.$table->tablealign; } else { - $output .= '
tablealign; } $output .= ' cellpadding="'.$table->cellpadding.'" cellspacing="'.$table->cellspacing.'"'; @@ -3003,23 +3010,24 @@ function html_print_csrf_error() /** - * Print an swith button + * Print an swith button. * - * @param array $atributes. Valid params: - * name: Usefull to handle in forms - * value: If is checked or not - * disabled: Disabled. Cannot be pressed. - * id: Optional id for the switch. - * class: Additional classes (string). - * @return string with HTML of button + * @param array $attributes Valid params. + * name: Usefull to handle in forms. + * value: If is checked or not. + * disabled: Disabled. Cannot be pressed. + * id: Optional id for the switch. + * class: Additional classes (string). + * + * @return string with HTML of button. */ function html_print_switch($attributes=[]) { $html_expand = ''; // Check the load values on status. - $html_expand .= (bool) $attributes['value'] ? ' checked' : ''; - $html_expand .= (bool) $attributes['disabled'] ? ' disabled' : ''; + $html_expand .= (bool) ($attributes['value']) ? ' checked' : ''; + $html_expand .= (bool) ($attributes['disabled']) ? ' disabled' : ''; // Only load the valid attributes. $valid_attrs = [ @@ -3042,7 +3050,7 @@ function html_print_switch($attributes=[]) } return ""; } diff --git a/pandora_console/include/javascript/pandora.js b/pandora_console/include/javascript/pandora.js index b38ff66a30..09a97ef24e 100644 --- a/pandora_console/include/javascript/pandora.js +++ b/pandora_console/include/javascript/pandora.js @@ -1944,6 +1944,10 @@ function load_modal(settings) { if (settings.onsubmit.preaction != undefined) { settings.onsubmit.preaction(); } + if (settings.onsubmit.dataType == undefined) { + settings.onsubmit.dataType = "html"; + } + var formdata = new FormData(); if (settings.extradata) { settings.extradata.forEach(function(item) { @@ -1960,7 +1964,13 @@ function load_modal(settings) { formdata.append(this.name, $(this).prop("files")[0]); } } else { - formdata.append(this.name, $(this).val()); + if ($(this).attr("type") == "checkbox") { + if (this.checked) { + formdata.append(this.name, "on"); + } + } else { + formdata.append(this.name, $(this).val()); + } } }); @@ -1970,9 +1980,14 @@ function load_modal(settings) { processData: false, contentType: false, data: formdata, + dataType: settings.onsubmit.dataType, success: function(data) { if (settings.ajax_callback != undefined) { - settings.ajax_callback(data); + if (settings.idMsgCallback != undefined) { + settings.ajax_callback(data, settings.idMsgCallback); + } else { + settings.ajax_callback(data); + } } AJAX_RUNNING = 0; } @@ -1989,6 +2004,58 @@ function load_modal(settings) { }); } +/** + * Function to show modal with message Validation. + * + * @param {json} data Json example: + * $return = [ + * 'error' => 0 or 1, + * 'title' => [ + * Failed, + * Success, + * ], + * 'text' => [ + * Failed, + * Success, + * ], + *]; + * @param {string} idMsg ID div charge modal. + * + * @return {void} + */ +function generalShowMsg(data, idMsg) { + var title = data.title[data.error]; + var text = data.text[data.error]; + var failed = !data.error; + + $("#" + idMsg).empty(); + $("#" + idMsg).html(text); + $("#" + idMsg).dialog({ + width: 450, + position: { + my: "center", + at: "center", + of: window, + collision: "fit" + }, + title: title, + buttons: [ + { + class: + "ui-widget ui-state-default ui-corner-all ui-button-text-only sub ok submit-next", + text: "OK", + click: function(e) { + if (!failed) { + $(".ui-dialog-content").dialog("close"); + } else { + $(this).dialog("close"); + } + } + } + ] + }); +} + /** * Function for AJAX request. * diff --git a/pandora_console/include/styles/diagnostics.css b/pandora_console/include/styles/diagnostics.css new file mode 100644 index 0000000000..3b541ac523 --- /dev/null +++ b/pandora_console/include/styles/diagnostics.css @@ -0,0 +1,58 @@ +.pdf-report { + page-break-inside: avoid; +} + +.pdf-report th, +.title-self-monitoring, +.caption_table caption { + text-align: center; + font-size: 1.5em; + font-weight: bolder; + color: #fff; + background: #282828; + padding: 8px; +} + +.pdf-report tr { + text-align: justify; +} + +.datatables-td-title { + width: 25% !important; + font-weight: bolder; +} + +.datatables-td-max { + display: flex; + flex-direction: row; + flex-wrap: wrap; +} + +.datatables-td-max img { + margin-right: 10px; +} + +.datatables-td-max span { + width: 400px; + display: inline-block; + word-wrap: break-word; +} + +.pdf-report td { + font-size: 1.2em; +} + +.container-self-monitoring { + display: flex; + flex-direction: row; + flex-wrap: wrap; +} + +.element-self-monitoring { + flex: 2 1 600px; +} + +.footer-self-monitoring { + margin: 30px; + font-style: italic; +} diff --git a/pandora_console/include/styles/pandora.css b/pandora_console/include/styles/pandora.css index 06ac52dad8..758114e12d 100644 --- a/pandora_console/include/styles/pandora.css +++ b/pandora_console/include/styles/pandora.css @@ -5910,49 +5910,3 @@ table.table_modal_alternate tr td:first-child { .flot-text { width: 101%; } - -.title-self-monitoring, -.caption_table caption { - text-align: center; - font-size: 1.5em; - font-weight: bolder; - color: #fff; - background: #282828; - padding: 8px; -} - -.datatables-td-title { - width: 25% !important; - font-weight: bolder; -} - -.datatables-td-max { - display: flex; - flex-direction: row; - flex-wrap: wrap; -} - -.datatables-td-max img { - margin-right: 10px; -} - -.datatables-td-max span { - width: 400px; - display: inline-block; - word-wrap: break-word; -} - -.container-self-monitoring { - display: flex; - flex-direction: row; - flex-wrap: wrap; -} - -.element-self-monitoring { - flex: 2 1 600px; -} - -.footer-self-monitoring { - margin: 30px; - font-style: italic; -} From 3dee6888d62f75086f6848e6541e664944ea0220 Mon Sep 17 00:00:00 2001 From: Daniel Barbero Martin Date: Thu, 24 Oct 2019 17:42:37 +0200 Subject: [PATCH 07/11] fix --- .../include/class/Diagnostics.class.php | 129 +++++++++++++++--- pandora_console/include/functions_html.php | 87 ++++++++++++ pandora_console/include/functions_users.php | 26 ++++ pandora_console/include/javascript/pandora.js | 43 +++--- pandora_console/include/styles/pandora.css | 4 + 5 files changed, 253 insertions(+), 36 deletions(-) diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index 5fdeafa934..77303ccc54 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -68,8 +68,10 @@ class Diagnostics extends Wizard // Check access. check_login(); - // Check Acl. - if (!check_acl($config['id_user'], 0, 'PM')) { + // TODO:XXX + /* + // Check Acl. + if (!check_acl($config['id_user'], 0, 'PM')) { db_pandora_audit( 'ACL Violation', 'Trying to access diagnostic info' @@ -81,7 +83,8 @@ class Diagnostics extends Wizard include 'general/noaccess.php'; exit; - } + } + */ $this->ajaxController = $page; $this->pdf = $pdf; @@ -1755,18 +1758,14 @@ class Diagnostics extends Wizard // FIX for customer key. if ($key === 'customerKey') { - $spanValue = ''.$items[$key]['value'].''; - if ($this->pdf === true) { - $spanValue = ''; - $spanValue .= wordwrap( - $items[$key]['value'], - 10, - "\n", - true - ); - $spanValue .= ''; - } - + $customerKey = ui_print_truncate_text( + $items[$key]['value'], + 30, + false, + true, + false + ); + $spanValue = ''.$customerKey.''; $items[$key]['value'] = $spanValue; } @@ -1805,10 +1804,100 @@ class Diagnostics extends Wizard public function createdScheduleFeedbackTask():void { global $config; + + // TODO: feedback@artica.es + $mail_feedback = 'feedback@artica.es'; $email = 'daniel.barbero@artica.es'; $subject = 'PandoraFMS Report '.$config['pandora_uid']; $text = get_parameter('what-happened', ''); $attachment = get_parameter_switch('include_installation_data', 0); + $email_from = get_parameter_switch('email', ''); + + if (!check_acl($config['id_user'], 0, 'PM')) { + // TODO: MAIL TO ADMIN. + $email = get_mail_admin(); + $email = 'daniel.barbero@artica.es'; + $product_name = io_safe_output(get_product_name()); + $name_admin = get_name_admin(); + + $subject = __('Feedback').' '.$product_name.' '.$config['pandora_uid']; + + $title = __('Hello').' '.$name_admin; + $p1 = __( + 'User %s is reporting an issue in its %s experience', + $email_from, + $product_name + ); + $p1 .= ':'; + + $p2 = $text; + + if ($attachment === 1) { + $msg_attch = __('Find some files attached to this mail'); + $msg_attch .= '. '; + $msg_attch .= __( + 'PDF is the diagnostic information retrieved at report time' + ); + $msg_attch .= '. '; + $msg_attch .= __('CSV contains the statuses of every product file'); + $msg_attch .= '. '; + } + + $p3 = __( + 'If you think this report must be escalated, feel free to forward this mail to "%s"', + $mail_feedback + ); + + $legal = __('LEGAL WARNING'); + $legal1 = __( + 'The information contained in this transmission is privileged and confidential information intended only for the use of the individual or entity named above' + ); + $legal1 .= '. '; + $legal2 = __( + 'If the reader of this message is not the intended recipient, you are hereby notified that any dissemination, distribution or copying of this communication is strictly prohibited' + ); + $legal2 .= '. '; + $legal3 = __( + 'If you have received this transmission in error, do not read it' + ); + $legal3 .= '. '; + $legal4 = __( + 'Please immediately reply to the sender that you have received this communication in error and then delete it' + ); + $legal4 .= '.'; + + $patterns = [ + '/__title__/', + '/__p1__/', + '/__p2__/', + '/__attachment__/', + '/__p3__/', + '/__legal__/', + '/__legal1__/', + '/__legal2__/', + '/__legal3__/', + '/__legal4__/', + ]; + + $substitutions = [ + $title, + $p1, + $p2, + $msg_attch, + $p3, + $legal, + $legal1, + $legal2, + $legal3, + $legal4, + ]; + + $html_template = file_get_contents( + $config['homedir'].'/include/templates/feedback_send_mail.html' + ); + + $text = preg_replace($patterns, $substitutions, $html_template); + } $idUserTask = db_get_value( 'id', @@ -1948,11 +2037,11 @@ class Diagnostics extends Wizard 'label' => __('Your email'), 'class' => 'flex-row-baseline', 'arguments' => [ - 'name' => 'email', - 'id' => 'email', - 'type' => 'text', - 'return' => true, - 'size' => 40, + 'name' => 'email', + 'id' => 'email', + 'type' => 'email', + 'size' => 40, + 'required' => 'required', ], ]; diff --git a/pandora_console/include/functions_html.php b/pandora_console/include/functions_html.php index 5ae28f8e27..ca809a727f 100644 --- a/pandora_console/include/functions_html.php +++ b/pandora_console/include/functions_html.php @@ -1535,6 +1535,89 @@ function html_print_input_text($name, $value, $alt='', $size=50, $maxlength=255, } +/** + * Render an input email element. + * + * @param array $settings Array with attributes input. + * only name is necessary. + * + * @return string Html input. + */ +function html_print_input_email(array $settings):string +{ + // TODO: const. + $valid_attrs = [ + 'accept', + 'disabled', + 'maxlength', + 'name', + 'readonly', + 'placeholder', + 'size', + 'value', + 'accesskey', + 'class', + 'dir', + 'id', + 'lang', + 'style', + 'tabindex', + 'title', + 'xml:lang', + 'onfocus', + 'onblur', + 'onselect', + 'onchange', + 'onclick', + 'ondblclick', + 'onmousedown', + 'onmouseup', + 'onmouseover', + 'onmousemove', + 'onmouseout', + 'onkeypress', + 'onkeydown', + 'onkeyup', + 'required', + 'pattern', + 'autocomplete', + ]; + + $output = ''; + if (isset($settings) === true && is_array($settings) === true) { + // Check Name is necessary. + if (isset($settings['name']) === true) { + $output = ' $attr_value) { + // Check valid attribute. + if (in_array($attribute, $valid_attrs) === false) { + continue; + } + + $output .= $attribute.'="'.$attr_value.'" '; + } + + $output .= $function.'/>'; + } + } + + return $output; +} + + /** * Render an input image element. * @@ -3208,6 +3291,10 @@ function html_print_input($data, $wrapper='div', $input_only=false) ); break; + case 'email': + $output .= html_print_input_email($data); + break; + case 'hidden': $output .= html_print_input_hidden( $data['name'], diff --git a/pandora_console/include/functions_users.php b/pandora_console/include/functions_users.php index 97d97c7273..86e4475eea 100755 --- a/pandora_console/include/functions_users.php +++ b/pandora_console/include/functions_users.php @@ -1236,3 +1236,29 @@ function users_get_explode_tags(&$group) } } + + +/** + * Get mail admin. + * + * @return string Return mail admin. + */ +function get_mail_admin():string +{ + $mail = db_get_value('email', 'tusuario', 'is_admin', 1); + + return $mail; +} + + +/** + * Get name admin. + * + * @return string Return name admin. + */ +function get_name_admin():string +{ + $mail = db_get_value('fullname', 'tusuario', 'is_admin', 1); + + return $mail; +} diff --git a/pandora_console/include/javascript/pandora.js b/pandora_console/include/javascript/pandora.js index 09a97ef24e..886d680c73 100644 --- a/pandora_console/include/javascript/pandora.js +++ b/pandora_console/include/javascript/pandora.js @@ -1958,7 +1958,14 @@ function load_modal(settings) { formdata.append("page", settings.onsubmit.page); formdata.append("method", settings.onsubmit.method); + var flagError = false; $("#" + settings.form + " :input").each(function() { + if (this.checkValidity() === false) { + // TODO: Tooltip msg. + console.log(this.validationMessage); + flagError = true; + } + if (this.type == "file") { if ($(this).prop("files")[0]) { formdata.append(this.name, $(this).prop("files")[0]); @@ -1974,24 +1981,28 @@ function load_modal(settings) { } }); - $.ajax({ - method: "post", - url: settings.url, - processData: false, - contentType: false, - data: formdata, - dataType: settings.onsubmit.dataType, - success: function(data) { - if (settings.ajax_callback != undefined) { - if (settings.idMsgCallback != undefined) { - settings.ajax_callback(data, settings.idMsgCallback); - } else { - settings.ajax_callback(data); + if (flagError === false) { + $.ajax({ + method: "post", + url: settings.url, + processData: false, + contentType: false, + data: formdata, + dataType: settings.onsubmit.dataType, + success: function(data) { + if (settings.ajax_callback != undefined) { + if (settings.idMsgCallback != undefined) { + settings.ajax_callback(data, settings.idMsgCallback); + } else { + settings.ajax_callback(data); + } } + AJAX_RUNNING = 0; } - AJAX_RUNNING = 0; - } - }); + }); + } else { + AJAX_RUNNING = 0; + } } } ], diff --git a/pandora_console/include/styles/pandora.css b/pandora_console/include/styles/pandora.css index 758114e12d..a0cf338114 100644 --- a/pandora_console/include/styles/pandora.css +++ b/pandora_console/include/styles/pandora.css @@ -5910,3 +5910,7 @@ table.table_modal_alternate tr td:first-child { .flot-text { width: 101%; } + +input:invalid { + border-color: #c00; +} From 22a2b7cd0b6ed5ae3847ed1fa3e3904f0bcc4255 Mon Sep 17 00:00:00 2001 From: Daniel Barbero Date: Fri, 25 Oct 2019 10:43:03 +0200 Subject: [PATCH 08/11] Add feedback phpInfo --- .../include/class/Diagnostics.class.php | 497 ++++++++++-------- .../include/templates/feedback_send_mail.html | 58 ++ 2 files changed, 328 insertions(+), 227 deletions(-) create mode 100644 pandora_console/include/templates/feedback_send_mail.html diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index 77303ccc54..6f1898f14e 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -68,24 +68,6 @@ class Diagnostics extends Wizard // Check access. check_login(); - // TODO:XXX - /* - // Check Acl. - if (!check_acl($config['id_user'], 0, 'PM')) { - db_pandora_audit( - 'ACL Violation', - 'Trying to access diagnostic info' - ); - - if (is_ajax()) { - echo json_encode(['error' => 'noaccess']); - } - - include 'general/noaccess.php'; - exit; - } - */ - $this->ajaxController = $page; $this->pdf = $pdf; } @@ -1637,14 +1619,25 @@ class Diagnostics extends Wizard '; - $return .= $this->getChart( + $table = new stdClass(); + $table->width = '100%'; + $table->class = 'pdf-report'; + $table->style = []; + $table->style[0] = 'font-weight: bolder;'; + $table->autosize = 1; + + $table->head = []; + $table->head[0] = $params['nameModule']; + + $table->data = []; + $table->data[0] = $this->getChart( $params['idAgent'], $params['nameModule'], true, false ); - $return .= ''; + + $return = html_print_table($table, true); } } catch (Exception $e) { $return = $e->getMessage(); @@ -1796,212 +1789,6 @@ class Diagnostics extends Wizard } - /** - * Create cron task form feedback. - * - * @return void Json result AJAX request. - */ - public function createdScheduleFeedbackTask():void - { - global $config; - - // TODO: feedback@artica.es - $mail_feedback = 'feedback@artica.es'; - $email = 'daniel.barbero@artica.es'; - $subject = 'PandoraFMS Report '.$config['pandora_uid']; - $text = get_parameter('what-happened', ''); - $attachment = get_parameter_switch('include_installation_data', 0); - $email_from = get_parameter_switch('email', ''); - - if (!check_acl($config['id_user'], 0, 'PM')) { - // TODO: MAIL TO ADMIN. - $email = get_mail_admin(); - $email = 'daniel.barbero@artica.es'; - $product_name = io_safe_output(get_product_name()); - $name_admin = get_name_admin(); - - $subject = __('Feedback').' '.$product_name.' '.$config['pandora_uid']; - - $title = __('Hello').' '.$name_admin; - $p1 = __( - 'User %s is reporting an issue in its %s experience', - $email_from, - $product_name - ); - $p1 .= ':'; - - $p2 = $text; - - if ($attachment === 1) { - $msg_attch = __('Find some files attached to this mail'); - $msg_attch .= '. '; - $msg_attch .= __( - 'PDF is the diagnostic information retrieved at report time' - ); - $msg_attch .= '. '; - $msg_attch .= __('CSV contains the statuses of every product file'); - $msg_attch .= '. '; - } - - $p3 = __( - 'If you think this report must be escalated, feel free to forward this mail to "%s"', - $mail_feedback - ); - - $legal = __('LEGAL WARNING'); - $legal1 = __( - 'The information contained in this transmission is privileged and confidential information intended only for the use of the individual or entity named above' - ); - $legal1 .= '. '; - $legal2 = __( - 'If the reader of this message is not the intended recipient, you are hereby notified that any dissemination, distribution or copying of this communication is strictly prohibited' - ); - $legal2 .= '. '; - $legal3 = __( - 'If you have received this transmission in error, do not read it' - ); - $legal3 .= '. '; - $legal4 = __( - 'Please immediately reply to the sender that you have received this communication in error and then delete it' - ); - $legal4 .= '.'; - - $patterns = [ - '/__title__/', - '/__p1__/', - '/__p2__/', - '/__attachment__/', - '/__p3__/', - '/__legal__/', - '/__legal1__/', - '/__legal2__/', - '/__legal3__/', - '/__legal4__/', - ]; - - $substitutions = [ - $title, - $p1, - $p2, - $msg_attch, - $p3, - $legal, - $legal1, - $legal2, - $legal3, - $legal4, - ]; - - $html_template = file_get_contents( - $config['homedir'].'/include/templates/feedback_send_mail.html' - ); - - $text = preg_replace($patterns, $substitutions, $html_template); - } - - $idUserTask = db_get_value( - 'id', - 'tuser_task', - 'function_name', - 'cron_task_feedback_send_mail' - ); - - // Params for send mail with cron. - $parameters = [ - 0 => '0', - 1 => $email, - 2 => $subject, - 3 => $text, - 4 => $attachment, - 'first_execution' => strtotime('now'), - ]; - - // Values insert task cron. - $values = [ - 'id_usuario' => $config['id_user'], - 'id_user_task' => $idUserTask, - 'args' => serialize($parameters), - 'scheduled' => 'no', - 'id_grupo' => 0, - ]; - - $result = db_process_sql_insert( - 'tuser_task_scheduled', - $values - ); - - $error = 1; - if ($result === false) { - $error = 0; - } - - $return = [ - 'error' => $error, - 'title' => [ - __('Failed'), - __('Success'), - ], - 'text' => [ - ui_print_error_message(__('Mal'), '', true), - ui_print_success_message(__('bien'), '', true), - ], - ]; - - exit(json_encode($return)); - } - - - /** - * Print Diagnostics PDF report. - * - * @param string|null $filename Filename. - * - * @return void - */ - public function exportPDF(?string $filename=null):void - { - global $config; - - $this->pdf = true; - - enterprise_include_once('/include/class/Pdf.class.php'); - $mpdf = new Pdf([]); - - // ADD style. - $mpdf->addStyle($config['homedir'].'/include/styles/diagnostics.css'); - - // ADD Metadata. - $product_name = io_safe_output(get_product_name()); - $mpdf->setMetadata( - __('Diagnostics Info'), - $product_name.' Enteprise', - $product_name, - __( - 'Automated %s report for user defined report', - $product_name - ) - ); - - // ADD Header. - $mpdf->setHeaderHTML(__('Diagnostics Info')); - - // ADD content to report. - $mpdf->addHTML( - $this->printMethodsDiagnostigsInfo() - ); - - $mpdf->addHTML( - $this->printCharts() - ); - - // ADD Footer. - $mpdf->setFooterHTML(); - - // Write html filename. - $mpdf->writePDFfile($filename); - } - - /** * Print Diagnostics Form feedback. * @@ -2068,6 +1855,215 @@ class Diagnostics extends Wizard } + /** + * Create cron task form feedback. + * + * @return void Json result AJAX request. + */ + public function createdScheduleFeedbackTask():void + { + global $config; + + // TODO: feedback@artica.es + $mail_feedback = 'feedback@artica.es'; + $email = 'daniel.barbero@artica.es'; + $subject = 'PandoraFMS Report '.$config['pandora_uid']; + $text = get_parameter('what-happened', ''); + $attachment = get_parameter_switch('include_installation_data', 0); + $email_from = get_parameter_switch('email', ''); + $title = __('Hello Feedback-Men'); + + $product_name = io_safe_output(get_product_name()); + + if (check_acl($config['id_user'], 0, 'PM') !== 1) { + // TODO: MAIL TO ADMIN. + $email = get_mail_admin(); + $email = 'daniel.barbero@artica.es'; + $name_admin = get_name_admin(); + + $subject = __('Feedback').' '.$product_name.' '.$config['pandora_uid']; + + $title = __('Hello').' '.$name_admin; + } + + $p1 = __( + 'User %s is reporting an issue in its %s experience', + $email_from, + $product_name + ); + $p1 .= ':'; + + $p2 = $text; + + if ($attachment === 1) { + $msg_attch = __('Find some files attached to this mail'); + $msg_attch .= '. '; + $msg_attch .= __( + 'PDF is the diagnostic information retrieved at report time' + ); + $msg_attch .= '. '; + $msg_attch .= __('CSV contains the statuses of every product file'); + $msg_attch .= '. '; + } + + $p3 = __( + 'If you think this report must be escalated, feel free to forward this mail to "%s"', + $mail_feedback + ); + + $legal = __('LEGAL WARNING'); + $legal1 = __( + 'The information contained in this transmission is privileged and confidential information intended only for the use of the individual or entity named above' + ); + $legal1 .= '. '; + $legal2 = __( + 'If the reader of this message is not the intended recipient, you are hereby notified that any dissemination, distribution or copying of this communication is strictly prohibited' + ); + $legal2 .= '. '; + $legal3 = __( + 'If you have received this transmission in error, do not read it' + ); + $legal3 .= '. '; + $legal4 = __( + 'Please immediately reply to the sender that you have received this communication in error and then delete it' + ); + $legal4 .= '.'; + + $patterns = [ + '/__title__/', + '/__p1__/', + '/__p2__/', + '/__attachment__/', + '/__p3__/', + '/__legal__/', + '/__legal1__/', + '/__legal2__/', + '/__legal3__/', + '/__legal4__/', + ]; + + $substitutions = [ + $title, + $p1, + $p2, + $msg_attch, + $p3, + $legal, + $legal1, + $legal2, + $legal3, + $legal4, + ]; + + $html_template = file_get_contents( + $config['homedir'].'/include/templates/feedback_send_mail.html' + ); + + $text = preg_replace($patterns, $substitutions, $html_template); + + $idUserTask = db_get_value( + 'id', + 'tuser_task', + 'function_name', + 'cron_task_feedback_send_mail' + ); + + // Params for send mail with cron. + $parameters = [ + 0 => '0', + 1 => $email, + 2 => $subject, + 3 => $text, + 4 => $attachment, + 'first_execution' => strtotime('now'), + ]; + + // Values insert task cron. + $values = [ + 'id_usuario' => $config['id_user'], + 'id_user_task' => $idUserTask, + 'args' => serialize($parameters), + 'scheduled' => 'no', + 'id_grupo' => 0, + ]; + + $result = db_process_sql_insert( + 'tuser_task_scheduled', + $values + ); + + $error = 1; + if ($result === false) { + $error = 0; + } + + $return = [ + 'error' => $error, + 'title' => [ + __('Failed'), + __('Success'), + ], + 'text' => [ + ui_print_error_message(__('Invalid cron task'), '', true), + ui_print_success_message(__('Cron task generated'), '', true), + ], + ]; + + exit(json_encode($return)); + } + + + /** + * Print Diagnostics PDF report. + * + * @param string|null $filename Filename. + * + * @return void + */ + public function exportPDF(?string $filename=null):void + { + global $config; + + $this->pdf = true; + + enterprise_include_once('/include/class/Pdf.class.php'); + $mpdf = new Pdf([]); + + // ADD style. + $mpdf->addStyle($config['homedir'].'/include/styles/diagnostics.css'); + + // ADD Metadata. + $product_name = io_safe_output(get_product_name()); + $mpdf->setMetadata( + __('Diagnostics Info'), + $product_name.' Enteprise', + $product_name, + __( + 'Automated %s report for user defined report', + $product_name + ) + ); + + // ADD Header. + $mpdf->setHeaderHTML(__('Diagnostics Info')); + + // ADD content to report. + $mpdf->addHTML( + $this->printMethodsDiagnostigsInfo() + ); + + $mpdf->addHTML( + $this->printCharts() + ); + + // ADD Footer. + $mpdf->setFooterHTML(); + + // Write html filename. + $mpdf->writePDFfile($filename); + } + + /** * Send Csv md5 files. * @@ -2131,4 +2127,51 @@ class Diagnostics extends Wizard } + /** + * Send PHP info in report. + * + * @param string $filename Download dir report. + * + * @return void + */ + public function phpInfoReports(string $filename) + { + global $config; + + $this->pdf = true; + + // Extract info PHP. + ob_start(); + phpinfo(); + $php_info = ob_get_clean(); + + enterprise_include_once('/include/class/Pdf.class.php'); + $mpdf = new Pdf([]); + + // ADD Metadata. + $product_name = io_safe_output(get_product_name()); + $mpdf->setMetadata( + __('PHP Info'), + $product_name.' Enteprise', + $product_name, + __( + 'Automated %s report for user defined report', + $product_name + ) + ); + + // ADD Header. + $mpdf->setHeaderHTML(__('PHP Info')); + + // ADD content to report. + $mpdf->addHTML($php_info); + + // ADD Footer. + $mpdf->setFooterHTML(); + + // Write html filename. + $mpdf->writePDFfile($filename); + } + + } diff --git a/pandora_console/include/templates/feedback_send_mail.html b/pandora_console/include/templates/feedback_send_mail.html new file mode 100644 index 0000000000..e06b68f246 --- /dev/null +++ b/pandora_console/include/templates/feedback_send_mail.html @@ -0,0 +1,58 @@ + + + + + + + Feedback + + + +

__title__

+
+

__p1__

+

__p2__

+

__attachment__

+

__p3__

+
+
__legal__
+ + + + + + From c4aea1ac5918a4812b98bdb4c19997d3e8862429 Mon Sep 17 00:00:00 2001 From: Daniel Barbero Date: Fri, 25 Oct 2019 13:28:01 +0200 Subject: [PATCH 09/11] add styles validation form of modal --- .../include/class/Diagnostics.class.php | 17 ++++++------ pandora_console/include/javascript/pandora.js | 10 +++++-- pandora_console/include/styles/discovery.css | 27 +++++++++++++++++++ pandora_console/include/styles/pandora.css | 4 --- 4 files changed, 44 insertions(+), 14 deletions(-) diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index 6f1898f14e..b839851421 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -1810,13 +1810,14 @@ class Diagnostics extends Wizard 'id' => 'div-what-happened', 'class' => 'flex-row', 'arguments' => [ - 'name' => 'what-happened', - 'type' => 'textarea', - 'value' => '', - 'return' => true, - 'rows' => 1, - 'columns' => 1, - 'size' => 25, + 'name' => 'what-happened', + 'type' => 'textarea', + 'value' => '', + 'return' => true, + 'rows' => 1, + 'columns' => 1, + 'size' => 25, + 'attributes' => 'required="required"', ], ]; @@ -1827,7 +1828,7 @@ class Diagnostics extends Wizard 'name' => 'email', 'id' => 'email', 'type' => 'email', - 'size' => 40, + 'size' => 42, 'required' => 'required', ], ]; diff --git a/pandora_console/include/javascript/pandora.js b/pandora_console/include/javascript/pandora.js index 886d680c73..f3737eabdf 100644 --- a/pandora_console/include/javascript/pandora.js +++ b/pandora_console/include/javascript/pandora.js @@ -1959,10 +1959,16 @@ function load_modal(settings) { formdata.append("method", settings.onsubmit.method); var flagError = false; + $("#" + settings.form + " :input").each(function() { if (this.checkValidity() === false) { - // TODO: Tooltip msg. - console.log(this.validationMessage); + $(this).prop("title", this.validationMessage); + $(this).tooltip({ + tooltipClass: "uitooltip", + position: { my: "right bottom", at: "right bottom" }, + show: { duration: 200 } + }); + $(this).tooltip("open"); flagError = true; } diff --git a/pandora_console/include/styles/discovery.css b/pandora_console/include/styles/discovery.css index 82b022050f..2095e98b8e 100644 --- a/pandora_console/include/styles/discovery.css +++ b/pandora_console/include/styles/discovery.css @@ -205,6 +205,7 @@ label { } li > input[type="text"], +li > input[type="email"], li > input[type="password"], .discovery_text_input > input[type="password"], .discovery_text_input > input[type="text"], @@ -270,3 +271,29 @@ a.ext_link { margin-left: 1em; font-size: 8pt; } + +input:invalid, +input[type="email"]:invalid { + border-bottom-color: #fb4444; +} + +textarea:invalid { + border-color: #fb4444; +} + +div.ui-tooltip.ui-corner-all.ui-widget-shadow.ui-widget.ui-widget-content.uitooltip { + background: grey; + opacity: 0.9; + border-radius: 4px; + box-shadow: 0 0 0px #fff; + padding: 6px; +} + +.ui-tooltip-content { + background: transparent; + color: #fff; + font-weight: bold; + font-family: "lato-lighter", "Open Sans", sans-serif; + letter-spacing: 0.03pt; + font-size: 8pt; +} diff --git a/pandora_console/include/styles/pandora.css b/pandora_console/include/styles/pandora.css index a0cf338114..758114e12d 100644 --- a/pandora_console/include/styles/pandora.css +++ b/pandora_console/include/styles/pandora.css @@ -5910,7 +5910,3 @@ table.table_modal_alternate tr td:first-child { .flot-text { width: 101%; } - -input:invalid { - border-color: #c00; -} From f6fd5cc21fd75ce884094bf4b0553ede8ac787ed Mon Sep 17 00:00:00 2001 From: Daniel Barbero Martin Date: Tue, 29 Oct 2019 09:13:48 +0100 Subject: [PATCH 10/11] Add image feedback --- pandora_console/general/header.php | 4 ++-- pandora_console/include/class/Diagnostics.class.php | 5 +---- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/pandora_console/general/header.php b/pandora_console/general/header.php index 70978bbcb5..e060cf96f6 100644 --- a/pandora_console/general/header.php +++ b/pandora_console/general/header.php @@ -334,13 +334,13 @@ if ($config['menu_type'] == 'classic') { $header_feedback .= ''; $header_feedback .= ''; $header_feedback .= html_print_image( - '/images/icono_warning.png', + '/images/feedback-header.png', true, [ 'title' => __('Feedback'), 'id' => 'feedback-header', 'alt' => __('Feedback'), - 'style' => 'cursor: pointer; width: 28px;', + 'style' => 'cursor: pointer; width: 27px;', ] ); $header_feedback .= ''; diff --git a/pandora_console/include/class/Diagnostics.class.php b/pandora_console/include/class/Diagnostics.class.php index b839851421..43f3d948b4 100644 --- a/pandora_console/include/class/Diagnostics.class.php +++ b/pandora_console/include/class/Diagnostics.class.php @@ -1865,9 +1865,8 @@ class Diagnostics extends Wizard { global $config; - // TODO: feedback@artica.es $mail_feedback = 'feedback@artica.es'; - $email = 'daniel.barbero@artica.es'; + $email = $mail_feedback; $subject = 'PandoraFMS Report '.$config['pandora_uid']; $text = get_parameter('what-happened', ''); $attachment = get_parameter_switch('include_installation_data', 0); @@ -1877,9 +1876,7 @@ class Diagnostics extends Wizard $product_name = io_safe_output(get_product_name()); if (check_acl($config['id_user'], 0, 'PM') !== 1) { - // TODO: MAIL TO ADMIN. $email = get_mail_admin(); - $email = 'daniel.barbero@artica.es'; $name_admin = get_name_admin(); $subject = __('Feedback').' '.$product_name.' '.$config['pandora_uid']; From 6ff85d2abb61c37f0052851e789256d86c70e16c Mon Sep 17 00:00:00 2001 From: Daniel Barbero Martin Date: Tue, 29 Oct 2019 09:21:08 +0100 Subject: [PATCH 11/11] fixed image --- pandora_console/images/feedback-header.png | Bin 0 -> 578 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 pandora_console/images/feedback-header.png diff --git a/pandora_console/images/feedback-header.png b/pandora_console/images/feedback-header.png new file mode 100644 index 0000000000000000000000000000000000000000..c77ff461e419a416a030d1e4d70568c5b93619d5 GIT binary patch literal 578 zcmV-I0=@l-P)5(?Fc7pg6yOd*8pybV zm{*>G3W6&ze(?)Ke!MUh5GugmynqU#q=Bder-R&OR+&Q>*(Sry9Gozy{IFOoN*_k(0bT-}ZBPE;gfVGCZpc?eRJ0->a0XqISLAcr`0A;U zs~VGMAR1A;IZHqr#sFu~oPsO6_VRXT+f_Y3e3mstTeNXN`}7F`1#!7M2B&~j0s#Dr zJi@DjNb;Jt?m%*DlT%`GTL%t{1vuNp4FKQ(tzFyq%Gr3EN1ZL9{S!RB;|Ya08q*Yu zJA9-|1yAGTKOPYXxn+CD%_c2J*}444Trpo%&XBC^bsL_!k7sCwMsVqB6#yCJN&F!& zX!Qa2%P4G^