Month-to-Date Sales vs Last Month Widget
Adds a dashboard widget comparing this month's revenue and order count so far with the same days of last month, with the change in percent.
Opens WPIDE on
Code
add_action( 'wp_dashboard_setup', function () {
if ( ! current_user_can( 'view_woocommerce_reports' ) ) {
return;
}
wp_add_dashboard_widget( 'wpide_month_sales', 'Sales this month', function () {
global $wpdb;
$data = get_transient( 'wpide_month_sales' );
if ( false === $data ) {
$tz = wp_timezone();
$now = new DateTimeImmutable( 'now', $tz );
$this_from = $now->modify( 'first day of this month midnight' );
$last_from = $this_from->modify( '-1 month' );
$last_to = $last_from->add( $this_from->diff( $now ) );
$hpos = class_exists( '\Automattic\WooCommerce\Utilities\OrderUtil' ) && \Automattic\WooCommerce\Utilities\OrderUtil::custom_orders_table_usage_is_enabled();
$sum = function ( $from, $to ) use ( $wpdb, $hpos ) {
$from = $from->setTimezone( new DateTimeZone( 'UTC' ) )->format( 'Y-m-d H:i:s' );
$to = $to->setTimezone( new DateTimeZone( 'UTC' ) )->format( 'Y-m-d H:i:s' );
if ( $hpos ) {
return $wpdb->get_row( $wpdb->prepare( "SELECT COUNT(*) AS orders, COALESCE(SUM(total_amount),0) AS total FROM {$wpdb->prefix}wc_orders WHERE type = 'shop_order' AND status IN ('wc-processing','wc-completed') AND date_created_gmt BETWEEN %s AND %s", $from, $to ) );
}
return $wpdb->get_row( $wpdb->prepare( "SELECT COUNT(*) AS orders, COALESCE(SUM(m.meta_value),0) AS total FROM {$wpdb->posts} p INNER JOIN {$wpdb->postmeta} m ON m.post_id = p.ID AND m.meta_key = '_order_total' WHERE p.post_type = 'shop_order' AND p.post_status IN ('wc-processing','wc-completed') AND p.post_date_gmt BETWEEN %s AND %s", $from, $to ) );
};
$data = array( 'this' => (array) $sum( $this_from, $now ), 'last' => (array) $sum( $last_from, $last_to ) );
set_transient( 'wpide_month_sales', $data, 30 * MINUTE_IN_SECONDS );
}
$change = (float) $data['last']['total'] > 0 ? ( (float) $data['this']['total'] - (float) $data['last']['total'] ) / (float) $data['last']['total'] * 100 : null;
printf(
'<p style="font-size:24px;margin:.2em 0"><strong>%1$s</strong></p><p>%2$s</p><p>%3$s</p>',
wp_kses_post( wc_price( $data['this']['total'] ) ),
esc_html( sprintf( '%d orders so far this month', $data['this']['orders'] ) ),
null === $change
? esc_html( 'No sales in the same period last month.' )
: wp_kses_post( sprintf( '<span style="color:%1$s">%2$s%3$s%%</span> compared with the same days last month (%4$s).', $change >= 0 ? '#008a20' : '#d63638', $change >= 0 ? '+' : '', number_format_i18n( $change, 1 ), wc_price( $data['last']['total'] ) ) )
);
} );
} );
Notes
Counts processing and completed orders, caches the figures for 30 minutes and works with HPOS and legacy order storage.
How to add this snippet
- Install WPIDE on your WordPress site (it is free) and open Code Snippets.
- Use snippet above adds it from the library in one click. Or copy the code into a new snippet with the same code type.
- It is added inactive: review the code and settings, then switch it on.