前言:可以先阅读官方文档了解计划任务的自定义开发规则。官方文档
应用场景:对系统各模块的审计数据进行抽取,生成最终的报表,并且实时处理用户编辑数据操作过程中产生的审计数据。
实现思路:
1、编写抽取各模块数据的计划任务脚本;
2、配置计划任务例行,执行一次可处理历史数据;
3、新增最高层after_save钩子,在用户操作编辑数据时,将指定数据处理需求插入计划任务的任务队列,系统队列消耗机制会自动调用队列的数据来处理消耗该任务数据,从而完成新增审计数据的抽取。
关键扩展细节:
①计划任务脚本
//脚本路径:custom/Extension/modules/Schedulers/Ext/ScheduledTasks/AuditReport.php
//实现轮廓
<?php
$job_classes[] = "AuditReport";//定义脚本名称
class AuditReport implements RunnableSchedulerJob
{
public function run($arguments)
{
//TODO:
/*
$arguments即是data的参数
1、通过计划任务例行入库的队列任务数据的arguments为空,这种场景可处理历史审计数据的抽取;
2、通过after_save钩子入库的队列任务数据为指定操作模块记录,这种场景可处理新增审计数据的抽取;
3、在此处逻辑处理需考虑以上两种场景。
*/
return true;
}
public function setJob(SchedulersJob $job)
{
$this->job = $job;
}
public function fillMessage($message)
{
$this->job->message .= "$message\n";
}
}
②定义计划任务名称的中英文标签
//路径:
//custom/Extension/modules/Schedulers/Ext/Language/zh_CN.AuditReport.php
//custom/Extension/modules/Schedulers/Ext/Language/en_us.AuditReport.php
$mod_strings['LBL_AUDITREPORT'] = '审计报表';
③定义逻辑钩子after_save
//路径:custom/Extension/application/Ext/LogicHooks/AuditReportHook.php
if (!isset($hook_array) || !is_array($hook_array)) {
$hook_array = array();
}
if (!isset($hook_array['after_save']) || !is_array($hook_array['after_save'])) {
$hook_array['after_save'] = array();
}
$hook_array['after_save'][] = Array(999, '', 'custom/modules/Schedulers/InsertQueue.php','InsertQueue', 'insert_queue_for_audit');
④after_save逻辑钩子处理类
//路径:custom/modules/Schedulers/InsertQueue.php
<?php
class InsertQueue{
public function insert_queue_for_audit($bean, $event, $arguments){
if(!in_array($bean->module_dir,$audit_modules)) return;
require_once 'include/SugarQueue/SugarJobQueue.php';
$scheduledJob = new SchedulersJob();
//Give it a useful name
$scheduledJob->name = "Syn Audit for {$bean->module_name} {$bean->id}";
$scheduledJob->assigned_user_id = '1';
$scheduledJob->scheduler_id = 'xxx';
$scheduledJob->data = json_encode(array(
'id' => $bean->id,
'module_name' => $bean->module_name)
);
//script
$scheduledJob->target = "class::AuditReport";
//执行时间延迟5分钟,因为auditBean的处理在after_save之后
//$job->execute_time = $GLOBALS['timedate']->nowDb();
$date = $GLOBALS['timedate']->getNow();
$execute_time = $date->add(new DateInterval("PT3M"));
$scheduledJob->execute_time = $execute_time->format("Y-m-d H:i:s");
$queue = new SugarJobQueue();
$queue->submitJob($scheduledJob);
}
}
⑤处理计划任务配置页下拉列表可选值
//路径:modules/Schedulers/Scheduler.php
//方法getJobsList中补充一下处理代码
foreach ($job_classes as $k => $v) {
self::$job_strings['class::' . $v] = $mod_strings['LBL_' . strtoupper($v)];
}