| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345 |
- <?php
- Lib::loadClass('RouteBase');
- Lib::loadClass('Core_AsyncJobs');
- class Route_AsyncJobs extends RouteBase {
- function isInstalled() { return Core_AsyncJobs::isInstalled(); }
- function getSbinPath() { return realpath(APP_PATH_ROOT . "/../sbin/"); }
- function defaultAction() { UI::layout([ $this, 'defaultView' ]); }
- function defaultView() {
- echo UI::h('h1', [], "Async jobs (wps server)");
- if (!User::isAdmin()) throw new Exception("Access Denied");
- DBG::nicePrint(Config::getConfFile(), "Config::getConfFile()");
- try {
- Core_AsyncJobs::isInstalled();
- } catch (Exception $e) {
- UI::alert('danger', $e->getMessage());
- }
- echo UI::h('div', [ 'style' => "padding:12px 0; border-bottom:1px solid #ddd" ], [
- UI::hButtonPost("Check", [
- 'class' => "btn btn-default",
- 'title' => "check if async process manager is working",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "pm2Check",
- ]
- ]),
- " ",
- UI::h('a', [
- 'href' => $this->getLink('list'),
- 'class' => "btn btn-default",
- ], "Lista"),
- " ",
- UI::hButtonPost("pm2 list", [
- 'class' => "btn btn-warning",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "pm2List",
- ]
- ]),
- " ",
- UI::hButtonPost("pm2 kill", [
- 'class' => "btn btn-warning",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "pm2Kill",
- ]
- ]),
- " ",
- UI::hButtonPost("pm2 run1", [
- 'class' => "btn btn-warning",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "mp2Start1",
- ]
- ]),
- " ",
- UI::hButtonPost("pm2 run2", [
- 'class' => "btn btn-warning",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "mp2Start2",
- ]
- ]),
- " ",
- UI::hButtonPost("pm2 run3", [
- 'class' => "btn btn-warning",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "mp2Start3",
- ]
- ]),
- " ",
- UI::hButtonPost("pm2 delete stopped", [
- 'class' => "btn btn-warning",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "mp2DeleteStopped",
- ]
- ]),
- " ",
- UI::hButtonPost("reinstall pm2-www", [
- 'class' => "btn btn-warning",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "testReinstallPm2ByWWW",
- ]
- ]),
- " ",
- UI::hButtonPost("Test", [
- 'class' => "btn btn-warning",
- 'title' => "Test server permissions",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "makeTests",
- ]
- ]),
- ]);
- $postTask = V::get('_postTask', '', $_POST);
- switch ($postTask) {
- case "pm2Check": UI::tryCatchView([ $this, 'pm2CheckPostTask' ]); break;
- case "pm2List": UI::tryCatchView([ $this, 'pm2ListPostTask' ]); break;
- case "pm2Kill": UI::tryCatchView([ $this, 'pm2KillPostTask' ]); break;
- case "mp2Start1": UI::tryCatchView([ $this, 'mp2Start1PostTask' ]); break;
- case "mp2Start2": UI::tryCatchView([ $this, 'mp2Start2PostTask' ]); break;
- case "mp2Start3": UI::tryCatchView([ $this, 'mp2Start3PostTask' ]); break;
- case "mp2DeleteStopped": UI::tryCatchView([ $this, 'mp2DeleteStoppedPostTask' ]); break;
- case "testReinstallPm2ByWWW": UI::tryCatchView([ $this, 'testReinstallPm2ByWWWPostTask' ]); break;
- case "makeTests": UI::tryCatchView([ $this, 'makeTestsPostTask' ]); break;
- }
- }
- function pm2CheckPostTask() {
- $cmd = "pm2 ping";
- V::exec($cmd, $out, $ret);
- echo "cmd: <code>{$cmd}</code><br>RETURN CODE: '{$ret}'<br><pre>OUTPUT:\n" . implode("\n", $out) . "</pre>";
- // expected: end($out) === "{ msg: 'pong' }"
- }
- function listAction() { UI::layout([ $this, 'listView' ]); }
- function listView() {
- echo UI::h('ol', [ 'class' => "breadcrumb", 'style' => "font-size:14px" ], [
- UI::h('li', [], [
- UI::h('i', [ 'class' => "glyphicon glyphicon-home" ]),
- " ",
- UI::h('a', [ 'href' => $this->getLink() ], "Async jobs"),
- ]),
- UI::h('li', [ 'class' => "active" ], [
- "Lista"
- ]),
- UI::h('a', [
- 'href' => $this->getLink('list'),
- 'class' => "pull-right btn btn-link",
- 'style' => "padding:0; line-height:1em",
- ], "odśwież"),
- ]);
- $postTask = V::get('_postTask', '', $_POST);
- switch ($postTask) {
- case "stopJob": UI::tryCatchView([ $this, 'stopJobPostTask' ]); break;
- case "startJob": UI::tryCatchView([ $this, 'startJobPostTask' ]); break;
- }
- echo UI::hTable([
- 'rows' => array_map([ $this, 'viewTableRowAsyncJob' ], Core_AsyncJobs::getSimpleList()),
- ]);
- }
- function stopJobPostTask() {
- $idJob = V::get('idJob', 0, $_POST, 'int'); // $jobInfo['pm_id'],
- $name = V::get('name', '', $_POST); // $jobInfo['name'],
- if ($idJob < 0) throw new Exception("Wrong param idJob");
- if ($idJob === 0 && $_POST['idJob'] !== '0') throw new Exception("Wrong param idJob 0");
- Core_AsyncJobs::stopJob($idJob);
- }
- function startJobPostTask() {
- $idJob = V::get('idJob', 0, $_POST, 'int'); // $jobInfo['pm_id'],
- $name = V::get('name', '', $_POST); // $jobInfo['name'],
- if ($idJob < 0) throw new Exception("Wrong param idJob");
- if ($idJob === 0 && $_POST['idJob'] !== '0') throw new Exception("Wrong param idJob 0");
- Core_AsyncJobs::startJob($idJob);
- }
- function pm2ListPostTask() {
- $cmd = "pm2 list";
- V::exec($cmd, $out, $ret);
- echo "cmd: <code>{$cmd}</code><br>RETURN CODE: '{$ret}'<br><pre>OUTPUT:\n" . implode("\n", $out) . "</pre>";
- $cmd = "pm2 jlist";
- V::exec($cmd, $out, $ret);
- echo "cmd: <code>{$cmd}</code><br>RETURN CODE: '{$ret}'<br><pre>OUTPUT:\n" . implode("\n", $out) . "</pre>";
- echo '<hr style="margin:24px auto">';
- $parsedJobList = Core_AsyncJobs::getFullList();
- DBG::nicePrint($parsedJobList, "\$parsedJobList");
- echo '<hr style="margin:24px auto">';
- UI::table([
- 'rows' => array_map([ $this, 'viewTableRowAsyncJob' ], Core_AsyncJobs::getSimpleList()),
- ]);
- }
- function viewTableRowAsyncJob($jobInfo) {
- return [
- 'name' => $jobInfo['name'],
- 'pid' => $jobInfo['pid'],
- 'pm_id' => $jobInfo['pm_id'],
- 'status' => $jobInfo['pm2_env.status'],
- 'memory' => $jobInfo['monit.memory'],
- 'cpu' => $jobInfo['monit.cpu'],
- '#' => UI::h(null, [], [
- UI::h('a', [
- 'href' => $this->getLink('jobLog', [
- 'idJob' => $jobInfo['pm_id'],
- 'name' => $jobInfo['name'],
- ]),
- 'class' => "btn btn-xs btn-warning",
- ], "logi"),
- " ",
- UI::hButtonPost("stop", [
- 'class' => "btn btn-xs btn-default",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "stopJob",
- 'idJob' => $jobInfo['pm_id'],
- 'name' => $jobInfo['name'],
- ]
- ]),
- " ",
- UI::hButtonPost("start", [
- 'class' => "btn btn-xs btn-default",
- 'data' => [
- '_route' => 'AsyncJobs',
- '_postTask' => "startJob",
- 'idJob' => $jobInfo['pm_id'],
- 'name' => $jobInfo['name'],
- ]
- ]),
- ]),
- ];
- }
- function jobLogAction() { UI::layout([ $this, 'jobLogView' ]); }
- function jobLogView() {
- $idJob = V::get('idJob', 0, $_GET, 'int'); // $jobInfo['pm_id'],
- $name = V::get('name', '', $_GET); // $jobInfo['name'],
- echo UI::h('ol', [ 'class' => "breadcrumb", 'style' => "font-size:14px" ], [
- UI::h('li', [], [
- UI::h('i', [ 'class' => "glyphicon glyphicon-home" ]),
- " ",
- UI::h('a', [ 'href' => $this->getLink() ], "Async jobs"),
- ]),
- UI::h('li', [], [
- UI::h('a', [ 'href' => $this->getLink('list') ], "Lista"),
- ]),
- UI::h('li', [ 'class' => "active" ], [
- "Log dla '{$idJob}'",
- ]),
- ]);
- if ($idJob < 0) throw new Exception("Wrong param idJob");
- if ($idJob === 0 && $_GET['idJob'] !== '0') throw new Exception("Wrong param idJob 0");
- $out = Core_AsyncJobs::getJobLogs($idJob, 10);
- echo UI::h('div', [ 'style' => "background-color:#ddd; padding:4px 12px" ], "Logi dla zadania '{$idJob}'");
- echo UI::h('pre', [ 'style' => "border:1px solid #ddd; border-radius:0; padding:12px" ], $out);
- }
- function pm2KillPostTask() {
- $cmd = "pm2 kill";
- V::exec($cmd, $out, $ret);
- echo "cmd: <code>{$cmd}</code><br>RETURN CODE: '{$ret}'<br><pre>OUTPUT:\n" . implode("\n", $out) . "</pre>";
- }
- function mp2Start1PostTask() {
- $cmd = "pm2 start " . APP_PATH_ROOT . "/../sbin/test-sleep-loop.php --name='test-job-1'";
- V::exec($cmd . " 2>&1", $out, $ret);
- echo "cmd: <code>{$cmd}</code><br>RETURN CODE: '{$ret}'<br><pre>OUTPUT:\n" . implode("\n", $out) . "</pre>";
- }
- function mp2Start2PostTask() {
- $cmd = "pm2 start " . APP_PATH_ROOT . "/../sbin/test-sleep-loop.php --name='test-job-2'";
- V::exec($cmd . " 2>&1", $out, $ret);
- echo "cmd: <code>{$cmd}</code><br>RETURN CODE: '{$ret}'<br><pre>OUTPUT:\n" . implode("\n", $out) . "</pre>";
- }
- function mp2Start3PostTask() {
- $jobName = implode("&", [
- "ant=default_db.in7_dziennik_koresp/test-bash",
- "task=test-loop",
- "ns=default_db:IN7_DZIENNIK_KORESP",
- "pk=66263",
- ]);
- $jobNamespace = "p5";
- $cmd = implode(" ", [
- "pm2 start",
- APP_PATH_ROOT . "/../sbin/test-sleep-loop.php",
- "--name='{$jobName}'",
- "--namespace='{$jobNamespace}'",
- ]);
- V::exec($cmd . " 2>&1", $out, $ret);
- echo "cmd: <code>{$cmd}</code><br>RETURN CODE: '{$ret}'<br><pre>OUTPUT:\n" . implode("\n", $out) . "</pre>";
- }
- function mp2DeleteStoppedPostTask() {
- Core_AsyncJobs::deleteStopped();
- UI::alert("DONE");
- }
- function makeTestsPostTask() {
- $seBinPath = $this->getSbinPath();
- $listTest = []; // [ [ ret_code, cmd ], ... ]
- $listTest[] = [ 0, "cd '{$seBinPath}' && bash ./se.sh test-exit-0" ];
- $listTest[] = [ 1, "cd '{$seBinPath}' && bash ./se.sh test-exit-1" ];
- $listTest[] = [ 1, "cd '{$seBinPath}' && bash ./se.sh test-sudo" ];
- $listTest[] = [ 0, "cd '{$seBinPath}' && bash ./se.sh --sudo test-sudo" ];
- // $cmd = "cd '{$seBinPath}' && bash se.sh install-pm2-www"; // DBG: require root, add prefix 'sudo--'
- // $cmd = "cd '{$seBinPath}' && bash ./se.sh --sudo install-pm2-www";
- // $cmd = "cd '{$seBinPath}' && bash se.sh install-pm2-www"; // expected Permission denied - missing sudo
- // $cmd = "cd '{$seBinPath}' && bash se.sh sudo "; // expected Missing script name + usage
- // $cmd = "cd '{$seBinPath}' && bash se.sh non-existing-script"; // expecte Module not exists + usage
- // $cmd = "cd '{$seBinPath}' && bash se.sh "; // expected usage
- foreach ($listTest as $idx => $test) {
- list($expected, $cmd) = $test;
- $out = [];
- V::exec($cmd = "{$cmd} 2>&1", $out, $ret);
- echo UI::h('details', [], [
- UI::h('summary', [], "test {$idx} " . (($expected === $ret) ? "SUCCESS" : "FAILED")),
- UI::h('div', [], [
- UI::h('pre', [], "RET({$ret}). OUTPUT:" . "\n" . implode("\n", $out)),
- UI::h('div', [ 'class' => "alert alert-info" ], "test ({$ret})" . "\n<br>" . implode("\n<br>", $out) ),
- ($expected === $ret)
- ? UI::h('div', [ 'class' => 'alert alert-success' ], "OK: script return as expected!")
- : UI::h('div', [ 'class' => 'alert alert-danger' ], "FAIL: script return '{$ret}' but expected '{$expected}'!")
- ,
- ]),
- ]);
- }
- }
- function testReinstallPm2ByWWWPostTask() {
- $seBinPath = $this->getSbinPath();
- $out = [];
- $cmd = "cd '{$seBinPath}' && bash ./se.sh --sudo install-pm2-www";
- V::exec($cmd = "{$cmd} 2>&1", $out, $ret);
- echo UI::h('pre', [], "RET({$ret}). OUTPUT:" . "\n" . implode("\n", $out));
- if (0 !== $ret) throw new Exception( (empty($out)) ? "Error: install pm2-www failed! ({$ret})" : implode("\n<br>", $out) );
- if (!file_exists('/usr/local/bin/pm2-www')) {
- throw new Exception("Nie udało się zainstalować pm2-www");
- } else {
- throw new AlertSuccessException("Zainstalowano pm2-www");
- }
- }
- }
|