"container"]); echo UI::h('h1', [], [ UI::h('a', ['href'=>"index.php"], "SE"), " » ", " Status systemu procesy5" ]); try { DB::getPDO(); $this->runPostTask(); // _postTask = $this->"{$_POST['_postTask']}PostTask"() $this->viewStatusDatabase(); if (in_array(User::get('ADM_ADMIN_LEVEL'), ['0', '1'])) { $this->viewStatusUsers(); } // UI::table([ // 'caption' => 'Baza danych', // 'rows' => DB::getPDO()->fetchAll(" SHOW VARIABLES ") // ]); } catch (Exception $e) { UI::alert('danger', $e->getMessage()); } UI::endTag('div');// .container UI::dol(); } function runPostTask() { if ($postTask = V::get('_postTask', '', $_REQUEST)) { DBG::log($args, 'array', "exec '{$postTask}'"); if (!method_exists($this, "{$postTask}PostTask")) throw new Exception("Post Task not exists!"); ob_start(); $this->{"{$postTask}PostTask"}($args); $outputPostTask = ob_get_clean(); if ($outputPostTask) { echo UI::h('details', [], [ UI::h('summary', [], "Wynik '{$postTask}' (rozwiń)"), $outputPostTask, ]); } } } public function viewStatusDatabase() { $dbEvents = DB::getPDO()->fetchFirst(" SHOW VARIABLES WHERE VARIABLE_NAME = 'event_scheduler' "); // DBG::nicePrint($dbEvents, '$dbEvents'); // [Variable_name] => event_scheduler // [Value] => ON $aclObjectCacheExists = false; $objectStorage = SchemaFactory::loadDefaultObject('SystemObject'); $aclCacheTableName = $objectStorage->getRootTableName(); if ($aclCacheTableName) { try { $totalObjects = DB::getPDO()->fetchValue("select count(*) as cnt from `{$aclCacheTableName}`"); if ($totalObjects > 0) $aclObjectCacheExists = true; } catch (Exception $e) { DBG::log($e); } } DBG::log($objectStorage, 'array', "\$objectStorage"); DBG::log($objectStorage->getRootTableName(), 'array', "\$objectStorage->getRootTableName()"); Lib::loadClass('RefConfig'); $totalToUpdateRef = RefConfig::getToUpdateTotal(); UI::table([ 'caption' => UI::h('b', ['style' => "color:#000"], [ "Baza danych", " ", UI::hButtonPost("sprawdź tabele", [ 'class' => "btn btn-xs btn-default", 'data' => [ '_postTask' => 'checkDatabaseTables', ] ]), ]), 'rows' => [ [ 'nazwa' => "Event Scheduler (generowanie Grafika, itp.)", 'wartość' => ('ON' == $dbEvents['Value']) ? UI::h('span', ['class' => "label label-success"], "ON") : UI::h('span', ['class' => "label label-danger"], "OFF"), '#' => UI::hButtonPost("Włącz", [ 'class' => "btn btn-xs btn-default", 'data' => [ '_postTask' => 'fixEventSheduler', ] ]) ], [ 'nazwa' => "System obiektów (xsd)", 'wartość' => ($aclObjectCacheExists) ? UI::h('span', ['class' => "label label-success"], "ON") : UI::h('span', ['class' => "label label-danger"], "OFF"), '#' => UI::hButtonPost("Aktualizuj cache", [ 'class' => "btn btn-xs btn-default", 'data' => [ '_postTask' => 'updateObjectCache' ] ]) ], [ 'nazwa' => "Tabela z relacjami (REF)", 'wartość' => ($totalToUpdateRef) ? UI::h('span', ['class' => "label label-danger"], "wymaga aktualizacji ({$totalToUpdateRef})") : UI::h('span', ['class' => "label label-success"], "akualne"), '#' => UI::hButtonPost("Aktualizuj tabele relacyjne", [ 'class' => "btn btn-xs btn-default", 'data' => [ '_postTask' => 'updateRefTables' ] ]) ], ] ]); } public function fixEventShedulerPostTask() { DB::getPDO()->execSql(" SET GLOBAL event_scheduler='ON' "); } public function updateObjectCachePostTask() { DBG::log("updateObjectCachePostTask..."); SchemaFactory::loadDefaultObject('SystemSource')->updateCache(); SchemaFactory::loadDefaultObject('SystemObject')->updateCache(); // SchemaFactory::loadDefaultObject('SystemObjectField')->updateCache(); // TODO: require loop by acl objects UI::alert('info', "Lista obiketów zaktualizowana"); } function updateRefTablesPostTask() { Lib::loadClass('RefConfig'); DBG::log("DBG:updateRefTablesPostTask..."); $toUpdateStep = 10; $baseRefOffset = V::get('baseref_offset', 0, $_POST, 'int'); $backRefOffset = V::get('backref_offset', 0, $_POST, 'int'); $todoBaseRefOffset = $baseRefOffset; $todoBackRefOffset = $backRefOffset; $baseRefToUpdate = RefConfig::getToUpdateItems(); DBG::log($baseRefToUpdate, 'array', "DBG:updateRefTablesPostTask \$baseRefToUpdate"); if ($baseRefOffset > count($baseRefToUpdate)) { $backRefToUpdate = RefConfig::getToUpdateItems('backRef'); $listBackRefConf = array_slice($backRefToUpdate, $backRefOffset, $toUpdateStep); DBG::log($listBackRefConf, 'array', "DBG:updateRefTablesPostTask \$listBackRefConf ({$backRefOffset}, {$toUpdateStep})"); self::_updateRefTables($listBackRefConf); $todoBackRefOffset = $backRefOffset + $toUpdateStep; } else { $listBaseRefConf = array_slice($baseRefToUpdate, $baseRefOffset, $toUpdateStep); DBG::log($listBaseRefConf, 'array', "DBG:updateRefTablesPostTask \$listBaseRefConf ({$baseRefOffset}, {$toUpdateStep})"); self::_updateRefTables($listBaseRefConf); $todoBaseRefOffset = $baseRefOffset + $toUpdateStep; } $totalToUpdateRef = RefConfig::getToUpdateTotal(); echo ($totalToUpdateRef) ? UI::h('div', [ 'class' => 'alert alert-warning'], [ "Uwaga: Struktura tabel z relacjami częściowo zaktualizowana. Pozostało {$totalToUpdateRef}. ", UI::hButtonPost("Uruchom dla kolejnych", [ 'class' => "btn btn-xs btn-default", 'data' => [ '_postTask' => 'updateRefTables', 'baseref_offset' => $todoBaseRefOffset, 'backref_offset' => $todoBackRefOffset, ] ]) ]) : UI::h('div', [ 'class' => 'alert alert-info' ], "Struktura tabel z relacjami zaktualizowana"); } static function _updateRefTables($listRefConf) { Lib::loadClass('RefConfig'); // $listRefConf = array_slice($listRefConf, 0, 10); $totalTableSkippedNotAcl = 0; $totalTableSkippedMissingAclType = 0; $totalTableSkippedFieldNotFound = 0; DBG::nicePrint($listRefConf, '$listRefConf'); foreach ($listRefConf as $refConf) { try { UI::alert('info', "Aktualizuje ['{$refConf['ID']}'] od '{$refConf['ROOT_OBJECT_NS']}' do '{$refConf['CHILD_NAME']}' ..."); RefConfig::getRefConfig($refConf['ROOT_OBJECT_NS'], $refConf['CHILD_NAME'], $refConf['CHILD_NS']); } catch (\Exception $e) { DBG::log($e); if ('Ref allowed only for AntAcl objects' === $e->getMessage()) { $totalTableSkippedNotAcl++; } else if ('Field ' === substr($e->getMessage(), 0, strlen('Field ')) && false !== strpos($e->getMessage(), 'not found')) { $totalTableSkippedFieldNotFound++; } else if ("Not Implemented acl type ''" === substr($e->getMessage(), 0, strlen("Not Implemented acl type ''"))) { $totalTableSkippedMissingAclType++; } UI::alert('danger', "Problem z aktualizacją tabeli z relacjami ['{$refConf['ID']}'] od '{$refConf['ROOT_OBJECT_NS']}' do '{$refConf['CHILD_NAME']}'"); } } if ($totalTableSkippedNotAcl) UI::alert('warning', "Nie zaktualizowano {$totalTableSkippedNotAcl} tabeli z relajami - obiekty różnego typu od 'Acl'"); if ($totalTableSkippedFieldNotFound) UI::alert('warning', "Nie zaktualizowano {$totalTableSkippedFieldNotFound} tabeli z relajami - pola 'do' nie istnieją"); if ($totalTableSkippedMissingAclType) UI::alert('warning', "Nie zaktualizowano {$totalTableSkippedMissingAclType} tabeli z relajami - brak typu obiektu (Instance config)"); } public function viewStatusUsers() { $nowMinus3Months = date("Y-m-d", mktime(0,0,0, date('m') - 1, date('d'), date('Y'))); $sesUsers = DB::getPDO()->fetchAll(" select c.ID, c.CONF_KEY, c.CONF_VAL from CRM_CONFIG c where c.CONF_KEY like 'acl_user_%_%_cache_update' and c.CONF_VAL > '{$nowMinus3Months}' "); $sesUsers = array_reduce( $sesUsers, function ($ret, $record) { // $format = "acl_user_{ID_USERS}_{ID_PROCES}_cache_update"; list($idUser, $idProces) = explode('_', substr($record['CONF_KEY'], strlen('acl_user_'), -1 * strlen('_cache_update'))); if (!array_key_exists($idUser, $ret)) { $ret[$idUser] = [ 'idUser' => $idUser, 'lastUpdateAclCache' => $record['CONF_VAL'], 'log' => [] ]; } else { $ret[$idUser]['lastUpdateAclCache'] = ($record['CONF_VAL'] > $ret[$idUser]['lastUpdateAclCache']) ? $record['CONF_VAL'] : $ret[$idUser]['lastUpdateAclCache']; } $ret[$idUser]['log'][] = [ 'ID_PROCES' => $idProces, 'data' => $record['CONF_VAL'] ]; return $ret; }, [] ); $sesUsers = array_map(function ($sesGroup) { return [ 'idUser' => $sesGroup['idUser'], 'user' => DB::getPDO()->fetchValue("select u.ADM_ACCOUNT from ADMIN_USERS u where u.ID = {$sesGroup['idUser']}"), 'lastUpdateAclCache' => $sesGroup['lastUpdateAclCache'], 'log' => UI::h('span', [ 'style' => "color:#bbb" ], implode('
', array_map(function ($log) { return ($log['ID_PROCES'] > 0) ? "Filtr procesu {$log['ID_PROCES']} uruchomiony {$log['data']}" : "Filtr ogólny uruchomiony {$log['data']}"; }, $sesGroup['log']))), ]; }, $sesUsers); usort($sesUsers, function ($ua, $ub) { $a = $ua['lastUpdateAclCache']; $b = $ub['lastUpdateAclCache']; return ($a === $b) ? 0 : ( ($a < $b) ? 1 : -1 ) ; }); if ('0' == User::get('ADM_ADMIN_LEVEL')) { $sesUsers = array_map(function ($row) { $row['#'] = UI::h('div', [ 'style' => "display:inline-block", 'class' => "activateUserDebugBtn" . ( DBG::hasUserDebug($row['idUser'], User::getID()) ? ' active' : '' ) ], [ UI::h('label', ['style' => "padding-right:6px; font-weight:normal"], "Debug"), UI::hButtonAjax("Włącz", "activateUserDebug", [ 'class' => "btn btn-xs btn-default activateUserDebugBtn-activate", 'href' => $this->getLink('startUserDebugAjax'), 'data' => [ 'idUser' => $row['idUser'], 'do' => 'activate' ] ]), UI::hButtonAjax("Wyłącz", "activateUserDebug", [ 'class' => "btn btn-xs btn-default activateUserDebugBtn-deactivate", 'href' => $this->getLink('startUserDebugAjax'), 'data' => [ 'idUser' => $row['idUser'], 'do' => 'deactivate' ] ]), ]); return $row; }, $sesUsers); } UI::table([ 'caption' => UI::h('b', ['style' => "color:#000"], "Ostatnie logowania do aplikacji") . " (update acl cache)", // TODO: Aktualnie zalogowani użytkownicy 'rows' => $sesUsers ]); echo UI::h('style', ['type' => "text/css"], " .activateUserDebugBtn .activateUserDebugBtn-activate { display:inline } .activateUserDebugBtn .activateUserDebugBtn-deactivate { display:none } .activateUserDebugBtn.active .activateUserDebugBtn-activate { display:none } .activateUserDebugBtn.active .activateUserDebugBtn-deactivate { display:inline } "); echo UI::h('script', ['src'=>"static/vendor.js?_v=b636cab1", 'type'=>"text/javascript"]); echo UI::h('script', [], " (function (global) { if (!global.p5VendorJs.React) throw 'Missing p5VendorJs.React' if (!global.p5VendorJs.ReactDOM) throw 'Missing p5VendorJs.ReactDOM' if (!global.p5VendorJs.ToggleButton) throw 'Missing p5VendorJs.ToggleButton' if (!global.fetch) throw 'Missing global.fetch' var React = global.p5VendorJs.React var ReactDOM = global.p5VendorJs.ReactDOM var h = React.createElement function convertToReactToggle(n, activateBtn, deactivateBtn, isActive) { var toggleReact = document.createElement('div') toggleReact.style.display = 'inline-block' n.parentNode.insertBefore(toggleReact, n.nextSibling) deactivateBtn.style.display = 'none' activateBtn.style.display = 'none' function reactToggleBtnOnToggle(value) { if (value) { deactivateBtn.onclick() } else { activateBtn.onclick() } render_reactToggleBtn(!value) } function render_reactToggleBtn(state) { ReactDOM.render( h(global.p5VendorJs.ToggleButton, { value: state, onToggle: reactToggleBtnOnToggle }) , toggleReact ) } render_reactToggleBtn(isActive) } var toggles = document.querySelectorAll('.activateUserDebugBtn') for (var i = 0; i < toggles.length; i++) { var btns = toggles[i].querySelectorAll('a') if (2 !== btns.length) contiune; var activateBtn = btns[0] var deactivateBtn = btns[1] convertToReactToggle(toggles[i], activateBtn, deactivateBtn, toggles[i].classList.contains('active')) } })(window) "); UI::hButtonAjaxOnResponse("activateUserDebug", /* payload, n */ " p5UI__notifyAjaxCallback(payload) // console.log('activateUserDebug :: payload', payload) if ('success' !== payload.type) return false if (payload.body && 'active' in payload.body) { if (payload.body.active) { n.parentNode.classList.add('active') } else { n.parentNode.classList.remove('active') } } "); } public function startUserDebugAjaxAction() { Response::sendTryCatchJson(array($this, 'startUserDebugAjax'), $_POST); } public function startUserDebugAjax($args) { if ('0' !== (string)User::get('ADM_ADMIN_LEVEL')) throw new Exception("Access Denied"); $idUser = V::get('idUser', 0, $args); if ($idUser <= 0) throw new Exception("Missing idUser"); $do = V::get('do', 0, $args); if (!in_array($do, ['activate', 'deactivate'])) throw new Exception("Missing do"); $hasDebug = DBG::hasUserDebug($idUser, User::getID()); switch ($do) { case 'activate': DBG::startUserDebug($idUser, User::getID()); break; case 'deactivate': DBG::stopUserDebug($idUser, User::getID()); break; } return [ 'type' => 'success', '__args' => $args, '__$hasDebug' => $hasDebug, 'body' => [ 'active' => DBG::hasUserDebug($idUser, User::getID()) ] ]; } function checkDatabaseTablesPostTask() { $pdo = DB::getPDO(); // DBG::nicePrint($pdo, "DB Info"); // DBG::nicePrint(get_class_methods($pdo), "pdo methods"); $tblName = V::get('_fixTable', '', $_POST); if (!empty($tblName)) { $sqlTableName = DB::getPDO()->identifierQuote($tblName); $fixReturn = DB::getPDO()->fetchAll(" repair table {$sqlTableName} "); echo UI::hTable([ 'caption' => "Naprawa tabeli '{$tblName}':", 'rows' => $fixReturn ]); $lastFixRow = end($fixReturn); if ('OK' === V::get('Msg_text', '', $lastFixRow)) { UI::alert('success', "Naprawiono tabelę '{$tblName}'"); } else { UI::alert('danger', "Nie udało się naprawić tabeli '{$tblName}'"); } } $listTables = DB::getPDO()->fetchValuesList(" select TABLE_NAME from INFORMATION_SCHEMA.TABLES where TABLE_SCHEMA = :db_name and TABLE_TYPE = 'BASE TABLE' ", [ ':db_name' => DB::getPDO()->getDatabaseName(), ]); DBG::nicePrint($listTables, "all tables"); // $listTables = array_slice($listTables, 0, 10); // TODO: DBG UI::table([ 'rows' => array_map(function ($tblName) { $fixTableBtn = UI::hButtonPost("napraw tabele", [ 'class' => "btn btn-xs btn-primary", 'data' => [ '_postTask' => 'checkDatabaseTables', '_fixTable' => $tblName, ] ]); return [ 'table' => $tblName, 'status' => UI::h('details', [ 'open' => '' ], [ UI::h('summary', [], [ "check table `{$tblName}`", " ", $fixTableBtn, ]), UI::hTable([ 'rows' => DB::getPDO()->fetchAll(" check table `{$tblName}` ") ]), ]), ]; }, $listTables) ]); } }