From 22f32d9721809d2e655c7ab78d6a043b93de0af1 Mon Sep 17 00:00:00 2001 From: Michael Vogel Date: Fri, 9 Sep 2016 20:33:54 +0000 Subject: [PATCH] New process table for a better detection of running workers --- boot.php | 41 ++++++++++++++++++++++++++++++++++++- include/auth_ejabberd.php | 2 ++ include/cli_startup.php | 4 +++- include/cron.php | 1 + include/cronhooks.php | 2 ++ include/cronjobs.php | 1 + include/dbstructure.php | 13 ++++++++++++ include/dbupdate.php | 2 ++ include/delivery.php | 2 ++ include/directory.php | 2 ++ include/discover_poco.php | 2 ++ include/expire.php | 2 ++ include/gprobe.php | 2 ++ include/notifier.php | 2 ++ include/onepoll.php | 1 + include/poller.php | 28 ++++++++++++++++--------- include/pubsubpublish.php | 2 ++ include/queue.php | 1 + include/shadowupdate.php | 2 ++ include/tagupdate.php | 2 ++ include/threadupdate.php | 2 ++ include/update_gcontact.php | 2 ++ update.php | 2 +- 23 files changed, 107 insertions(+), 13 deletions(-) diff --git a/boot.php b/boot.php index d5b8439333..7097f3f983 100644 --- a/boot.php +++ b/boot.php @@ -38,7 +38,7 @@ define ( 'FRIENDICA_PLATFORM', 'Friendica'); define ( 'FRIENDICA_CODENAME', 'Asparagus'); define ( 'FRIENDICA_VERSION', '3.5-dev' ); define ( 'DFRN_PROTOCOL_VERSION', '2.23' ); -define ( 'DB_UPDATE_VERSION', 1201 ); +define ( 'DB_UPDATE_VERSION', 1202 ); /** * @brief Constant with a HTML line break. @@ -1099,6 +1099,42 @@ class App { } + /** + * @brief Log active processes into the "process" table + */ + function start_process() { + $trace = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 1); + + $command = basename($trace[0]["file"]); + + $this->remove_inactive_processes(); + + $r = q("SELECT `pid` FROM `process` WHERE `pid` = %d", intval(getmypid())); + if(!dbm::is_result($r)) + q("INSERT INTO `process` (`pid`,`command`,`created`) VALUES (%d, '%s', '%s')", + intval(getmypid()), + dbesc($command), + dbesc(datetime_convert())); + } + + /** + * @brief Remove inactive processes + */ + function remove_inactive_processes() { + $r = q("SELECT `pid` FROM `process`"); + if(dbm::is_result($r)) + foreach ($r AS $process) + if (!posix_kill($process["pid"], 0)) + q("DELETE FROM `process` WHERE `pid` = %d", intval($process["pid"])); + } + + /** + * @brief Remove the active process from the "process" table + */ + function end_process() { + q("DELETE FROM `process` WHERE `pid` = %d", intval(getmypid())); + } + /** * @brief Returns a string with a callstack. Can be used for logging. * @@ -1699,6 +1735,9 @@ function login($register = false, $hiddens=false) { * @brief Used to end the current process, after saving session state. */ function killme() { + + get_app()->end_process(); + if (!get_app()->is_backend()) session_write_close(); diff --git a/include/auth_ejabberd.php b/include/auth_ejabberd.php index 9a9d9accad..d7e91a5b2c 100755 --- a/include/auth_ejabberd.php +++ b/include/auth_ejabberd.php @@ -58,6 +58,8 @@ if(is_null($db)) { unset($db_host, $db_user, $db_pass, $db_data); }; +$a->start_process(); + // the logfile to which to write, should be writeable by the user which is running the server $sLogFile = get_config('jabber','logfile'); diff --git a/include/cli_startup.php b/include/cli_startup.php index d43bc1c947..7b15fbfb30 100644 --- a/include/cli_startup.php +++ b/include/cli_startup.php @@ -11,7 +11,7 @@ function cli_startup() { if(is_null($a)) { $a = new App; } - + if(is_null($db)) { @include(".htconfig.php"); require_once("dba.php"); @@ -19,6 +19,8 @@ function cli_startup() { unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + require_once('include/session.php'); load_config('config'); diff --git a/include/cron.php b/include/cron.php index 3f28e493cf..dde458a4a6 100644 --- a/include/cron.php +++ b/include/cron.php @@ -27,6 +27,7 @@ function cron_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); require_once('include/session.php'); require_once('include/datetime.php'); diff --git a/include/cronhooks.php b/include/cronhooks.php index 4bb1e5f659..986a86dfbb 100644 --- a/include/cronhooks.php +++ b/include/cronhooks.php @@ -17,6 +17,8 @@ function cronhooks_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + require_once('include/session.php'); require_once('include/datetime.php'); diff --git a/include/cronjobs.php b/include/cronjobs.php index 3a6df698e1..6df2dcd035 100644 --- a/include/cronjobs.php +++ b/include/cronjobs.php @@ -27,6 +27,7 @@ function cronjobs_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); require_once('include/session.php'); require_once('include/datetime.php'); diff --git a/include/dbstructure.php b/include/dbstructure.php index 53b94b46a8..4530a78599 100644 --- a/include/dbstructure.php +++ b/include/dbstructure.php @@ -1114,6 +1114,17 @@ function db_definition() { "choice" => array("choice"), ) ); + $database["process"] = array( + "fields" => array( + "pid" => array("type" => "int(10) unsigned", "not null" => "1", "primary" => "1"), + "command" => array("type" => "varchar(32)", "not null" => "1", "default" => ""), + "created" => array("type" => "datetime", "not null" => "1", "default" => "0000-00-00 00:00:00"), + ), + "indexes" => array( + "PRIMARY" => array("pid"), + "command" => array("command"), + ) + ); $database["profile"] = array( "fields" => array( "id" => array("type" => "int(11)", "not null" => "1", "extra" => "auto_increment", "primary" => "1"), @@ -1456,6 +1467,8 @@ function dbstructure_run(&$argv, &$argc) { unset($db_host, $db_user, $db_pass, $db_data); } + $a->start_process(); + if ($argc==2) { switch ($argv[1]) { case "update": diff --git a/include/dbupdate.php b/include/dbupdate.php index 28f1de340b..898f459630 100644 --- a/include/dbupdate.php +++ b/include/dbupdate.php @@ -16,6 +16,8 @@ function dbupdate_run(&$argv, &$argc) { unset($db_host, $db_user, $db_pass, $db_data); } + $a->start_process(); + load_config('config'); load_config('system'); diff --git a/include/delivery.php b/include/delivery.php index fe33774382..59cab43714 100644 --- a/include/delivery.php +++ b/include/delivery.php @@ -21,6 +21,8 @@ function delivery_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); } + $a->start_process(); + require_once("include/session.php"); require_once("include/datetime.php"); require_once('include/items.php'); diff --git a/include/directory.php b/include/directory.php index 85476bd5fd..381020c8a5 100644 --- a/include/directory.php +++ b/include/directory.php @@ -15,6 +15,8 @@ function directory_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + load_config('config'); load_config('system'); diff --git a/include/discover_poco.php b/include/discover_poco.php index 0b468faea1..9c9be8209c 100644 --- a/include/discover_poco.php +++ b/include/discover_poco.php @@ -18,6 +18,8 @@ function discover_poco_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + require_once('include/session.php'); require_once('include/datetime.php'); diff --git a/include/expire.php b/include/expire.php index 873c594e84..cfd38d3dcd 100644 --- a/include/expire.php +++ b/include/expire.php @@ -16,6 +16,8 @@ function expire_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + require_once('include/session.php'); require_once('include/datetime.php'); require_once('include/items.php'); diff --git a/include/gprobe.php b/include/gprobe.php index 91b9b16e33..d3ab028f1e 100644 --- a/include/gprobe.php +++ b/include/gprobe.php @@ -18,6 +18,8 @@ function gprobe_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + require_once('include/session.php'); require_once('include/datetime.php'); diff --git a/include/notifier.php b/include/notifier.php index 0610a4e398..5f700ee716 100644 --- a/include/notifier.php +++ b/include/notifier.php @@ -54,6 +54,8 @@ function notifier_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); } + $a->start_process(); + require_once("include/session.php"); require_once("include/datetime.php"); require_once('include/items.php'); diff --git a/include/onepoll.php b/include/onepoll.php index eb1045de14..c89e5b257c 100644 --- a/include/onepoll.php +++ b/include/onepoll.php @@ -24,6 +24,7 @@ function onepoll_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); require_once('include/session.php'); require_once('include/datetime.php'); diff --git a/include/poller.php b/include/poller.php index 0835528717..83ecb29395 100644 --- a/include/poller.php +++ b/include/poller.php @@ -29,6 +29,10 @@ function poller_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + + $mypid = getmypid(); + if ($a->max_processes_reached()) return; @@ -81,15 +85,19 @@ function poller_run(&$argv, &$argc){ q("UPDATE `workerqueue` SET `executed` = '%s', `pid` = %d WHERE `id` = %d AND `executed` = '0000-00-00 00:00:00'", dbesc(datetime_convert()), - intval(getmypid()), + intval($mypid), intval($r[0]["id"])); // Assure that there are no tasks executed twice - $id = q("SELECT `id` FROM `workerqueue` WHERE `id` = %d AND `pid` = %d", - intval($r[0]["id"]), - intval(getmypid())); + $id = q("SELECT `pid`, `executed` FROM `workerqueue` WHERE `id` = %d", intval($r[0]["id"])); if (!$id) { - logger("Queue item ".$r[0]["id"]." was executed multiple times - skip this execution", LOGGER_DEBUG); + logger("Queue item ".$r[0]["id"]." vanished - skip this execution", LOGGER_DEBUG); + continue; + } elseif ((strtotime($id[0]["executed"]) <= 0) OR ($id[0]["pid"] == 0)) { + logger("Entry for queue item ".$r[0]["id"]." wasn't stored - we better stop here", LOGGER_DEBUG); + return; + } elseif ($id[0]["pid"] != $mypid) { + logger("Queue item ".$r[0]["id"]." is to be executed by process ".$id[0]["pid"]." and not by me (".$mypid.") - skip this execution", LOGGER_DEBUG); continue; } @@ -111,15 +119,15 @@ function poller_run(&$argv, &$argc){ $funcname = str_replace(".php", "", basename($argv[0]))."_run"; if (function_exists($funcname)) { - logger("Process ".getmypid()." - Prio ".$r[0]["priority"]." - ID ".$r[0]["id"].": ".$funcname." ".$r[0]["parameter"]); + logger("Process ".$mypid." - Prio ".$r[0]["priority"]." - ID ".$r[0]["id"].": ".$funcname." ".$r[0]["parameter"]); $funcname($argv, $argc); if ($cooldown > 0) { - logger("Process ".getmypid()." - Prio ".$r[0]["priority"]." - ID ".$r[0]["id"].": ".$funcname." - in cooldown for ".$cooldown." seconds"); + logger("Process ".$mypid." - Prio ".$r[0]["priority"]." - ID ".$r[0]["id"].": ".$funcname." - in cooldown for ".$cooldown." seconds"); sleep($cooldown); } - logger("Process ".getmypid()." - Prio ".$r[0]["priority"]." - ID ".$r[0]["id"].": ".$funcname." - done"); + logger("Process ".$mypid." - Prio ".$r[0]["priority"]." - ID ".$r[0]["id"].": ".$funcname." - done"); q("DELETE FROM `workerqueue` WHERE `id` = %d", intval($r[0]["id"])); } else @@ -319,9 +327,9 @@ function poller_too_much_workers() { } function poller_active_workers() { - $workers = q("SELECT COUNT(*) AS `workers` FROM `workerqueue` WHERE `executed` != '0000-00-00 00:00:00'"); + $workers = q("SELECT COUNT(*) AS `processes` FROM `process` WHERE `command` = 'poller.php'"); - return($workers[0]["workers"]); + return($workers[0]["processes"]); } if (array_search(__file__,get_included_files())===0){ diff --git a/include/pubsubpublish.php b/include/pubsubpublish.php index 85637facb2..3fff746cb2 100644 --- a/include/pubsubpublish.php +++ b/include/pubsubpublish.php @@ -70,6 +70,8 @@ function pubsubpublish_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + require_once('include/items.php'); load_config('config'); diff --git a/include/queue.php b/include/queue.php index 47a3596bdb..6dcdfc8960 100644 --- a/include/queue.php +++ b/include/queue.php @@ -17,6 +17,7 @@ function queue_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); require_once("include/session.php"); require_once("include/datetime.php"); diff --git a/include/shadowupdate.php b/include/shadowupdate.php index 74c2a43ebd..e003edea17 100644 --- a/include/shadowupdate.php +++ b/include/shadowupdate.php @@ -14,6 +14,8 @@ if(is_null($db)) { unset($db_host, $db_user, $db_pass, $db_data); } +$a->start_process(); + load_config('config'); load_config('system'); diff --git a/include/tagupdate.php b/include/tagupdate.php index b12e809772..f962a8f3ac 100644 --- a/include/tagupdate.php +++ b/include/tagupdate.php @@ -14,6 +14,8 @@ if(is_null($db)) { unset($db_host, $db_user, $db_pass, $db_data); } +$a->start_process(); + load_config('config'); load_config('system'); diff --git a/include/threadupdate.php b/include/threadupdate.php index e9d9bf6e6b..454a4680af 100644 --- a/include/threadupdate.php +++ b/include/threadupdate.php @@ -14,6 +14,8 @@ if(is_null($db)) { unset($db_host, $db_user, $db_pass, $db_data); } +$a->start_process(); + load_config('config'); load_config('system'); diff --git a/include/update_gcontact.php b/include/update_gcontact.php index 88e1817f0b..ba0993d14d 100644 --- a/include/update_gcontact.php +++ b/include/update_gcontact.php @@ -16,6 +16,8 @@ function update_gcontact_run(&$argv, &$argc){ unset($db_host, $db_user, $db_pass, $db_data); }; + $a->start_process(); + require_once('include/Scrape.php'); require_once("include/socgraph.php"); diff --git a/update.php b/update.php index 80ce96c382..f1981f730f 100644 --- a/update.php +++ b/update.php @@ -1,6 +1,6 @@