Last active
March 1, 2020 23:38
-
-
Save peterwilsoncc/b83a23abb0c75a4cdf9301da12f245a6 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <?php | |
| namespace PWCC\NightlyCronSchedule; | |
| use DateTime; | |
| use DateTimeZone; | |
| use HM\Cavalcade\Plugin\Job; | |
| /** | |
| * Register hooks for WordPress. | |
| */ | |
| function bootstrap() { | |
| if ( ! class_exists( 'HM\Cavalcade\Plugin\Job' ) ) { | |
| return; | |
| } | |
| add_filter( 'pre_get_scheduled_event', __NAMESPACE__ . '\\pre_get_scheduled_event', 5, 4 ); | |
| add_filter( 'schedule_event', __NAMESPACE__ . '\\schedule_event' ); | |
| } | |
| function enforced_daily_schedules() { | |
| /** | |
| * Daily cron events to be enforced to run at a | |
| * particular hour. | |
| * | |
| * @param array $daily_events Events scheduled to run daily at particular times. | |
| * The key is the hook name, the value the hour of day. | |
| */ | |
| return apply_filters( | |
| 'pwcc.nightly-cron-scheduled.enforced-daily-schedules', | |
| [ | |
| 'wp_scheduled_delete' => 02, | |
| 'wp_scheduled_auto_draft_delete' => 03, | |
| 'delete_expired_transients' => 04, | |
| ] | |
| ); | |
| } | |
| /** | |
| * When getting Core daily tasks, ensure they are scheduled for night time. | |
| * | |
| * Ensure the following core hooks are scheduled to run within a ten minute window | |
| * of the specified time. | |
| * - wp_scheduled_delete: 2am | |
| * - wp_scheduled_auto_draft_delete: 3am | |
| * - delete_expired_transients: 4am | |
| * | |
| * @param null|bool $pre Value to return instead. Default null to continue adding the event. | |
| * @param stdClass $event { | |
| * An object containing an event's data. | |
| * | |
| * @type string $hook Action hook to execute when the event is run. | |
| * @type int $timestamp Unix timestamp (UTC) for when to next run the event. | |
| * @type string|false $schedule How often the event should subsequently recur. | |
| * @type array $args Array containing each separate argument to pass to the hook's callback function. | |
| * @type int $interval The interval time in seconds for the schedule. Only present for recurring events. | |
| * } | |
| * @return null|bool True if event successfully scheduled. False for failure. | |
| */ | |
| function pre_get_scheduled_event( $pre, $hook, $args, $timestamp ) { | |
| $core_schedules = enforced_daily_schedules(); | |
| if ( ! in_array( $hook, array_keys( $core_schedules ), true ) ) { | |
| return $pre; | |
| } | |
| $jobs = Job::get_jobs_by_query( [ | |
| 'hook' => $hook, | |
| 'timestamp' => $timestamp, | |
| 'args' => $args, | |
| ] ); | |
| if ( is_wp_error( $jobs ) || empty( $jobs ) ) { | |
| return false; | |
| } | |
| $job = $jobs[0]; | |
| $date = new DateTime(); | |
| $date->setTimestamp( $job->nextrun ); | |
| $date->setTimezone( new DateTimeZone( get_option('timezone_string') ) ); | |
| $date->modify( '-15 minutes' ); | |
| $start = (int) $date->format( 'Hi' ); | |
| $date->modify( '+30 minutes' ); | |
| $end = (int) $date->format( 'Hi' ); | |
| if ( | |
| ( $core_schedules[ $hook ] * 100 ) < $start || | |
| ( $core_schedules[ $hook ] * 100 ) > $end | |
| ) { | |
| // Outside window, delete event and return false. | |
| wp_clear_scheduled_hook( $hook ); | |
| return false; | |
| } | |
| /* | |
| * Return $pre and allow Cavalcade to deal with object creation and | |
| * dealing with any compatibility changes required for core. | |
| */ | |
| return $pre; | |
| } | |
| /** | |
| * Ensure core daily tasks are scheduled for night time. | |
| * | |
| * Ensure the following core hooks are scheduled to run at the specified time. | |
| * - wp_scheduled_delete: 2am | |
| * - wp_scheduled_auto_draft_delete: 3am | |
| * - delete_expired_transients: 4am | |
| * | |
| * @param stdClass $event { | |
| * An object containing an event's data. | |
| * | |
| * @type string $hook Action hook to execute when the event is run. | |
| * @type int $timestamp Unix timestamp (UTC) for when to next run the event. | |
| * @type string|false $schedule How often the event should subsequently recur. | |
| * @type array $args Array containing each separate argument to pass to the hook's callback function. | |
| * @type int $interval The interval time in seconds for the schedule. Only present for recurring events. | |
| * } | |
| */ | |
| function schedule_event( $event ) { | |
| $core_schedules = enforced_daily_schedules(); | |
| if ( ! in_array( $event->hook, array_keys( $core_schedules ), true ) ) { | |
| return $event; | |
| } | |
| $date = new DateTime(); | |
| $date->setTimestamp( $event->timestamp ); | |
| $date->setTimezone( new DateTimeZone( get_option('timezone_string') )); | |
| $date->modify( sprintf( 'tomorrow %d hours', $core_schedules[ $event->hook ] ) ); | |
| $date->setTime( $core_schedules[ $event->hook ], 0 ); | |
| $event->timestamp = $date->getTimestamp(); | |
| return $event; | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment