Skip to content

Instantly share code, notes, and snippets.

@chikaibeneme
Last active February 27, 2026 07:31
Show Gist options
  • Select an option

  • Save chikaibeneme/18ff1f47f06005dcda003461e48e92fc to your computer and use it in GitHub Desktop.

Select an option

Save chikaibeneme/18ff1f47f06005dcda003461e48e92fc to your computer and use it in GitHub Desktop.
resync events.php
function tecdev_fallback_sync_event_custom_tables( $event_id, &$reason = '' ) {
global $wpdb;
$event_id = absint( $event_id );
if ( ! $event_id ) {
$reason = 'Fallback: invalid event ID.';
return false;
}
$start_date = (string) get_post_meta( $event_id, '_EventStartDate', true );
$end_date = (string) get_post_meta( $event_id, '_EventEndDate', true );
$start_utc = (string) get_post_meta( $event_id, '_EventStartDateUTC', true );
$end_utc = (string) get_post_meta( $event_id, '_EventEndDateUTC', true );
$timezone = (string) get_post_meta( $event_id, '_EventTimezone', true );
$duration = (int) get_post_meta( $event_id, '_EventDuration', true );
if ( '' === $start_date || '' === $end_date || '' === $start_utc || '' === $end_utc ) {
$reason = 'Fallback: required event date meta is missing.';
return false;
}
if ( '' === $timezone ) {
$timezone = 'UTC';
}
if ( 0 === strpos( $timezone, 'UTC+' ) || 0 === strpos( $timezone, 'UTC-' ) ) {
if ( 'UTC+0' === $timezone || 'UTC-0' === $timezone ) {
$timezone = 'UTC';
}
}
if ( $duration <= 0 ) {
$start_ts = strtotime( $start_utc );
$end_ts = strtotime( $end_utc );
if ( $start_ts && $end_ts && $end_ts > $start_ts ) {
$duration = (int) ( $end_ts - $start_ts );
} else {
$duration = 7200;
}
}
$events_table = $wpdb->prefix . 'tec_events';
$occurrences_table = $wpdb->prefix . 'tec_occurrences';
$events_table_exists = $wpdb->get_var( $wpdb->prepare( 'SHOW TABLES LIKE %s', $events_table ) );
$occ_table_exists = $wpdb->get_var( $wpdb->prepare( 'SHOW TABLES LIKE %s', $occurrences_table ) );
if ( $events_table !== $events_table_exists || $occurrences_table !== $occ_table_exists ) {
$reason = sprintf( 'Fallback: required tables not found for prefix %s.', $wpdb->prefix );
return false;
}
$event_hash = md5( implode( '|', [ $event_id, $start_date, $end_date, $timezone, $start_utc, $end_utc, $duration ] ) );
$existing_event_id = (int) $wpdb->get_var(
$wpdb->prepare( "SELECT event_id FROM {$events_table} WHERE post_id = %d LIMIT 1", $event_id )
);
$event_row = [
'post_id' => $event_id,
'start_date' => $start_date,
'end_date' => $end_date,
'timezone' => $timezone,
'start_date_utc' => $start_utc,
'end_date_utc' => $end_utc,
'duration' => $duration,
'hash' => $event_hash,
];
if ( $existing_event_id > 0 ) {
$updated = $wpdb->update( $events_table, $event_row, [ 'event_id' => $existing_event_id ] );
if ( false === $updated ) {
$reason = 'Fallback: failed to update wp_tec_events row. DB: ' . $wpdb->last_error;
return false;
}
$event_table_id = $existing_event_id;
} else {
$inserted = $wpdb->insert( $events_table, $event_row );
if ( false === $inserted ) {
$reason = 'Fallback: failed to insert wp_tec_events row. DB: ' . $wpdb->last_error;
return false;
}
$event_table_id = (int) $wpdb->insert_id;
}
$wpdb->delete( $occurrences_table, [ 'post_id' => $event_id ], [ '%d' ] );
$occurrence_hash = md5( implode( '|', [ $event_table_id, $event_id, $start_utc, $end_utc ] ) );
$occurrence_row = [
'event_id' => $event_table_id,
'post_id' => $event_id,
'start_date' => $start_date,
'start_date_utc' => $start_utc,
'end_date' => $end_date,
'end_date_utc' => $end_utc,
'duration' => $duration,
'hash' => $occurrence_hash,
];
$occurrence_inserted = $wpdb->insert( $occurrences_table, $occurrence_row );
if ( false === $occurrence_inserted ) {
$reason = 'Fallback: failed to insert wp_tec_occurrences row. DB: ' . $wpdb->last_error;
return false;
}
$reason = 'Fallback SQL sync applied.';
return true;
}
function tecdev_sync_event_custom_tables( $event_id, &$reason = '' ) {
$event_id = absint( $event_id );
if ( ! $event_id ) {
$reason = 'Invalid event ID.';
return false;
}
$post = get_post( $event_id );
if ( ! ( $post instanceof WP_Post ) ) {
$reason = 'Post not found.';
return false;
}
if ( 'tribe_events' !== $post->post_type ) {
$reason = sprintf( 'Post type is %s, expected tribe_events.', $post->post_type );
return false;
}
$start = get_post_meta( $event_id, '_EventStartDate', true );
$end = get_post_meta( $event_id, '_EventEndDate', true );
if ( empty( $start ) || empty( $end ) ) {
$reason = 'Missing _EventStartDate/_EventEndDate meta values.';
return false;
}
if ( ! class_exists( '\\TEC\\Events\\Custom_Tables\\V1\\Updates\\Events' ) || ! function_exists( 'tribe' ) ) {
$reason = 'TEC updater class or tribe() helper is unavailable.';
if ( tecdev_fallback_sync_event_custom_tables( $event_id, $fallback_reason ) ) {
$reason .= ' ' . $fallback_reason;
return true;
}
if ( ! empty( $fallback_reason ) ) {
$reason .= ' ' . $fallback_reason;
}
return false;
}
try {
$updater = tribe( '\\TEC\\Events\\Custom_Tables\\V1\\Updates\\Events' );
if ( ! is_object( $updater ) ) {
$updater = new \TEC\Events\Custom_Tables\V1\Updates\Events();
}
if ( ! is_object( $updater ) || ! method_exists( $updater, 'update' ) ) {
$reason = 'Could not initialize TEC updater service.';
return false;
}
$updated = (bool) $updater->update( $event_id );
if ( method_exists( $updater, 'rebuild_known_range' ) ) {
$updater->rebuild_known_range();
}
if ( ! $updated ) {
$reason = 'TEC updater returned false (event data could not be upserted).';
if ( tecdev_fallback_sync_event_custom_tables( $event_id, $fallback_reason ) ) {
$reason = $reason . ' ' . $fallback_reason;
return true;
}
if ( ! empty( $fallback_reason ) ) {
$reason = $reason . ' ' . $fallback_reason;
}
}
return $updated;
} catch ( Throwable $throwable ) {
$reason = $throwable->getMessage();
if ( tecdev_fallback_sync_event_custom_tables( $event_id, $fallback_reason ) ) {
$reason .= ' ' . $fallback_reason;
return true;
}
if ( ! empty( $fallback_reason ) ) {
$reason .= ' ' . $fallback_reason;
}
return false;
}
}
add_action( 'save_post_tribe_events', function ( $post_id, $post, $update ) {
if ( wp_is_post_revision( $post_id ) || wp_is_post_autosave( $post_id ) ) {
return;
}
tecdev_sync_event_custom_tables( $post_id );
}, 100, 3 );
add_action( 'admin_init', function () {
if ( ! is_admin() || ! current_user_can( 'manage_options' ) ) {
return;
}
if ( empty( $_GET['tecdev_resync_events'] ) ) {
return;
}
$raw_ids = sanitize_text_field( wp_unslash( $_GET['tecdev_resync_events'] ) );
$ids = array_filter( array_map( 'absint', array_map( 'trim', explode( ',', $raw_ids ) ) ) );
if ( empty( $ids ) ) {
return;
}
$synced = 0;
$failed = [];
foreach ( $ids as $id ) {
$reason = '';
if ( tecdev_sync_event_custom_tables( $id, $reason ) ) {
$synced++;
} else {
$failed[ (int) $id ] = $reason ?: 'Unknown failure.';
}
}
if ( ! empty( $failed ) ) {
set_transient( 'tecdev_resync_report_' . get_current_user_id(), $failed, 10 * MINUTE_IN_SECONDS );
}
wp_safe_redirect(
add_query_arg(
[
'post_type' => 'tribe_events',
'tecdev_resync_done' => (int) $synced,
'tecdev_resync_fail' => count( $failed ),
],
admin_url( 'edit.php' )
)
);
exit;
} );
add_action( 'admin_notices', function () {
if ( ! is_admin() || ! current_user_can( 'manage_options' ) ) {
return;
}
if ( ! isset( $_GET['post_type'] ) || 'tribe_events' !== sanitize_key( wp_unslash( $_GET['post_type'] ) ) ) {
return;
}
if ( ! isset( $_GET['tecdev_resync_done'] ) ) {
return;
}
$done = absint( $_GET['tecdev_resync_done'] );
$fails = isset( $_GET['tecdev_resync_fail'] ) ? absint( $_GET['tecdev_resync_fail'] ) : 0;
echo '<div class="notice notice-info"><p>';
echo esc_html( sprintf( 'TEC resync complete. Synced: %d. Failed: %d.', $done, $fails ) );
echo '</p></div>';
$failed = get_transient( 'tecdev_resync_report_' . get_current_user_id() );
if ( ! empty( $failed ) && is_array( $failed ) ) {
echo '<div class="notice notice-warning"><p><strong>TEC resync failures:</strong></p><ul style="margin-left:1.25em; list-style:disc;">';
foreach ( $failed as $id => $reason ) {
echo '<li>' . esc_html( sprintf( 'Event %d: %s', (int) $id, (string) $reason ) ) . '</li>';
}
echo '</ul></div>';
delete_transient( 'tecdev_resync_report_' . get_current_user_id() );
}
} );
add_action( 'init', function () {
add_rewrite_rule( '^event/([^/]+)/([0-9]{4}-[0-9]{2}-[0-9]{2})/([0-9]+)/?$', 'index.php?tribe_events=$matches[1]&eventDate=$matches[2]&eventSequence=$matches[3]', 'top' );
add_rewrite_rule( '^event/([^/]+)/([0-9]{4}-[0-9]{2}-[0-9]{2})/?$', 'index.php?tribe_events=$matches[1]&eventDate=$matches[2]', 'top' );
add_rewrite_rule( '^event/([^/]+)/?$', 'index.php?tribe_events=$matches[1]', 'top' );
}, 20 );
add_action( 'admin_init', function () {
$rewrite_version = '2';
if ( get_option( 'tecdev_single_event_rewrite_version' ) === $rewrite_version ) {
return;
}
add_rewrite_rule( '^event/([^/]+)/([0-9]{4}-[0-9]{2}-[0-9]{2})/([0-9]+)/?$', 'index.php?tribe_events=$matches[1]&eventDate=$matches[2]&eventSequence=$matches[3]', 'top' );
add_rewrite_rule( '^event/([^/]+)/([0-9]{4}-[0-9]{2}-[0-9]{2})/?$', 'index.php?tribe_events=$matches[1]&eventDate=$matches[2]', 'top' );
add_rewrite_rule( '^event/([^/]+)/?$', 'index.php?tribe_events=$matches[1]', 'top' );
flush_rewrite_rules( false );
update_option( 'tecdev_single_event_rewrite_version', $rewrite_version, false );
} );
add_action( 'template_redirect', function () {
if ( ! is_404() ) {
return;
}
$request_uri = isset( $_SERVER['REQUEST_URI'] ) ? wp_unslash( $_SERVER['REQUEST_URI'] ) : '';
$path = (string) wp_parse_url( $request_uri, PHP_URL_PATH );
$path = trim( $path, '/' );
if ( ! preg_match( '#^event/([^/]+)/([0-9]{4}-[0-9]{2}-[0-9]{2})(?:/([0-9]+))?$#', $path, $matches ) ) {
return;
}
$slug = sanitize_title( $matches[1] );
$date_ymd = sanitize_text_field( $matches[2] );
if ( empty( $slug ) || empty( $date_ymd ) ) {
return;
}
$parent = get_page_by_path( $slug, OBJECT, 'tribe_events' );
if ( ! ( $parent instanceof WP_Post ) ) {
return;
}
$occurrence_query = new WP_Query(
[
'post_type' => 'tribe_events',
'post_status' => [ 'publish', 'private' ],
'post_parent' => (int) $parent->ID,
'posts_per_page' => 1,
'fields' => 'ids',
'meta_query' => [
[
'key' => '_EventStartDate',
'value' => $date_ymd,
'compare' => 'LIKE',
],
],
]
);
if ( ! empty( $occurrence_query->posts ) ) {
$target = get_permalink( (int) $occurrence_query->posts[0] );
if ( ! empty( $target ) ) {
wp_safe_redirect( $target, 302 );
exit;
}
}
$parent_url = get_permalink( $parent->ID );
if ( ! empty( $parent_url ) ) {
wp_safe_redirect( $parent_url, 302 );
exit;
}
}, 1 );
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment