modifs.mineures sans commentaires

This commit is contained in:
Jephté Clain 2024-06-14 13:29:47 +04:00
parent e9ab61b154
commit dca04418b7
5 changed files with 74 additions and 16 deletions

View File

@ -3,7 +3,7 @@
$internalUse = $argv[1] ?? null;
if ($internalUse !== "--internal-use") exit("Wrong args");
$paramsfile = $argv[2] ?? null;
if (!file_exists($paramsfile)) exit("bad params file");
if (!file_exists($paramsfile)) exit("Bad params file");
$argc -= 2;
$argv = array_merge(
array_slice($argv, 0, 1),
@ -14,12 +14,14 @@ $app_params = unserialize(file_get_contents($paramsfile));
require $app_params["vendor"]["autoload"];
use nur\cli\Application;
use nur\sery\output\msg;
use nur\sery\wip\app\app;
use nur\sery\app\launcher;
use nur\yaml;
class _LaunchApp extends Application {
const NAME = "_launch";
const USE_LOGFILE = true;
const ACTION_INFOS = 0, ACTION_START = 1, ACTION_STOP = 2;
@ -46,15 +48,18 @@ class _LaunchApp extends Application {
function main() {
$appClass = $this->args[0] ?? null;
if ($appClass === null) {
self::die("Vous devez spécifier la classe de l'application");
msg::error("Vous devez spécifier la classe de l'application");
self::die();
} elseif (!class_exists($appClass)) {
self::die("$appClass: Cette classe n'existe pas");
msg::error("$appClass: Cette classe n'existe pas");
self::die();
}
$args = array_slice($this->args, 1);
$useRunfile = constant("$appClass::USE_RUNFILE");
if (!$useRunfile) {
self::die("Cette application ne supporte pas l'usage de runfile");
msg::error("Cette application ne supporte pas l'usage de runfile");
self::die();
}
$runfile = app::with($appClass, self::$internal_use_app_params)->getRunfile();

View File

@ -9,6 +9,9 @@ use nur\config\ArrayConfig;
use nur\msg;
use nur\os;
use nur\path;
use nur\sery\app\launcher;
use nur\sery\app\RunFile;
use nur\sery\cl;
use nur\sery\wip\app\app;
use nur\sery\output\log as nlog;
use nur\sery\output\msg as nmsg;
@ -365,4 +368,15 @@ abstract class Application {
}
abstract function main();
const BGLAUNCH_SCRIPT = null;
static function runfile(): RunFile {
$callerParams = app::get()->getParams();
return app::with(static::class, $callerParams)->getRunfile();
}
static function bglaunch(?array $args=null) {
launcher::launch(static::class, cl::merge([
static::BGLAUNCH_SCRIPT,
], $args));
}
}

View File

@ -37,12 +37,13 @@ class RunFile {
}
protected function initData(bool $withDateStart=true): array {
$pid = $withDateStart? posix_getpid(): null;
$dateStart = $withDateStart? new DateTime(): null;
return [
"name" => $this->name,
"id" => bin2hex(random_bytes(16)),
"pg_pid" => null,
"pid" => posix_getpid(),
"pid" => $pid,
"serial" => 0,
# lock
"locked" => false,
@ -52,6 +53,7 @@ class RunFile {
"date_start" => $dateStart,
"date_stop" => null,
"exitcode" => null,
"is_done" => null,
# action
"action" => null,
"action_date_start" => null,
@ -72,22 +74,27 @@ class RunFile {
$file->lockWrite();
$data = $file->unserialize(null, false, true);
if (!is_array($data)) {
$data = $this->initData();
$data = $this->initData(false);
$file->ftruncate();
$file->serialize($data, false, true);
}
$file->ftruncate();
return [$file, $data];
}
protected function serialize(SharedFile $file, array $data, ?array $merge=null): void {
$file->ftruncate();
$file->serialize(self::merge($data, $merge), true, true);
}
protected function update(callable $func): void {
/** @var SharedFile$file */
[$file, $data] = $this->willWrite();
$merge = call_user_func($func, $data);
$this->serialize($file, $data, $merge);
if ($merge !== null && $merge !== false) {
$this->serialize($file, $data, $merge);
} else {
$file->cancelWrite();
}
}
function haveWorked(int $serial, ?int &$currentSerial=null): bool {
@ -154,20 +161,20 @@ class RunFile {
});
}
/** tester si l'application a déjà été démarrée */
/** tester si l'application a déjà été démarrée au moins une fois */
function wasStarted(): bool {
$data = $this->read();
return $data["date_start"] !== null;
}
/** tester si l'application est démarrée et non arrêtée */
function isStarted(): bool {
function isStarted(?array &$data=null): bool {
$data = $this->read();
return $data["date_start"] !== null && $data["date_stop"] === null;
}
/**
* vérifier si la tâche tourne et est accessible
* vérifier si l'application marquée comme démarrée tourne réellement
*/
function isRunning(?array &$data=null): bool {
$data = $this->read();
@ -198,14 +205,14 @@ class RunFile {
});
}
/** tester si l'application est déjà été stoppée */
/** tester si l'application est déjà été stoppée au moins une fois */
function wasStopped(): bool {
$data = $this->read();
return $data["date_stop"] !== null;
}
/** tester si l'application a été démarrée puis arrêtée */
function isStopped(): bool {
function isStopped(?array &$data=null): bool {
$data = $this->read();
return $data["date_start"] !== null && $data["date_stop"] !== null;
}
@ -221,6 +228,24 @@ class RunFile {
});
}
/**
* comme {@link self::isStopped()} mais ne renvoie true qu'une seule fois si
* $updateDone==true
*/
function isDone(?array &$data=null, bool $updateDone=true): bool {
$done = false;
$this->update(function (array $ldata) use (&$done, &$data, $updateDone) {
$data = $ldata;
if ($data["date_start"] === null || $data["date_stop"] === null || $data["is_done"]) {
return false;
}
$done = true;
if (!$updateDone) return null;
return ["is_done" => $done];
});
return $done;
}
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# gestion des actions

View File

@ -8,7 +8,7 @@ use nur\sery\StateException;
use nur\sery\wip\app\app;
class launcher {
static function launch(string $appClass, ...$args): int {
static function launch(string $appClass, array $args): int {
$app = app::get();
$vendorBindir = $app->getVendorbindir();
$launch_php = "$vendorBindir/_launch.php";
@ -21,17 +21,20 @@ class launcher {
$cmd = new Cmd([
$launch_php,
"--internal-use", $tmpfile->getFile(),
$appClass, ...$args,
$appClass, "--", ...$args,
]);
$cmd->addRedir("null");
$cmd->passthru($exitcode);
# attendre un peu que la commande aie le temps de s'initialiser
sleep(1);
$tmpfile->close();
return $exitcode;
}
static function _start(array $args, Runfile $runfile): bool {
if ($runfile->isLocked()) return false;
if ($runfile->warnIfLocked()) return false;
$pid = pcntl_fork();
if ($pid == -1) {
# parent, impossible de forker
@ -43,6 +46,7 @@ class launcher {
## child, fork ok
# Créer un groupe de process, pour pouvoir les tuer toutes en même temps
$runfile->tm_startPg();
$pid = posix_getpid();
$exitcode = -776;
try {
# puis lancer la commande
@ -50,7 +54,9 @@ class launcher {
#XXX fichier de log?
$cmd->addSource("/g/init.env");
$cmd->addRedir("null");
msg::debug("$pid: launching\n".$cmd->getCmd());
$cmd->fork_exec($exitcode);
msg::debug("$pid: exitcode=$exitcode");
return true;
} finally {
$runfile->wfStopped($exitcode);

View File

@ -455,4 +455,12 @@ class Stream extends AbstractIterator implements IReader, IWriter {
function serialize($object, bool $close=true, bool $alreadyLocked=false): void {
$this->putContents(serialize($object), $close, $alreadyLocked);
}
/**
* annuler une tentative d'écriture commencée avec {@link self::canWrite()}
*/
function cancelWrite(bool $close=true): void {
if ($this->useLocking) $this->unlock($close);
elseif ($close) $this->close();
}
}