Automating Customer Order Checks

User
At the moment, we manually search a customers billing/shipping name and postcode (if different) across the whole orders database for every order we receive.
This allows us to check their order history so we can action the order accordingly.
As you can imagine, this is very time-consuming and adds burden on the system and is unneccessary for new customers that ends up not having any other order history.
To reduce the workload, we would like to automate some of this process.
Therefore we were hoping for every order that is placed, if the system can automatically check to make sure there are no other orders with the customer/shipping name, customer/shipping address and postcode, account or email.
Please note: the reason we would have to check all these fields and not just if it is a new account is because sometimes a user may create a new account, but have an order history under different accounts so it is still important to flag customers with the same shipping/billing name, email, shipping/billing address/postcode etc. so we can view their full order history.
If there are no other orders present, then it would be good if on the orders dashboard this order can be denoted with a green dot or something similar to signify that it is a new customer.
Therefore if an order comes in with a green dot annotation, then we know we do not need to check the order history as it is a new customer.
Ideally, this green dot or annotation should be a 'screen option' so it can be enabled/disabled on the order dashboard as we chose (if this is simple enough).
Importantly, in regards to this task we wanted to discuss and make sure if the system automatically runs these check
create wp cron to check new order for custom who has done first time
and don't load on server
Assistant
To automate the process of checking for existing customer order histories in your WooCommerce setup, you can create a custom solution that includes the following steps:

### 1. Create a Custom Function to Check for Existing Orders
You can use a custom function that checks the orders database for existing orders based on the criteria you've specified (billing/shipping name, email, address, and postcode). This function can be triggered when a new order is placed.

### 2. Use WooCommerce Hooks
Leverage WooCommerce hooks to trigger your function when a new order is created. The `woocommerce_new_order` action hook is suitable for this purpose. Here’s a basic outline of what the code could look like:

add_action('woocommerce_new_order', 'check_existing_customer_orders', 10, 1);

function check_existing_customer_orders($order_id) {
    $order = wc_get_order($order_id);
    
    $billing_name = $order->get_billing_first_name() . ' ' . $order->get_billing_last_name();
    $shipping_name = $order->get_shipping_first_name() . ' ' . $order->get_shipping_last_name();
    $billing_email = $order->get_billing_email();
    $billing_address = $order->get_billing_address_1();
    $billing_postcode = $order->get_billing_postcode();
    $shipping_address = $order->get_shipping_address_1();
    $shipping_postcode = $order->get_shipping_postcode();
    
    // Query to check for existing orders
    $args = array(
        'post_type' => 'shop_order',
        'post_status' => 'wc-completed',
        'posts_per_page' => -1,
        'fields' => 'ids',
        'meta_query' => array(
            'relation' => 'OR',
            array(
                'key' => '_billing_first_name',
                'value' => $order->get_billing_first_name(),
                'compare' => '='
            ),
            array(
                'key' => '_billing_last_name',
                'value' => $order->get_billing_last_name(),
                'compare' => '='
            ),
            array(
                'key' => '_billing_email',
                'value' => $billing_email,
                'compare' => '='
            ),
            array(
                'key' => '_billing_address_1',
                'value' => $billing_address,
                'compare' => '='
            ),
            array(
                'key' => '_billing_postcode',
                'value' => $billing_postcode,
                'compare' => '='
            ),
            // Add additional checks for shipping details as necessary
        ),
    );

    $existing_orders = new WP_Query($args);

    if ($existing_orders->have_posts()) {
        // Customer has existing orders
        update_post_meta($order_id, '_is_new_customer', 'no');
    } else {
        // Customer is new
        update_post_meta($order_id, '_is_new_customer', 'yes');
    }
}

### 3. Display the Green Dot on the Order Dashboard
You can modify the WooCommerce Orders dashboard to show a green dot if the order is from a new customer. Use the `manage_edit-shop_order_columns` and `manage_shop_order_posts_custom_column` hooks:

add_filter('manage_edit-shop_order_columns', 'add_new_customer_column');
function add_new_customer_column($columns) {
    $columns['new_customer'] = __('New Customer', 'your-text-domain');
    return $columns;
}

add_action('manage_shop_order_posts_custom_column', 'display_new_customer_column', 10, 2);
function display_new_customer_column($column, $post_id) {
    if ('new_customer' === $column) {
        $is_new_customer = get_post_meta($post_id, '_is_new_customer', true);
        if ($is_new_customer === 'yes') {
            echo '<span style="color: green;">✓</span>'; // Checkmark or green dot
        } else {
            echo '<span style="color: red;">✘</span>'; // Cross or red dot for existing customers
        }
    }
}

### 4. Enable/Disable the Green Dot as a Screen Option
To allow users to toggle this feature, you can add a screen option in the WooCommerce Orders dashboard. Use the following code:

add_action('admin_init', 'add_new_customer_screen_option');
function add_new_customer_screen_option() {
    $screen = get_current_screen();
    if ($screen->id === 'edit-shop_order') {
        $args = array(
            'label' => 'Show New Customer Dot',
            'default' => 'yes',
            'option' => 'show_new_customer_dot'
        );
        add_screen_option('checkbox', $args);
    }
}

add_filter('pre_get_posts', 'filter_new_customer_column');
function filter_new_customer_column($query) {
    if (!is_admin() || !$query->is_main_query() || $query->get('post_type') !== 'shop_order') {
        return;
    }

    $show_new_customer_dot = get_user_meta(get_current_user_id(), 'show_new_customer_dot', true);
    if ($show_new_customer_dot === 'yes') {
        // Implement any filtering or logic if necessary
    }
}

### 5. Create a WP Cron Job (Optional)
If you want to periodically check for new orders in the background without impacting server performance, consider using WP Cron jobs. However, since you're checking for orders upon placement, this might not be necessary unless you want to perform periodic checks on existing orders.

### Summary
This approach will help you automate the process of checking for existing customers while providing an easy way to identify new customers in the WooCommerce Orders dashboard. Be sure to test this implementation in a staging environment before deploying it to your live site. If you need more details on any part, feel free to ask!

User
create wp cron
Assistant
To create a WP Cron job that checks for new orders and identifies new customers periodically, you can follow these steps:

### Step 1: Schedule a Custom WP Cron Event
You can schedule a custom cron event to run at a specified interval. In this example, we'll set it to check for new orders every hour.

// Hook into the 'wp' action to schedule the cron event
add_action('wp', 'schedule_new_customer_check_cron');

function schedule_new_customer_check_cron() {
    if (!wp_next_scheduled('check_new_customer_orders_cron')) {
        // Schedule the event to run hourly
        wp_schedule_event(time(), 'hourly', 'check_new_customer_orders_cron');
    }
}

### Step 2: Create the Function to Run on the Cron Event
Next, create the function that will run when the cron event is triggered. This function will check for new orders and update the customer status.

// Hook the function to the scheduled event
add_action('check_new_customer_orders_cron', 'check_new_customer_orders_cron_function');

function check_new_customer_orders_cron_function() {
    // Query for new orders (you can adjust this as needed)
    $args = array(
        'post_type' => 'shop_order',
        'post_status' => 'wc-pending',
        'posts_per_page' => -1,
    );

    $orders = new WP_Query($args);

    // Loop through each order and check if it's a new customer
    if ($orders->have_posts()) {
        foreach ($orders->posts as $order_id) {
            $order = wc_get_order($order_id);
            
            $billing_name = $order->get_billing_first_name() . ' ' . $order->get_billing_last_name();
            $billing_email = $order->get_billing_email();
            $billing_address = $order->get_billing_address_1();
            $billing_postcode = $order->get_billing_postcode();

            // Query to check for existing orders
            $existing_orders_args = array(
                'post_type' => 'shop_order',
                'post_status' => 'wc-completed',
                'posts_per_page' => -1,
                'fields' => 'ids',
                'meta_query' => array(
                    'relation' => 'OR',
                    array(
                        'key' => '_billing_first_name',
                        'value' => $order->get_billing_first_name(),
                        'compare' => '='
                    ),
                    array(
                        'key' => '_billing_last_name',
                        'value' => $order->get_billing_last_name(),
                        'compare' => '='
                    ),
                    array(
                        'key' => '_billing_email',
                        'value' => $billing_email,
                        'compare' => '='
                    ),
                    array(
                        'key' => '_billing_address_1',
                        'value' => $billing_address,
                        'compare' => '='
                    ),
                    array(
                        'key' => '_billing_postcode',
                        'value' => $billing_postcode,
                        'compare' => '='
                    ),
                ),
            );

            $existing_orders = new WP_Query($existing_orders_args);

            if ($existing_orders->have_posts()) {
                // Customer has existing orders
                update_post_meta($order_id, '_is_new_customer', 'no');
            } else {
                // Customer is new
                update_post_meta($order_id, '_is_new_customer', 'yes');
            }
        }
    }
}

### Step 3: Clear the Scheduled Event on Plugin Deactivation
To avoid having orphaned cron jobs, it's a good practice to clear the scheduled event when your plugin is deactivated.

// Clear the scheduled event upon plugin deactivation
register_deactivation_hook(__FILE__, 'clear_new_customer_check_cron');

function clear_new_customer_check_cron() {
    $timestamp = wp_next_scheduled('check_new_customer_orders_cron');
    wp_unschedule_event($timestamp, 'check_new_customer_orders_cron');
}

### Summary
This setup will create a WP Cron job that checks for new orders every hour. The `check_new_customer_orders_cron_function` function will query the database for new orders, check if the customer exists in the order history, and update the order metadata accordingly.

### Notes
– Adjust the frequency of the cron event as needed (e.g., change `'hourly'` to `'twicedaily'` or `'daily'`).
– Make sure to test this implementation thoroughly in a staging environment before deploying it to your live site.
– You can also trigger the cron event manually for testing by visiting the following URL in your browser (replace `example.com` with your site's domain):

https://example.com/wp-cron.php?doing_wp_cron

Feel free to ask if you need any further assistance or modifications!

Leave a Comment

Your email address will not be published. Required fields are marked *