Search code examples
phpwordpresswoocommercecustom-fieldsemail-notifications

Add attendees emails as CC for WooCommerce processing and completed email notifications


I'm currently trying to add emails from my custom checkout field to the list of cc recipients for processing and completed order emails.

I have used this code for creating repeating sets of custom fields, based on product quantity in the cart.

add_action( 'woocommerce_before_order_notes', 'persons_details' );
function persons_details( $checkout ) {
    $count = WC()->cart->get_cart_contents_count();
    $i = 0;

    for( $k=1; $k<= $count; $k++ ) {
        $i++;
        echo '<div><strong>'. __('Účastník ') . $i . '</strong></div>';
        
        woocommerce_form_field( 'cstm_full_name' . $i, array(
            'type'          => 'text',
            'class'         => array('my-field-class form-row-first'),
            'label'         => __("Jméno a Příjmení"),
            'placeholder'   => __(""),
            'required'      => true,
        ), $checkout->get_value( 'cstm_full_name' . $i ));
        
        woocommerce_form_field( 'cstm_email' . $i, array(
            'type'          => 'email',
            'class'         => array( 'my-field-class form-row-last' ),
            'label'         => __( "Email" ),
            'placeholder'   => __(""),
            'required'      => true,
        ), $checkout->get_value( 'cstm_email' . $i ));
        
        woocommerce_form_field( 'cstm_phone' . $i, array(
            'type'          => 'number',
            'class'         => array('my-field-class form-row-first'),
            'label'         => __("Telefon"),
            'placeholder'   => __(""),
            'required'      => true,
        ), $checkout->get_value( 'cstm_phone' . $i ));
        
        woocommerce_form_field( 'cstm_bdate' . $i, array(
            'type'          => 'date',
            'class'         => array('my-field-class form-row-last'),
            'label'         => __("Datum narození"),
            'placeholder'   => __(""),
            'required'      => true,
        ), $checkout->get_value( 'cstm_bdate' . $i ));
        
        echo '<div class="clear"></div>
        <div class="clearbox"></div>';
    }
}

add_action( 'woocommerce_checkout_create_order', 'save_custom_checkout_field_order_meta' );
function save_custom_checkout_field_order_meta( $order )
{
    $count = WC()->cart->get_cart_contents_count();
    $order->update_meta_data( 'cstm_items_count', intval($count) ); // Save the cart contents count as meta data
    
    $i = 0;
    for($k=1; $k<= $count; $k++) {
        $i++;
        if ( isset($_POST['cstm_full_name'.$i]) && ! empty($_POST['cstm_full_name'.$i]) ) {
            $order->update_meta_data( 'cstm_full_name'.$i, sanitize_text_field($_POST['cstm_full_name'.$i]) );
        }
        if ( isset($_POST['cstm_email'.$i]) && ! empty($_POST['cstm_email'.$i]) ) {
            $order->update_meta_data( 'cstm_email'.$i, sanitize_text_field($_POST['cstm_email'.$i]) );
        }
        if ( isset($_POST['cstm_phone'.$i]) && ! empty($_POST['cstm_phone'.$i])) {
            $order->update_meta_data( 'cstm_phone'.$i, sanitize_text_field($_POST['cstm_phone'.$i]) );
        }
        if ( isset($_POST['cstm_bdate'.$i]) && ! empty($_POST['cstm_bdate'.$i])) {
            $order->update_meta_data( 'cstm_bdate'.$i, sanitize_text_field($_POST['cstm_bdate'.$i]) );
        }
    }
}

add_action( 'woocommerce_email_order_meta', 'add_email_custom_order_meta', 10, 3 );
function add_email_custom_order_meta( $order, $sent_to_admin, $plain_text ){
    $quantity = $order->get_meta('cstm_items_count'); // Get items quantity count from meta data
    
    echo '<ul>';
    $i = 0;
    for( $k=1; $k <= $quantity; $k++ ) {
        $i++;
        echo '<li><strong>'. __("Účastník ") . $i . '<strong></li>
        <li>' . __("Jméno a Příjmení: ") . $order->get_meta('cstm_full_name'.$i) . '</li>
        <li>' . __("Email: ") . $order->get_meta('cstm_email'.$i) . '</li>
        <li>' . __("Telefon: ") . $order->get_meta('cstm_phone'.$i) . '</li>
        <li>' . __("Datum narození: ") . $order->get_meta('cstm_bdate'.$i) . '</li>';
    }
    echo '</ul>';
}

add_action( 'woocommerce_admin_order_data_after_order_details', 'display_custom_fields_in_admin_order_pages' );
function display_custom_fields_in_admin_order_pages( $order ){ 
    $quantity = $order->get_meta('cstm_items_count'); // Get items quantity count from meta data  
    
    echo '<div class="order_data_column" style="width: 100% !important;">
        <h4>' . __( 'Your label' ) . '</h4>
        <ul>';
        $i = 0;
        for( $k=1; $k <= $quantity; $k++ ) {
            $i++;
            echo '<li><strong>'. __("Účastník ") . $i . '<strong></li>
            <li>' . __("Jméno a Příjmení: ") . $order->get_meta('cstm_full_name'.$i) . '</li>
            <li>' . __("Email: ") . $order->get_meta('cstm_email'.$i) . '</li>
            <li>' . __("Telefon: ") . $order->get_meta('cstm_phone'.$i) . '</li>
            <li>' . __("Datum narození: ") .$order->get_meta('cstm_bdate'.$i) . '</li>';
        }
        echo '</ul>
    </div>';
}

add_action( 'woocommerce_after_checkout_validation', 'custom_checkout_fields_validation', 20, 2 );
function custom_checkout_fields_validation( $data, $errors ){
    $count = WC()->cart->get_cart_contents_count();
    
    $i = 0;
    for($k=1; $k<= $count; $k++) {
        $i++;
        if ( isset($_POST['cstm_full_name'.$i]) && empty($_POST['cstm_full_name'.$i]) ) {
            $errors->add( 'cstm_full_name'.$i,  __( "Prosím vyplňte povinné pole u Účastníka $i \"Jméno a Příjmení\"" ), 'error' );
        }
        if ( isset($_POST['cstm_email'.$i]) && empty($_POST['cstm_email'.$i]) ) {
            $errors->add( 'cstm_email'.$i,  __( "Prosím vyplňte povinné pole u Účastníka $i \"Email\"" ), 'error' );
        }
        if ( isset($_POST['cstm_phone'.$i]) && empty($_POST['cstm_phone'.$i])) {
            $errors->add( 'cstm_phone'.$i,  __( "Prosím vyplňte povinné pole u Účastníka $i \"Telefon\"" ), 'error' );
        }
        if ( isset($_POST['cstm_bdate'.$i]) && empty($_POST['cstm_bdate'.$i])) {
            $errors->add( 'cstm_bdate'.$i,  __( "Prosím vyplňte povinné pole u Účastníka $i \"Datum narození\"" ), 'error' );
        }
    }
}

And that works marvelously, collecting the data etc. Had a little bit of and hiccup with the Divi checkout template, but when I switched back to the default woocommerce checkout shortcode, data from those fields are collected.

Now, one of these fields is an attendee email, which collects email addresses of all of the course students. These I would like to include in the CC field for the Processing and Completed order status email notifications.

I have tried to modify this code:

add_filter( 'woocommerce_email_headers', 'student_email_notification', 20, 3 );
function student_email_notification( $header, $email_id, $order ) {
    // Only for 'wc_course_order' notification
    if( 'wc_course_order' != $email_id ) return $header; 

    $student_emails = array();
    $enroll_num = 0;

    // Loop though  Order IDs
    foreach( $order->get_items() as $item_id => $item_data ){
        $course_qty = $item_data->get_quantity();
        $q = 1;
        while ( $q <= $course_qty){
            $enroll_num++;
            // Get the student full Name
            $full_name     = wc_get_order_item_meta( $item_id, 'First Name - '.$enroll_num, true );
            $full_name    .= ' ' . wc_get_order_item_meta( $item_id, 'Last Name - '.$enroll_num, true );
            // Get the student email
            $student_email = wc_get_order_item_meta( $item_id, 'Student Email - '.$enroll_num, true );
            if( ! empty($student_email) && $full_name != ' ' )
                // Format the name and the email and set it in an array
                $student_emails[] = utf8_decode($full_name . ' <' . $student_email . '>'); // Add name + email to the array
            $q++;
        }
    }

    // If any student email exist we add it
    if( count($student_emails) > 0 ){
        // Remove duplicates (if there is any)
        $student_emails = array_unique($student_emails);
        // Add the emails to existing recipients
        $header .= 'Bcc: ' . implode(',', $student_emails) . "\r\n";
    }
    return $header;
}

But couldn't get it to work. What am I doing wrong?


Solution

  • There are multiple mistakes in your code. The following code below will allow adding attendees emails as CC for Processing and Completed order email notifications:

    add_filter( 'woocommerce_email_headers', 'additional_cc_recipient', 10, 3 );
    function additional_cc_recipient( $headers, $email_id, $order ) {
        // Only for Processing and Completed order email notifications
        if( in_array($email_id, ['customer_processing_order', 'customer_completed_order']) ) {
            if ( $count = $order->get_meta('cstm_items_count') ) {
                $recipient = []; // initializing
    
                for ( $i = 1; $i <= $count; $i++ ) {
                    if ( $email = $order->get_meta('cstm_email'.$i) ) {
                        // Add attendees emails, avoiding duplicates
                        $recipient[$email] = utf8_decode($order->get_meta('cstm_full_name'.$i) . ' <' . $email . '>');
                    }
                }
                $headers .= 'Cc: ' . implode(',', $recipient) . "\r\n";
            }
        } 
        return $headers;
    }
    

    Code goes in functions.php file of your child theme (or in a plugin). It should work.