Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Select an option

  • Save andrewlimaza/d552e9dbd6dd5be471095cf7e8b6aa87 to your computer and use it in GitHub Desktop.

Select an option

Save andrewlimaza/d552e9dbd6dd5be471095cf7e8b6aa87 to your computer and use it in GitHub Desktop.
Set billing start date (subscription delay) to expiration date when member is renewing for recurring level
<?php
/**
* Move the members subscription start date based on their remaining days of current level that has an expiration date.
* Note: Do not set initial payment to $0, let members pay ahead for their next billing period before starting subscriptions.
* Useful for any migration where we cannot migrate the subscription and need to checkout again.
*/
function my_pmpro_renewal_defer_startdate( $checkout_level ) {
// Only run on the frontend during checkout
if ( ! function_exists( 'pmpro_getMembershipLevelForUser' ) ) {
return $checkout_level;
}
$user_id = get_current_user_id();
if ( ! $user_id ) {
return $checkout_level;
}
// Only for recurring levels.
if ( ! pmpro_isLevelRecurring( $checkout_level ) ) {
return $checkout_level;
}
// Get the member's current level
$current_level = pmpro_getMembershipLevelForUser( $user_id );
// Only proceed if they already hold this exact level (renewal scenario)
if ( empty( $current_level ) || (int) $current_level->id !== (int) $checkout_level->id ) {
return $checkout_level;
}
// Only defer if there's a future expiration date
if ( empty( $current_level->enddate ) || $current_level->enddate === '0000-00-00 00:00:00' ) {
return $checkout_level;
}
// Seconds remaining on the current level from today until the enddate.
$days_remaining = $current_level->enddate - time();
// If there are any days remaining, they still pay the full initial amount BUT they also get their subscription first payment date to be delayed for remaining days.
if ( $days_remaining > 0 ) {
// The original first-billing date is now + cycle_number cycle_period (e.g. +1 Year).
$original_startdate = strtotime( '+' . (int) $checkout_level->cycle_number . ' ' . $checkout_level->cycle_period );
$new_startdate = $original_startdate + $days_remaining;
$checkout_level->startdate = date( 'Y-m-d', $new_startdate );
// Adjust the text at checkout to show a small hint that billing will only start on a specific date.
add_filter( 'pmpro_level_cost_text', 'my_pmpro_show_checkout_level_startdate_in_cost_text', 10, 2 );
}
return $checkout_level;
}
add_action( 'pmpro_checkout_level', 'my_pmpro_renewal_defer_startdate' );
// Show the checkout level startdate in the cost text so customer's know.
function my_pmpro_show_checkout_level_startdate_in_cost_text( $cost, $level ) {
if ( ! empty( $level->startdate ) ) {
$start_date = date_i18n( get_option( 'date_format' ), strtotime( $level->startdate ) );
$cost .= sprintf( ' <small>(%s %s)</small>', esc_html__( 'Billing starts on', 'paid-memberships-pro' ), esc_html( $start_date ) );
}
return $cost;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment