File: D:/HostingSpaces/PvdBoogaard/indoorski.nl/backup/oude-site/marketing/admin/functions/schedule.php
<?php
/**
* This file has the sending page in it. This only handles sending and scheduling of newsletters.
*
* @version $Id: schedule.php,v 1.42 2008/01/09 23:19:06 chris Exp $
* @author Chris <chris@interspire.com>
*
* @package SendStudio
* @subpackage SendStudio_Functions
*/
/**
* Include the base sendstudio functions.
*/
require_once(dirname(__FILE__) . '/sendstudio_functions.php');
/**
* Class for management of sending newsletters.
*
* @package SendStudio
* @subpackage SendStudio_Functions
*/
class Schedule extends SendStudio_Functions
{
/**
* Constructor
* Loads the schedule, newsletters and send language files.
*
* @see LoadLanguageFile
*
* @return Void Doesn't return anything.
*/
function Schedule()
{
$this->LoadLanguageFile();
$this->LoadLanguageFile('Newsletters');
$this->LoadLanguageFile('Send');
}
/**
* Process
* This handles working out what stage you are up to and so on with workflow.
* Handles editing of schedules, pausing, resuming and deleting of schedules.
* Deleting a scheduled event (especially) needs to update statistics if there are any emails left over in the queue.
*
* @see GetUser
* @see User_API::HasAccess
* @see SENDSTUDIO_CRON_ENABLED
* @see GetApi
* @see Jobs_API::PauseJob
* @see Jobs_API::ResumeJob
* @see Jobs_API::LoadJob
* @see ManageSchedules
* @see CheckJob
* @see AdjustTime
*/
function Process()
{
$action = (isset($_GET['Action'])) ? strtolower($_GET['Action']) : null;
$user = &GetUser();
$access = $user->HasAccess('Newsletters', 'Send');
$popup = (in_array($action, $this->PopupWindows)) ? true : false;
$this->PrintHeader($popup);
if (!$access) {
$this->DenyAccess();
return;
}
if (!SENDSTUDIO_CRON_ENABLED) {
$GLOBALS['Error'] = GetLang('CronNotEnabled');
$this->ParseTemplate('ErrorMsg');
$this->PrintFooter();
return;
}
if ($action == 'processpaging') {
$this->SetPerPage($_GET['PerPageDisplay']);
$action = '';
}
$jobapi = $this->GetApi('Jobs');
$approve_job = IEM::sessionGet('ApproveJob');
if ($approve_job) {
if (isset($_GET['A'])) {
$jobapi->ApproveJob($approve_job, $user->Get('userid'));
$GLOBALS['Message'] = $this->PrintSuccess('JobScheduledOK');
IEM::sessionRemove('ApproveJob');
}
}
$jobid = 0;
if (isset($_GET['job'])) {
$jobid = (int)$_GET['job'];
}
switch ($action) {
/**
* These methods are all called the same thing:
* 'ActionJob'
* The 'action' has an upper-case first letter
* then 'Job' has the same.
* They also all just take the jobid as the argument.
*/
case 'approve':
case 'edit':
case 'pause':
case 'resend':
case 'resume':
case 'update':
if (!$this->CanAccessJobs($jobid)) {
$this->DenyAccess();
return false;
}
$method = ucwords($action) . 'Job';
call_user_func(array($this, $method), $jobid);
break;
case 'delete':
$jobids = array();
if (isset($_POST['jobs'])) {
$jobids = $_POST['jobs'];
} else {
$jobids[] = $jobid;
}
if (!$this->CanAccessJobs($jobids)) {
$this->DenyAccess();
return false;
}
$this->DeleteJobs($jobids);
break;
default:
$this->ManageSchedules();
}
$this->PrintFooter($popup);
}
/**
* ManageSchedules
* Prints a list of scheduled events (only newsletters at this stage but could be expanded).
* This allows you to edit, delete, pause and resume events.
*
* @see GetUser
* @see GetApi
* @see GetPerPage
* @see GetSortDetails
* @see User_API::GetLists
* @see User_API::HasAccess
* @see Jobs_API::GetJobList
* @see SetupPaging
* @see Jobs_API::GetJobStatus
* @see PrintDate
*/
function ManageSchedules()
{
$user = &GetUser();
$jobsApi = $this->GetApi('Jobs');
$settingsApi = $this->GetApi('Settings');
$cron_check = $settingsApi->CheckCron();
$cron_run1 = $settingsApi->Get('cronrun1');
$cron_run2 = $settingsApi->Get('cronrun2');
if ($cron_run1 > 0 && $cron_run2 > 0) {
$schedule = $settingsApi->Get('Schedule');
$send_schedule = $schedule['send'];
$cron_diff = SENDSTUDIO_CRON_SEND * 60;
$next_run = $send_schedule['lastrun'] + ($cron_diff);
$now = time();
$time_to_wait = $next_run - $now;
$update_cron_time = 'true';
} else {
$time_to_wait = GetLang('Unknown');
$cron_diff = 0;
$next_run = 0;
$update_cron_time = 'false';
}
$this->DisplayCronWarning(false);
if ($update_cron_time && $cron_diff > 0) {
while ($time_to_wait < 0) {
$time_to_wait += $cron_diff;
}
}
$GLOBALS['UpdateCronTime'] = $update_cron_time;
$GLOBALS['CronTimeLeft'] = $time_to_wait;
$GLOBALS['CronTimeDifference'] = $cron_diff;
$perpage = $this->GetPerPage();
$DisplayPage = $this->GetCurrentPage();
$start = 0;
if ($perpage != 'all') {
$start = ($DisplayPage - 1) * $perpage;
}
$lists = $user->GetLists();
$listids = array_keys($lists);
if ($user->HasAccess('Newsletters', 'Send')) {
$GLOBALS['Newsletters_SendButton'] = $this->ParseTemplate('Newsletter_Send_Button', true, false);
}
$include_unapproved = false;
if ($user->Admin()) {
$include_unapproved = true;
$numJobs = $jobsApi->GetJobList('send', 'newsletter', $listids, true, 0, 0, $include_unapproved, false);
} else {
$numJobs = $jobsApi->GetJobList('send', 'newsletter', $listids, true, 0, 0, $include_unapproved, false, $user->userid);
}
if ($numJobs < 1) {
if ($user->HasAccess('Newsletters', 'Send')) {
$msg = $this->PrintSuccess('Schedule_Empty', GetLang('NoSchedules_HasAccess'));
} else {
$msg = $this->PrintSuccess('Schedule_Empty', '');
}
if (!isset($GLOBALS['Message'])) {
$GLOBALS['Message'] = '';
}
$GLOBALS['Message'] .= $msg;
echo $this->ParseTemplate('Schedule_Manage_Row_Empty', true, false);
return;
}
if ($user->Admin()) {
$jobs = $jobsApi->GetJobList('send', 'newsletter', $listids, false, $start, $perpage, $include_unapproved, false);
} else {
$jobs = $jobsApi->GetJobList('send', 'newsletter', $listids, false, $start, $perpage, $include_unapproved, false, $user->userid);
}
$this->SetupPaging($numJobs, $DisplayPage, $perpage);
$GLOBALS['FormAction'] = 'Action=ProcessPaging';
$paging = $this->ParseTemplate('Paging', true, false);
$manage_row = '';
$timenow = AdjustTime();
$rid = 0;
foreach ($jobs as $p => $details) {
$rid++;
$GLOBALS['JobID'] = (int)$details['jobid'];
$GLOBALS['Status'] = $jobsApi->GetJobStatus($details['jobstatus']);
$GLOBALS['JobTime'] = $this->PrintTime($details['jobtime'], true);
$GLOBALS['ListName'] = htmlspecialchars($details['listname'], ENT_QUOTES, SENDSTUDIO_CHARSET);
$GLOBALS['NewsletterName'] = htmlspecialchars($details['name'], ENT_QUOTES, SENDSTUDIO_CHARSET);
$GLOBALS['NewsletterSubject'] = '';
if ($details['subject'] !== null) {
$GLOBALS['NewsletterSubject'] = ' - ' . htmlspecialchars($details['subject'], ENT_QUOTES, SENDSTUDIO_CHARSET);
}
$GLOBALS['NewsletterType'] = GetLang('Schedule_NewsletterType_Newsletter');
if ($details['jobdescription'] !== null) {
$GLOBALS['NewsletterType'] = htmlspecialchars($details['jobdescription'], ENT_QUOTES, SENDSTUDIO_CHARSET);
}
$action = sprintf(GetLang('Schedule_ViewNewsletter'), 'index.php?Page=Newsletters&Action=View&id=' . (int)$details['newsletterid']);
if ($details['jobtype'] != 'send') {
$action = '';
}
$GLOBALS['RowID'] = $rid;
$GLOBALS['RefreshLink'] = $GLOBALS['AlreadySent'] = '';
/**
* If a job is not 'p'aused or 'c'omplete, or 'i'n progress,
* show the "countdown" for when it will send.
*
* This allows addons to have their own "status" and still show a countdown for when it will send.
*/
if (!in_array($details['jobstatus'], array ('p', 'c', 'i'))) {
if ($details['jobstatus'] == 'w' && ($user->Admin() && $details['approved'] <= 0)) {
$GLOBALS['TipName'] = $this->GetRandomId();
$GLOBALS['ScheduleTip'] = GetLang('WaitingForApproval_Description');
$need_approval_tip = $this->ParseTemplate('Schedule_Needs_Approval_Tip', true, false);
$GLOBALS['Status'] = $need_approval_tip;
$action .= $this->ParseTemplate('Schedule_Manage_Row_ApproveLink', true, false);
$action .= $this->ParseTemplate('Schedule_Manage_Row_DeleteLink', true, false);
$GLOBALS['Action'] = $action;
$manage_row .= $this->ParseTemplate('Schedule_Manage_Row', true, false);
continue;
}
if ($next_run > 0) {
$details['jobtime'] = FixBrokenGMTTime($details['jobtime']);
$send_in_time_difference = $details['jobtime'] - time();
// if we're below 0, that means we should send next time cron runs.
if ($send_in_time_difference < 0) {
$send_in_time_difference = $time_to_wait;
}
if ($next_run > 0 && $details['jobtime'] <= $next_run) {
$send_in_time_difference = $next_run - time();
}
while ($send_in_time_difference < 0) {
$send_in_time_difference += $cron_diff;
}
if ($send_in_time_difference > 0) {
$have_refreshed = (isset($_GET['R'])) ? 1 : 0;
$GLOBALS['RefreshLink'] = "<script>UpdateMyTimer('" . $GLOBALS['JobID'] . "_" . $rid . "', " . (int)$send_in_time_difference . ", " . $have_refreshed . ");</script>";
} else {
if ($details['jobstatus'] == 'w') {
$GLOBALS['Status'] = GetLang('WaitingToSend');
}
}
} else {
if ($details['jobstatus'] == 'w') {
$GLOBALS['Status'] = GetLang('WaitingToSend');
}
}
}
if ($details['jobstatus'] == 'i') {
if ($user->Admin() && $details['approved'] <= 0) {
$GLOBALS['TipName'] = $this->GetRandomId();
$GLOBALS['ScheduleTip'] = GetLang('WaitingForApproval_Description');
$need_approval_tip = $this->ParseTemplate('Schedule_Needs_Approval_Tip', true, false);
$GLOBALS['Status'] = $need_approval_tip;
$action .= $this->ParseTemplate('Schedule_Manage_Row_ApproveLink', true, false);
$action .= $this->ParseTemplate('Schedule_Manage_Row_DeleteLink', true, false);
$GLOBALS['Action'] = $action;
$manage_row .= $this->ParseTemplate('Schedule_Manage_Row', true, false);
continue;
}
$queueinfo = $jobsApi->GetJobQueueSize($details['jobid']);
if (!empty($queueinfo)) {
$GLOBALS['AlreadySent'] = sprintf(GetLang('AlreadySentTo'), $this->FormatNumber($queueinfo['totalsent']), $this->FormatNumber($queueinfo['sendsize']));
}
$GLOBALS['RefreshDisplayPage'] = $DisplayPage;
$action .= $this->ParseTemplate('Schedule_Manage_Row_RefreshLink', true, false);
}
// if the job is paused, we can resume it.
if ($details['jobstatus'] == 'p') {
$action .= $this->ParseTemplate('Schedule_Manage_Row_ResumeLink', true, false);
}
// if the job is in progress we can pause it.
// or if it's in progress.
// that will allow us to delay it without losing all of the info....
if ($details['jobstatus'] == 'i' || $details['jobstatus'] == 'w') {
$action .= $this->ParseTemplate('Schedule_Manage_Row_PauseLink', true, false);
}
// if it's not in progress, we can edit or delete the scheduled event.
// but only if it has not started yet (the queueid will be > 0 for started events).
if ($details['jobstatus'] != 'i') {
if ($details['queueid'] == 0 && $details['jobstatus'] != 'c') {
$action .= $this->ParseTemplate('Schedule_Manage_Row_EditLink', true, false);
}
$action .= $this->ParseTemplate('Schedule_Manage_Row_DeleteLink', true, false);
}
$GLOBALS['Action'] = $action;
$manage_row .= $this->ParseTemplate('Schedule_Manage_Row', true, false);
}
$template = $this->ParseTemplate('Schedule_Manage', true, false);
$template = str_replace('%%TPL_Schedule_Manage_Row%%', $manage_row, $template);
$template = str_replace('%%TPL_Paging%%', $paging, $template);
$template = str_replace('%%TPL_Paging_Bottom%%', $GLOBALS['PagingBottom'], $template);
echo $template;
}
/**
* EditJob
* Allows you to edit a job's send time and view other details (which list(s), newsletter).
*
* @param Int $jobid JobId to edit.
*
* @see CheckJob
* @see GetApi
* @see Jobs_API::Load
* @see GetUser
* @see Newsletters_API::Load
* @see Lists_API::Load
* @see CreateDateTimeBox
*
* @return Void Prints out the form for editing, doesn't return anything.
*
* @uses EventData_IEM_SCHEDULE_EDITJOB
*/
function EditJob($jobid=0)
{
$check = $this->CheckJob($jobid);
if (!$check) {
return false;
}
$api = $this->GetApi('Jobs');
$job = $api->LoadJob($jobid);
/**
* Trigger event
*/
$tempEventData = new EventData_IEM_SCHEDULE_EDITJOB();
$tempEventData->jobrecord = &$job;
if (!$tempEventData->trigger()) {
return;
}
unset($tempEventData);
/**
* -----
*/
$user = &GetUser();
$user_lists = $user->GetLists();
$newslettername = '';
$newsletterApi = $this->GetApi('Newsletters');
$newsletterApi->Load($job['jobdetails']['Newsletter']);
$newslettername = $newsletterApi->Get('name');
$GLOBALS['JobID'] = $jobid;
$listdetails = array();
foreach ($job['jobdetails']['Lists'] as $l => $listid) {
$listdetails[] = htmlspecialchars($user_lists[$listid]['name'], ENT_QUOTES, SENDSTUDIO_CHARSET);
}
$listnames = implode(', ', $listdetails);
$GLOBALS['NewsletterID'] = $newsletterApi->Get('newsletterid');
$GLOBALS['Send_NewsletterName'] = sprintf(GetLang('Send_NewsletterName'), htmlspecialchars($newslettername, ENT_QUOTES, SENDSTUDIO_CHARSET));
$GLOBALS['Send_SubscriberList'] = sprintf(GetLang('Send_SubscriberList'), $listnames);
$GLOBALS['SendTimeBox'] = $this->CreateDateTimeBox($job['jobtime']);
$this->ParseTemplate('Schedule_Edit');
}
/**
* CheckJob
* Makes sure the job you're trying to access is valid. It also makes sure it's not in progress.
*
* @param Int $jobid The job to check.
*
* @see ManageSchedules
* @see GetApi
* @see Jobs_API::LoadJob
*
* @return Boolean Returns false if there is a problem with the job (it's not valid or we can't load it). It also returns false if the job is in progress - it will print a message out and then print the schedule list.
*/
function CheckJob($jobid=0)
{
$jobid = (int)$jobid;
if ($jobid <= 0) {
$GLOBALS['Error'] = GetLang('JobDoesntExist');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
$this->ManageSchedules();
return false;
}
$api = $this->GetApi('Jobs');
$job = $api->LoadJob($jobid);
if (empty($job)) {
$GLOBALS['Error'] = GetLang('JobDoesntExist');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
$this->ManageSchedules();
return false;
}
if ($job['jobstatus'] == 'i') {
$GLOBALS['Error'] = GetLang('UnableToEditJob_InProgress');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
$this->ManageSchedules();
return false;
}
return true;
}
/**
* PauseJob
* Handles the "pause job" process.
* An addon can override this functionality to do it's own work.
* If it does, it must call
*
* InterspireEventData::preventDefault
*
* to stop the default action from happening.
*
* The job is loaded (based on the id) before it is passed to the InterspireEvent::trigger method.
*
* Once either the addon does it's processing work, or the default action happens, the user is taken back to the "ManageSchedules" page.
*
* @param Int $jobid The job we are going to pause.
*
* @uses Jobs_API::PauseJob
* @uses InterspireEvent::trigger
* @see InterspireEventData::preventDefault
* @see ManageSchedules
*
* @uses EventData_IEM_SCHEDULE_PAUSEJOB
*/
function PauseJob($jobid=0)
{
$jobapi = $this->GetApi('Jobs');
$jobinfo = $jobapi->LoadJob($jobid);
/**
* Trigger event
*/
$tempEventData = new EventData_IEM_SCHEDULE_PAUSEJOB();
$tempEventData->jobrecord = &$jobinfo;
if (!$tempEventData->trigger()) {
$this->ManageSchedules();
return;
}
unset($tempEventData);
/**
* -----
*/
$result = $jobapi->PauseJob($jobid);
if ($result) {
$GLOBALS['Message'] = $this->PrintSuccess('JobPausedSuccess');
} else {
$GLOBALS['Error'] = GetLang('JobPausedFail');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
}
$this->ManageSchedules();
}
/**
* ResumeJob
* Handles the "resume job" process.
* An addon can override this functionality to do it's own work.
* If it does, it must call
*
* InterspireEventData::preventDefault
*
* to stop the default action from happening.
*
* The job is loaded (based on the id) before it is passed to the InterspireEvent::trigger method.
*
* Once either the addon does it's processing work, or the default action happens, the user is taken back to the "ManageSchedules" page.
*
* @param Int $jobid The job we are going to resume.
*
* @uses Jobs_API::ResumeJob()
* @see InterspireEventData::preventDefault
* @see ManageSchedules
*
* @uses EventData_IEM_SCHEDULE_RESUMEJOB
*/
function ResumeJob($jobid=0)
{
$jobapi = $this->GetApi('Jobs');
$jobinfo = $jobapi->LoadJob($jobid);
/**
* Trigger event
*/
$tempEventData = new EventData_IEM_SCHEDULE_RESUMEJOB();
$tempEventData->jobrecord = &$jobinfo;
if (!$tempEventData->trigger()) {
$this->ManageSchedules();
return;
}
unset($tempEventData);
/**
* -----
*/
$result = $jobapi->ResumeJob($jobid);
if ($result) {
$GLOBALS['Message'] = $this->PrintSuccess('JobResumedSuccess');
} else {
$GLOBALS['Error'] = GetLang('JobResumedFail');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
}
$this->ManageSchedules();
}
/**
* ApproveJob
* Approve job allows an administrator to 'approve' or 'authorise' a send
* even if it takes a user over their per-month of email quota.
* It checks the user doing the approving is an admin user.
* If they are not, they cannot approve a send.
*
* An addon can override this functionality if need be.
* If it does, it must call
*
* InterspireEventData::preventDefault
*
* to stop the default action from happening.
*
* @param Int $jobid The job that needs approving.
*
* @uses Jobs_API::ApproveJob()
* @uses ManageSchedules
* @uses InterspireEvent::trigger
* @see InterspireEventData::preventDefault
*
* @return Void Doesn't return anything. Once the job is approved or checked, the user is shown the "Manage Schedules" page.
*
* @uses EventData_IEM_SCHEDULE_APPROVEJOB
*/
function ApproveJob($jobid=0)
{
$jobapi = $this->GetApi('Jobs');
$jobinfo = $jobapi->LoadJob($jobid);
/**
* Trigger event
*/
$tempEventData = new EventData_IEM_SCHEDULE_APPROVEJOB();
$tempEventData->jobrecord = &$jobinfo;
if (!$tempEventData->trigger()) {
$this->ManageSchedules();
return;
}
unset($tempEventData);
/**
* -----
*/
$user = &GetUser();
if (!$user->Admin()) {
$GLOBALS['Error'] = GetLang('JobApprovedFail_NotAdmin');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
} else {
$result = $jobapi->ApproveJob($jobid, $user->Get('userid'), $user->Get('userid'));
if ($result) {
$GLOBALS['Message'] = $this->PrintSuccess('JobApprovedSuccess');
} else {
$GLOBALS['Error'] = GetLang('JobApprovedFail');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
}
}
$this->ManageSchedules();
}
/**
* DeleteJobs
* Takes an array of job id's that are going to be deleted, and tries to delete them one by one.
*
* An addon/extension handles it's own work if necessary
* and if it does, it removes the 'jobid' from the jobids array that was passed in
* so the default action won't be performed (again) on the job.
*
* @param Array $jobids The job id's that are going to be deleted.
*
* @uses Jobs_API::ApproveJob
* @uses ManageSchedules
* @uses InterspireEvent::trigger
* @see InterspireEventData::preventDefault
*
* @return Void Doesn't return anything. Once the job is approved or checked, the user is shown the "Manage Schedules" page.
*
* @uses EventData_IEM_SCHEDULE_DELETEJOBS
*/
function DeleteJobs($jobids=array())
{
$jobapi = $this->GetApi('Jobs');
$jobids = $jobapi->CheckIntVars($jobids);
// in case the schedule is for multiple lists, we only want the unique job ids.
$jobids = array_unique($jobids);
$msg = '';
$success = 0;
$fail = 0;
/**
* Trigger event
*/
$tempEventData = new EventData_IEM_SCHEDULE_DELETEJOBS();
$tempEventData->jobids = &$jobids;
$tempEventData->Message = &$msg;
$tempEventData->success = &$success;
$tempEventData->failure = &$fail;
$tempEventData->trigger();
unset($tempEventData);
/**
* -----
*/
$user = &GetUser();
$stats_api = $this->GetApi('Stats');
foreach ($jobids as $p => $jobid) {
$in_progress = $jobapi->JobStarted($jobid);
if ($in_progress) {
$fail++;
continue;
}
$jobinfo = $jobapi->LoadJob($jobid);
if (empty($jobinfo)) {
continue;
}
$statid = $jobapi->LoadStats($jobid);
/**
* If a send is started (ie it has stats),
* but is not completed,
* We need to mark it as complete.
*
* This also credits a user back if they have any limits in place.
*
* This needs to happen before we delete the 'job' from the database
* as deleting the job cleans up the queues/unsent items.
*/
if ($statid > 0 && $jobinfo['jobstatus'] != 'c') {
$stats_api->MarkNewsletterFinished($statid, $jobinfo['jobdetails']['SendSize'], false);
// Credits needs to be returned too whenever the job is canceled AFTER it has been scheduled, but before it was sent
} elseif ($jobinfo['jobstatus'] != 'c') {
$stats_api->RefundFixedCredit($jobid);
}
$result = $jobapi->Delete($jobid);
if ($result) {
$success++;
} else {
$fail++;
}
}
if ($success > 0) {
if ($success == 1) {
$msg .= $this->PrintSuccess('JobDeleteSuccess');
} else {
$msg .= $this->PrintSuccess('JobsDeleteSuccess', $success);
}
}
$GLOBALS['Message'] = $msg;
$this->ManageSchedules();
}
/**
* ResendJob
* Sets up a job ready for "re-sending" if any emails failed to be sent the first time.
* An addon can override this functionality if need be.
* If it does, it must call
*
* InterspireEventData::preventDefault
*
* to stop the default action from happening.
*
* @param Int $jobid The job that needs resending.
*
* @uses Jobs_API::ResendJob()
* @uses ManageSchedules
* @see InterspireEventData::preventDefault()
*
* @return Void Doesn't return anything. Once the job is set up for re-sending, the user is shown the "Manage Schedules" page.
*
* @uses EventData_IEM_SCHEDULE_RESENDJOB
*/
function ResendJob($jobid=0)
{
$jobapi = $this->GetApi('Jobs');
$jobinfo = $jobapi->LoadJob($jobid);
/**
* Trigger Event
*/
$tempEventData = new EventData_IEM_SCHEDULE_RESENDJOB();
$tempEventData->jobrecord = &$jobinfo;
if (!$tempEventData->trigger()) {
$this->ManageSchedules();
return;
}
unset($tempEventData);
/**
* -----
*/
$resend_setup = $jobapi->ResendJob($jobid);
if ($resend_setup) {
$GLOBALS['Message'] = $this->PrintSuccess('JobResendSuccess');
} else {
$GLOBALS['Error'] = GetLang('JobResendFail');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
}
$this->ManageSchedules();
}
/**
* UpdateJob
* Updates when a job/scheduled event is set to send.
*
* A scheduled event by default cannot be changed if:
* - it has already sent some emails (it's too hard to re-calculate/re-check/re-allocate per-month statistics)
* - you are trying to send "in the past"
*
* An addon can override this functionality if need be.
* If it does, it must call
*
* InterspireEventData::preventDefault
*
* to stop the default action from happening.
*
* @param Int $jobid The job that needs updating.
*
* @uses CheckJob
* @uses Jobs_API::UpdateTime
* @uses ManageSchedules
* @uses InterspireEvent::trigger
* @see InterspireEventData::preventDefault
*
* @return Void Doesn't return anything. Checks that it's ok to re-schedule a send. If it is ok, it changes the scheduled time. If it's not, the user gets a message.
*
* @uses EventData_IEM_SCHEDULE_UPDATEJOB
*/
function UpdateJob($jobid=0)
{
$check = $this->CheckJob($jobid);
if (!$check) {
return false;
}
$jobapi = $this->GetApi('Jobs');
$jobinfo = $jobapi->LoadJob($jobid);
/**
* Trigger Event
*/
$tempEventData = new EventData_IEM_SCHEDULE_UPDATEJOB();
$tempEventData->jobrecord = &$jobinfo;
if (!$tempEventData->trigger()) {
$this->ManageSchedules();
return;
}
unset($tempEventData);
/**
* -----
*/
$user = &GetUser();
$sendtime = $_POST['sendtime'];
$hr = $_POST['sendtime_hours'];
$minute = $_POST['sendtime_minutes'];
$ampm = null;
if (isset($_POST['sendtime_ampm'])) {
$ampm = strtolower($_POST['sendtime_ampm']);
}
if ($ampm == 'pm' && $hr < 12) {
$hr += 12;
}
if ($ampm == 'am' && $hr == 12) {
$hr = 0;
}
if ($hr > 23) {
$hr = $hr % 24;
}
$scheduletime = AdjustTime(array($hr, $minute, 0, (int)$_POST['datetime']['month'], (int)$_POST['datetime']['day'], (int)$_POST['datetime']['year']), true);
// see if they haev changed the send time. If they have, then we need to check stats again to make sure it's ok to do that.
if ($jobinfo['jobtime'] != $scheduletime) {
$now = $jobapi->GetServerTime();
// you are trying to schedule before now (well, 5 minutes ago), then don't allow it.
if ($scheduletime < ($now - (5 * 60))) {
$GLOBALS['Error'] = GetLang('Send_Step4_CannotSendInPast');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
$this->EditJob($jobid);
return;
}
if ($jobinfo['queueid'] > 0) {
$GLOBALS['Error'] = GetLang('CannotChangeAScheduleOnceItHasStarted');
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
$this->EditJob($jobid);
return;
}
$schedulemonth = AdjustTime(array(0, 0, 1, date('m', $scheduletime), 1, date('Y', $scheduletime)), true);
$original_schedulemonth = AdjustTime(array(0, 0, 1, date('m', $jobinfo['jobtime']), 1, date('Y', $jobinfo['jobtime'])), true);
if ($schedulemonth != $original_schedulemonth) {
$statsapi = $this->GetApi('Stats');
/**
* We need to check user stats for when this is scheduled to send.
*/
$check_stats = $statsapi->CheckUserStats($user, $jobinfo['jobdetails']['SendSize'], $scheduletime, true);
list($ok_to_send, $not_ok_to_send_reason) = $check_stats;
if (!$ok_to_send) {
$GLOBALS['Error'] = GetLang($not_ok_to_send_reason);
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
$this->EditJob($jobid);
return;
}
$new_size = $jobinfo['jobdetails']['SendSize'];
$statsapi->DeleteUserStats($user->userid, $jobid);
$statsapi->RecordUserStats($user->userid, $jobid, $new_size, $scheduletime);
}
}
$result = $jobapi->UpdateTime($jobid, $scheduletime);
if ($result) {
$GLOBALS['Message'] = $this->PrintSuccess('JobScheduled', $this->PrintTime($scheduletime));
} else {
$GLOBALS['Error'] = sprintf(GetLang('JobNotScheduled'), $this->PrintTime($scheduletime));
$GLOBALS['Message'] = $this->ParseTemplate('ErrorMsg', true, false);
}
$this->ManageSchedules();
}
/**
* CanAccessJobs
*
* Check whether or not current user is able to access the job.
* The checking that is currently being done is NOT optimized for query performance,
* as it WILL query the database multiple times for each job ID (and it does it without caching anything).
*
* @param Mixed $jobids Job IDs to be checked
* @return Boolean Returns TRUE if user has permission, FALSE otherwise
*/
function CanAccessJobs($jobids)
{
$user = &GetUser();
if ($user->Admin()) {
return true;
}
if (!is_array($jobids)) {
$jobids = array($jobids);
}
$jobids = array_map('intval', $jobids);
$jobids = array_unique($jobids);
if (empty($jobids)) {
return false;
}
$jobapi = $this->GetApi('Jobs');
foreach ($jobids as $jobid) {
$jobrecords = $jobapi->LoadJob($jobid);
if ($jobrecords['ownerid'] != $user->userid) {
return false;
}
}
return true;
}
}