274 lines
7.1 KiB
PHP
274 lines
7.1 KiB
PHP
<?php chdir(__DIR__) ?>
|
|
<?php require 'base.php' ?>
|
|
<?php
|
|
|
|
if (!isset($argv) || $argv === NULL) die;
|
|
|
|
if (file_exists('.cron.lock'))
|
|
die('cron.php is locked by ".cron.lock"');
|
|
touch('.cron.lock');
|
|
|
|
function logi($thing) { echo date('Y/m/d H:i:s').' INFO | '.strval($thing)."\n"; }
|
|
function loge($thing) { echo date('Y/m/d H:i:s').' ERROR | '.strval($thing)."\n"; }
|
|
|
|
function end_cronjobs() {
|
|
unlink('.cron.lock');
|
|
die;
|
|
}
|
|
|
|
|
|
////////////////
|
|
// INITIAL SETUP
|
|
//
|
|
$GLOBALS['_crondir'] = $GLOBALS['appconf']['data_dir'].'/cron';
|
|
if (!file_exists($GLOBALS['_crondir'])) {
|
|
mkdir($GLOBALS['_crondir']);
|
|
end_cronjobs();
|
|
}
|
|
$time_start = time();
|
|
//
|
|
////////////////
|
|
|
|
|
|
////////////////////////////////
|
|
// CRONJOBS for database caching
|
|
//
|
|
function run__cronjobs_db() {
|
|
$dir = $GLOBALS['_crondir'].'/db';
|
|
if (!file_exists($dir)) {
|
|
mkdir($dir);
|
|
return false;
|
|
}
|
|
$jobs = [];
|
|
foreach (scandir($dir) as $jf) {
|
|
if (in_array($jf,['.','..']))
|
|
continue;
|
|
$ps = explode(',',$jf);
|
|
$jobs []= (object)[
|
|
'id' => $ps[2],
|
|
'file' => $dir.'/'.$jf,
|
|
'software' => $ps[0],
|
|
'instance' => $ps[1],
|
|
'time' => intval($ps[3]),
|
|
];
|
|
}
|
|
foreach ($jobs as $job) {
|
|
$ms = time() - filemtime($job->file);
|
|
$data = null;
|
|
$data = @unserialize(file_get_contents($job->file));
|
|
if ($data === false) {
|
|
$data = ['last_accessed' => time(), 'sql' => $data];
|
|
file_put_contents($job->file, serialize($data));
|
|
}
|
|
if ($ms < $job->time) continue;
|
|
|
|
logi("Processing job: {$job->id}, software={$job->software}, instance={$job->instance}");
|
|
$ok = false;
|
|
switch ($job->software) {
|
|
case 'mastodon':
|
|
$pg = new PgDatabase($job->software, $job->instance);
|
|
if ($pg->is_ok()) {
|
|
$result = $pg->fetch_all($data['sql']);
|
|
content_cache__put($job->software.$job->instance.$data['sql'], 'always,'.$job->time, $result);
|
|
$pg->close();
|
|
$ok = true;
|
|
}
|
|
break;
|
|
}
|
|
if ($ok) {
|
|
logi("Job done: {$job->id}");
|
|
touch($job->file);
|
|
}
|
|
}
|
|
}
|
|
run__cronjobs_db();
|
|
//
|
|
////////////////////////////////
|
|
|
|
|
|
///////////////////////////////
|
|
// CRONJOBS for caching cleanup
|
|
//
|
|
function run__cronjobs_cache_cleanup() {
|
|
$cache_dir = $GLOBALS['appconf']['data_dir'].'/cache';
|
|
if (!file_exists($cache_dir))
|
|
return;
|
|
$others = [];
|
|
foreach (scandir($cache_dir) as $fl) {
|
|
if (in_array($fl, ['.','..']))
|
|
continue;
|
|
$ps = explode(',',$fl);
|
|
if ($ps[1] !== 'ondemand') {
|
|
$others []= $fl;
|
|
continue;
|
|
}
|
|
$time = intval($ps[2]);
|
|
$mtime = filemtime($cache_dir.'/'.$fl);
|
|
if (time() - $mtime >= $time) {
|
|
logi('CACHE-CLEANUP remove old file: '.$fl);
|
|
unlink($cache_dir.'/'.$fl);
|
|
}
|
|
}
|
|
$crondb_dir = $GLOBALS['appconf']['data_dir'].'/cron/db';
|
|
foreach (scandir($crondb_dir) as $fl) {
|
|
if (in_array($fl, ['.','..']))
|
|
continue;
|
|
$cron_file = $crondb_dir.'/'.$fl;
|
|
$data = @unserialize(file_get_contents($cron_file));
|
|
if ($data === false || !isset($data['last_accessed']))
|
|
continue;
|
|
$ms = time() - $data['last_accessed'];
|
|
$days_diff = intval($ms / 60 / 60 / 24);
|
|
if ($days_diff >= 7) {
|
|
logi('CACHE-CLEANUP remove cron/db cache creator file: '.$fl);
|
|
unlink($cron_file);
|
|
}
|
|
}
|
|
foreach ($others as $fl) {
|
|
$ps = explode(',',$fl);
|
|
if (count($ps) === 2 && $ps[1] === 'always') {
|
|
$id = $ps[0];
|
|
$contains = false;
|
|
foreach (scandir($crondb_dir) as $f) {
|
|
if (in_array($f, ['.','..']))
|
|
continue;
|
|
if (strpos($f, ','.$id.',') !== false) {
|
|
$contains = true;
|
|
break;
|
|
}
|
|
}
|
|
if (!$contains) {
|
|
logi('CACHE-CLEANUP remove unused "always" cache: '.$fl);
|
|
unlink($cache_dir.'/'.$fl);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
run__cronjobs_cache_cleanup();
|
|
//
|
|
///////////////////////////////
|
|
|
|
|
|
//////////////////////////////////////////
|
|
// CRONJOBS for creating jobs from filters
|
|
//
|
|
function run__cronjobs_filter_job($software, $instance, $filter, $action) {
|
|
$_GET = [
|
|
'filter_id' => $filter['id'],
|
|
'instance' => $instance
|
|
];
|
|
logi('Processing filter: '.serialize($_GET));
|
|
$users = mod_php('api/v1/database/'.$software.'/accounts/search');
|
|
if (gettype($users) !== 'array' || isset($users['error'])) {
|
|
loge('Unexpected value for users: '.strval($users));
|
|
return false;
|
|
}
|
|
if (!isset($users['data'])) {
|
|
loge('Unexpected value for users: '.strval($users));
|
|
return false;
|
|
}
|
|
foreach ($users['data'] as $user) {
|
|
$jobname = $action['action']['name'].'_'.$user['id'];
|
|
$jobmod = 'api/v1/http/'.$software.'/accounts/'.$action['action']['name'];
|
|
$report = '[automatic_report] User has been reported because it matches filter "'.$filter['preset_name'].'"';
|
|
$explain = $report;
|
|
if (isset($action['action']['explain']))
|
|
$explain = $action['action']['explain'];
|
|
$args = base64_encode(json_encode([
|
|
'_get' => [
|
|
'id' => $user['id'],
|
|
'instance' => $instance,
|
|
],
|
|
'_post' => [
|
|
'report' => $report,
|
|
'explain' => $explain,
|
|
],
|
|
]));
|
|
$_POST = [
|
|
'name' => $jobname,
|
|
'module' => $jobmod,
|
|
'args' => $args,
|
|
];
|
|
$result = mod_php('api/v1/cron/job/put');
|
|
if (isset($result['ok']))
|
|
logi($result['ok']);
|
|
else if (isset($result['error']))
|
|
loge($result['error']);
|
|
}
|
|
|
|
touch($GLOBALS['appconf']['data_dir'].'/filter_actions/users,'.$instance.','.$action['id']);
|
|
return true;
|
|
}
|
|
function run__cronjobs_filter_jobs() {
|
|
$_GET = ['type' => 'users'];
|
|
$filters = mod_php('api/v1/config/filters/get');
|
|
$config = mod_php('api/v1/config/get');
|
|
$filter_get = function($filters, $id) {
|
|
foreach ($filters as $f)
|
|
if ($f['id'] === $id)
|
|
return $f;
|
|
return null;
|
|
};
|
|
foreach ($GLOBALS['supported_ap_software'] as $software) {
|
|
foreach ($config['hosts'][$software] as $hostcfg) {
|
|
$_GET['instance'] = $hostcfg['instance'];
|
|
$actions = mod_php('api/v1/config/filters/actions/get');
|
|
if ($actions === null) continue;
|
|
foreach ($actions as $action) {
|
|
$filter = $filter_get($filters, $action['id']);
|
|
if ($filter === null) continue;
|
|
$ts_diff = time() - $action['filemtime'];
|
|
if ($ts_diff >= $action['action']['interval'])
|
|
run__cronjobs_filter_job($software,
|
|
$hostcfg['instance'], $filter, $action);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
run__cronjobs_filter_jobs();
|
|
//
|
|
//////////////////////////////////////////
|
|
|
|
|
|
///////////////////////////////////////
|
|
// CRONJOBS for running the actual jobs
|
|
//
|
|
function run_cronjobs() {
|
|
$max = 1000;
|
|
if (isset($GLOBALS['appconf']['cron__max_jobs']))
|
|
$max = intval($GLOBALS['appconf']['cron__max_jobs']);
|
|
if (getenv('MAX_JOBS') !== false)
|
|
$max = intval(getenv('MAX_JOBS'));
|
|
$_GET = ['max' => $max];
|
|
$jobs = mod_php('api/v1/cron/jobs');
|
|
foreach ($jobs as $job) {
|
|
$_GET = ['id' => $job];
|
|
$job_data = mod_php('api/v1/cron/job/get');
|
|
if (isset($job_data['args']['_get']))
|
|
$_GET = $job_data['args']['_get'];
|
|
if (isset($job_data['args']['_post']))
|
|
$_POST = $job_data['args']['_post'];
|
|
logi('Running job with data: '.serialize($job_data));
|
|
$r = mod_php($job_data['module']);
|
|
if ($r === 'does_not_exist') {
|
|
loge('Could not find module (mod.php file) for: '.$job_data['module']);
|
|
continue;
|
|
}
|
|
$_GET = ['id' => $job];
|
|
$result = mod_php('api/v1/cron/job/del');
|
|
if (isset($result['ok']))
|
|
logi($result['ok']);
|
|
else if (isset($result['error']))
|
|
loge($result['error']);
|
|
}
|
|
}
|
|
run_cronjobs();
|
|
//
|
|
///////////////////////////////////////
|
|
|
|
|
|
$ms_total = time() - $time_start;
|
|
logi("Cron has finished in {$ms_total} seconds");
|
|
|
|
end_cronjobs();
|