Need to send an email each time an event is created or modified

I need to be able to send an email to all of my subscribers each time an event is created or modified. I know that we can select a newsletter to be sent out when an event is created, but we create events often and don't want to create a new newsletter for each event. I would like to be able to use the Event variables to list location and name of the event in the email that gets sent. I am pretty new to PHP but it seems like there might be a way to create a function that could send the email and a filter that could be used to call the function each time an event is created or modified.

  • aristath

    Hello there @Phil, I hope you're well today!

    You will have to custom-code this..
    Something like this should work:

    <?php
    
    // SEND EMAIL ONCE POST IS PUBLISHED
    
    function custom_notify_new_post($post_id) {
    	if ( ( 'publish' == $_POST['post_status'] ) && ( 'publish' != $_POST['original_post_status'] ) ) {
    		$post = get_post( $post_id );
    
    		// Only continue processing if the post is an event
    		if ( 'incsub_event' != $post->post_type ) {
    			return;
    		}
    
    		// Get an array of users
    		$users = get_users();
    
    		foreach ( $users as $user ) {
    			// Get the user's email
    			$email = $user->user_email
    
    			// The email subject
    			$email_subject = "A new event has been published.";
    
    			ob_start(); ?>
    
    			<html>
    				<head>
    					<title>New event at <?php bloginfo( 'name' ) ?></title>
    				</head>
    				<body>
    					<p>
    						Hi <?php echo $author->user_firstname ?>,
    					</p>
    					<p>
    						A new event has been posted: <a href="<?php echo get_permalink($post->ID) ?>"><?php the_title_attribute() ?></a>.
    					</p>
    				</body>
    			</html>
    
    			<?php
    
    			$message = ob_get_contents();
    
    			ob_end_clean();
    
    			wp_mail( $email, $email_subject, $message );
    
    		}
    	}
    }
    
    add_action( 'publish_post', 'custom_notify_new_post' );

    Please note though that this will add an action that will send an email to ALL your users when a new event is published.
    If you have a lot of members, this can result in a significant delay when a new event is posted.

    I hope that helps!

    Cheers,
    Ari.

  • Ash

    Hi @Phil

    There is a little error in the above code. Please replace

    $email = $user->user_email

    with

    $email = $user->user_email;

    A semicolon is missing at the end.

    You can add those codes in your functions.php in the theme, if you think your theme won’t be changed. Otherwise mu-plugins is the best solution. To use mu-plugins, go to /wp-content/ and find the folder with name 'mu-plugins'. If there is no folder in that name, then create a folder, name it 'mu-plugins', create a file inside that, give any name you like and paste the code in there. You don't need to activate that plugin. Mu-plugins means must use plugins, so it will be activated automatically always. If you use mu-plugins then add a php start tag at the beginning of the code.

    Cheers
    Ash

  • Ash

    Please try the following modified code:

    add_action( 'save_post', 'notify_me_on_update_event' );
    function notify_me_on_update_event( $post_id ){
    	if ( wp_is_post_revision( $post_id ) )
    		return;
    
    	if( 'incsub_event' == get_post_type( $post ) ) {
    		$users = get_users();
    		foreach ( $users as $user ) {
    			$to = $user->user_email;
    			$sub = "A new event has been published.";
    			$body = 'Hi ' . $user->user_firstname . ', a new event has been posted: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. Thank you.';
    			wp_mail( $to, $sub, $body );
    		}
    	}
    }

    Hope it helps :slight_smile: Please feel free to ask more question if you have.

    Cheers
    Ash

  • Phil

    Hello, The code provided does indeed send an email when a new event is created, just like I wanted. It also sends an email when an event has been modified. I assumed that the code:

    if ( wp_is_post_revision( $post_id ) )
    return;

    would be triggered if an event was modified. I actually do want to send an email when an event is modified, but I want the email to be different. Is there another function that can be used to determine if the event is a modification and not a newly created event?

  • Ash

    Hi @Phil

    Don't remove the following line as then you will get email when the post is autosaved.

    if ( wp_is_post_revision( $post_id ) )
    		return;

    Please try this instead:

    add_action( 'save_post', 'notify_me_on_update_event' );
    function notify_me_on_update_event( $post_id ){
    	if ( wp_is_post_revision( $post_id ) )
    		return;
    
    	if( 'incsub_event' == get_post_type( $post_id ) ) {
    		$users = get_users();
    		foreach ( $users as $user ) {
    			$to = $user->user_email;
    			$sub = "A new event has been published.";
    			$body = 'Hi ' . $user->user_firstname . ', a new event has been posted: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. Thank you.';
    			wp_mail( $to, $sub, $body );
    		}
    	}
    }

    Let me know if it works.

    Hope it helps :slight_smile: Please feel free to ask more question if you have.

    Cheers
    Ash

  • Phil

    Ash,
    The old code worked just fine to send an email regarding an event. The change you suggested works as well. The problem I have is that this function gets triggered for new events AND modified events. I need the function to be able to determine if it is a new post OR a modified post. A new post will get one email, a modified post will get a completely different email. Does this make sense?

  • Phil

    A little more information. Unless I am not understanding the revisions.php file (which is entirely possible) the 'incsub_event' post type does not appear to support revisions. If that is the case, the code:

    if ( wp_is_post_revision( $post_id ) )
    		return;

    would never return if I was editing an event. Am I correct here? Just to summarize, the current code that was given to me does indeed send an email each time a new event is created. It also sends the autosave events, and also sends the email message when an event is modified. I need it to NOT send an email when auto saved, and to send a different email when an event is modified.

  • Phil

    Hey Ari,

    looks like I was wrong. Revisions are enabled for events. I am not sure how I will ever be able to do what I need as every time you open an event, it auto saves a revision. So if I send emails on revisions, it will send an email on the auto save. I need to send the email after the revisions have been made and the event is saved again. I dont know if there is some sort of hook in the events plugin somewhere that I can add an action on.

  • Ash

    Hi @Phil

    The problem I have is that this function gets triggered for new events AND modified events. I need the function to be able to determine if it is a new post OR a modified post. A new post will get one email, a modified post will get a completely different email.

    Would you please try this then?

    add_action( 'publish_post', 'notify_me_on_update_event' );
    function notify_me_on_update_event( $post_id, $post ){
    	if ( wp_is_post_revision( $post_id ) )
    		return;
    
    	if( 'incsub_event' == get_post_type( $post_id ) ) {
    		$users = get_users();
    		foreach ( $users as $user ) {
    			$to = $user->user_email;
    			$sub = "A new event has been published.";
                            if ($post->post_date == $post->post_modified)
                                $body = 'Hi ' . $user->user_firstname . ', a new event has been posted: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. Thank you.'; //Mail content for new created post
                            else
                                $body = 'Hi ' . $user->user_firstname . ', an event has been updated: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. Thank you.'; //Mail content for modified post
    			wp_mail( $to, $sub, $body );
    		}
    	}
    }

    Hope it helps :slight_smile: Please feel free to ask more question if you have.

    Cheers
    Ash

  • Phil

    Hi Ash,

    this code did help. I did have to modify it a little bit however. the codex shows that 'publish_post' is depreciated and it did not work. I changed it to 'save_post' I also had to remove the $post argument from the function and add a line to get the $post. This seems to work correctly now.

    function notify_on_new_event( $post_id ){
    	if ( wp_is_post_revision( $post_id ) )
    		return;
    
    	if( 'incsub_event' == get_post_type( $post_id ) ) {
    		If ( !get_the_title($post_id) == "Auto Draft" )
    			$users = get_users(array('meta_key' => 'gtt_event_optin', 'meta_value' => 'Yes'));
    			foreach ( $users as $user ) {
    				$to = $user->user_email;
    				$post = get_post($post_id);
    				if ($post->post_date == $post->post_modified)
    					$sub = "A new event has been published";
    					$body = 'Hi ' . $user->user_firstname . ', a new event has been posted: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. Thank you.'; //Mail content for new created post
    				else
    					$sub = "An event has been modified";
    					$body = 'Hi ' . $user->user_firstname . ', an event has been updated: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. Thank you.'; //Mail content for modified post
    				wp_mail( $to, $sub, $body );
    			}
    		}
    	}
    }
    
    add_action( 'save_post', 'notify_me_on_update_event' );

    I also added an if statement to see if the title was "Auto Draft" as the auto drafts were sending an email. The last issue I have is that if an event is deleted, the modified event gets sent. Is there a way to determine if the post was deleted so we can send a third email template? Also is there any way to get some of the event data in the email? I am looking for the event date and location specifically.

    thanks

  • Michael Bissett

    Hey @Phil,

    It seems like an "elseif" statement would have to be created, hooking into wp_trash_post, so a separate email would be sent:

    http://codex.wordpress.org/Function_Reference/wp_trash_post

    As for the date and location information, you could use get_post_meta to display that information in the email:

    http://codex.wordpress.org/Function_Reference/get_post_meta

    Let me call one of our SLS staff in to this thread, so that a fix can be cooked up here. :slight_smile:

    Regards,
    Michael

  • Saurabh

    Hi @Phil,

    I hope you are well today!

    I also added an if statement to see if the title was "Auto Draft" as the auto drafts were sending an email.

    The right action to use is save_post_incsub_event which is an action in the form of save_post{post_type} which is run only when a specific post type is saved. It passes three parameters, the post id, the post object and whether this is an update (or a newly published post).

    Since revisions and auto saves (not auto-drafts) are a different post type, they will be ignored.

    So the code will be far simpler:

    function notify_on_new_event( $post_ID, $post, $update ){
    
            $users = get_users(array('meta_key' => 'gtt_event_optin', 'meta_value' => 'Yes'));
            foreach ( $users as $user ) {
                    $to = $user->user_email;
                    if (!$update){
                            $sub = "A new event has been published";
                            $body = 'Hi ' . $user->user_firstname . ', a new event has been posted: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. Thank you.'; //Mail content for new created post
                    } else {
                        if($post->post_status='trash'){
                            // event delete email
                        } else if($post->post_status='publish'){
                            $sub = "An event has been modified";
                            $body = 'Hi ' . $user->user_firstname . ', an event has been updated: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. Thank you.'; //Mail content for modified post
                        }
                    }
                    wp_mail( $to, $sub, $body );
            }
    }
    
    add_action( 'save_post_incsub_event', 'notify_me_on_update_event', 10, 3 );

    The last issue I have is that if an event is deleted, the modified event gets sent. Is there a way to determine if the post was deleted so we can send a third email template?

    That was happening because you were checking the dates. The code above includes a check for post status, so there are only three conditions for sending mail: if a post was new, if it was updated and if it was trashed. Even auto-drafts are ignored.

    Also is there any way to get some of the event data in the email? I am looking for the event date and location specifically.

    There is a way. See plugins/events-and-bookings/lib/class_eab_event_model.php

    In this file, you'll find a class called Eab_EventModel. We just need to instantiate it with our post object, like this:

    $event = new Eab_EventModel( $post );

    After that we can access, almost all the public methods from the class. For eg, for your needs:

    $venue = $event->get_venue();
    $start_date = $event->get_start_dates();
    $end_date = $event->get_end_dates();

    Do have a look at the class for more details. Let me know if you need more help with this.

    Best

    Saurabh

  • Phil

    Thanks Saurabh,
    unfortunatly this code did not work as expected. This code fired the new email before the event had actually been saved. Therefore, there was no information available about the event. When the information was put into the event and saved, an email was not sent with this information. Further, when the event was modified, it did not send out the modification email. Any ideas?

  • Saurabh

    Hi @Phil,

    Hope you are well today!

    This code fired the new email before the event had actually been saved. Therefore, there was no information available about the event.

    Sorry, I missed that. The even information itself is hooked to the wp_insert_post action. And the action I have described runs before it. So, this won't serve our purpose. Even the save_post action runs before it, so you will not have access to the events data.

    Even if we hook into wp_insert_post, we may not have access to the event data. So the action to use would be from the events functions (eab-event_meta-after_save_meta). So, the modified code would need to hook into this action.

    When the information was put into the event and saved, an email was not sent with this information. Further, when the event was modified, it did not send out the modification email.

    I'd need to check this, before I can work on the custom code. Would you be able to extend support access on your site?

    Once I have that, I could check the code that's there, right now and see why the conditions aren't working right.

    I would like to be able to send the RSVP list. This of course would only apply to modified events as a new event would not have any RSVP's yet.

    RSVP's can be fetched using another method of the class I have described earlier. This method get_rsvps() provides an array of yes, maybe and no statuses.

    However, let us sort the conditional emailing before we pull the event data into the emails.

    Best

    Saurabh

  • Saurabh

    Hi @Phil,

    I have modified the code, as follows. I didn't test it on the only site that you have some events on and the child theme activated, since I didn't want to mess with your events.

    Could I test this on a subsite where you have no events and the child theme is not yet activated?

    function notify_on_new_events( $post_id ){
    
    		// get the post object
    		$post = get_post($post_id);
    
    		// figure out if this is an update
    		$update = ($post->post_date < $post->post_modified) ? true : false;
    
    		// get event details
    		$event = new Eab_EventModel( $post );
    		$start_date = $event->get_start_date();
    		$venue = $event->get_venue();
    		$rsvp = $event->get_rsvps();
    		$attending = $rsvp['yes'];
    		foreach ($attending as $key=>$username){
    			$user_list . = ', '. $username;
    		}
            $users = get_users(array('meta_key' => 'gtt_event_optin', 'meta_value' => 'Yes'));
            foreach ( $users as $user ) {
                    $to = $user->user_email;
                    if (!$update){
                            $sub = "A new event has been published";
                            $body = 'Hi ' . $user->user_firstname . ', a new event has been posted: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. It will take place at ' . $venue . '. Thank you.'; //Mail content for new created post
                    } else {
                        if($post->post_status='trash'){
                            // event delete email
                        } else if($post->post_status='publish'){
                            $sub = "An event has been modified";
                            $body = 'Hi ' . $user->user_firstname . ', an event has been updated: <a href="'.get_permalink($post_id).'">'.get_the_title($post_id).'</a>. This event now starts at ' . $start_date . '. Thank you.'; //Mail content for modified post
                        }
                    }
                    wp_mail( $to, $sub, $body );
            }
    }
    
    add_action( 'eab-event_meta-after_save_meta', 'notify_on_new_events' );

    Meanwhile, do let me know how it works for you.

    Best

    Saurabh

  • Phil

    Saurabh,

    I found a syntax error that needed to be resolved.
    $user_list . = ', '. $username;
    This needed the first period removed. After that when I created an event, the function fired immediately with a post title of 'Auto Draft' I added the following to resolve this:

    // if the title is Auto Draft, exit
    		if ( get_the_title($post_id) == 'Auto Draft')
    			return;

    Now, when a new event is created, the proper email gets sent and the Auto Draft email does not get sent. This is a good first step. The next part was modifying an event. This did not trigger an email to be sent out. That part is still not functioning.

    You can test with the only site that has events enabled. It will not be in production until I get this resolved. It was to have been in production a couple of weeks ago. Please feel free to create events and then modify them to test the functionality as needed.

    Phil

  • Phil

    Hey Saurabh,

    I discovered something. I added an echo statement as the first line of the function so I would know that the function is being called. When I create a new event, I see the echo'd text. When I open the existing event to edit it, I do not see the text that should have been echo'd. This tells me that when an event is being edited after publishing, The 'eab-event_meta-after_save_meta' action is not being used.

    Phil

  • Saurabh

    Hi @Phil,

    Good that we are gaining more insights. However, the updating involves a redirection and the echo text will be lost, unless we add a die(); statement immediately afterwards.

    The conditionals were a little messed up. Also 'auto_draft' is a post status to check rather than the title. I have tested and modified the code and the following works:

    function notify_on_new_events( $post_id ){
    
    	// get the post object
    	$post = get_post($post_id);
    
    	// exclude all other statuses
    	if (!('publish' === $post->post_status || 'trash' === $post->post_status)){
    		return;
    	}
    
    	$mail_type = false;
    
    	if ('trash' === $post->post_status){
    		$mail_type = 'delete';
    	}else if ('publish' === $post->post_status){
    		$mail_type = 'new';
    		if($post->post_date < $post->post_modified){
    			$mail_type = 'modified';
    		}
    	}
    
    	if(false === $mail_type){
    		return;
    	}
    
    	// get event details
    	$event = new Eab_EventModel( $post );
    	$start_date = $event->get_start_date();
    	$start_time = $event->get_start_date();
    	$venue = $event->get_venue();
    
    	$rsvp = $event->get_rsvps();
    	$attending = $rsvp['yes'];
    
    	$user_list = '';
    
    	foreach ($attending as $key=>$username){
    		$user_list .= ', ' . $username;
    	}
    
    	// uncomment to test, re-comment to change post status and then uncomment again :)
    	// print_r('<div style="width:100%;background:red;">'.$mail_type.' | '.$start_date.' | '.$venue.' | '.$user_list.'</div>');die();
    
    	// set up recipients
    	$users = get_users(array('meta_key' => 'gtt_event_optin', 'meta_value' => 'Yes'));
    
    	// send mail to each user
    	foreach ( $users as $user ) {
    		$to = $user->user_email;
    
    		switch ($mail_type){
    			case 'new':
    				// send the new event mail
    				$sub = '';
    				$body = '';
    				break;
    			case 'modified':
    				// send the updated event mail
    				$sub = '';
    				$body = '';
    				break;
    			case 'delete':
    				// send the deleted event mail
    				$sub = '';
    				$body = '';
    				break;
    			default:
    				//do nothing
    				break;
    		}
    		if(!empty($sub)){
    			wp_mail( $to, $sub, $body, $headers );
    		}
    	} 	
    
    }
    
    add_action( 'eab-event_meta-after_save_meta', 'notify_on_new_events' );

    I have updated the code on your website. For brevity and clarity, I haven't pasted the actual email code here.

    Do let me know if you find any issues with this.

    Best

    Saurabh

  • leebenjaminrael

    I would like to expand on this functionality to include events created via the buddypress front end event creator.

    The hook 'eab-event_meta-after_save_meta' only seems to be triggered in the backend admin console. I have tried 'wp_ajax_eab_events_fpe-save_event' and 'eab_events_fpe-save_event' to trigger a save/publish event for the front end but its not firing.

    Could you please let me know if there is hook I can use for the ajax save of a event from the front end?

    EDIT:: eab-events-fpe-save_meta seems to be working.

  • Sean

    Hi

    I have followed the above mentioned steps. However, it does not work for me.

    1. Email was not sent out when creation / modify of event
    2. Email for E-newsletter was sent out after numerous time of refreshing the screen (e.g. if email was to send to 3 users, would need to refresh the screen 3 times in order for email to be send out)
    3. Images could not be display after change of permalink to display by postname

    Could you please help?

    • Ash

      Hey there.

      Thanks for posting in this thread, however it might be best if you open your own, even if the issues seem closely related. That way it will remain independent of this one and ensure it doesn't confuse issues here if this thread needs reopening again by the author.

      It also means the member who started this thread or anyone following it isn't inundated with post notifications each time we respond to each other. A lengthy thread could annoy the original poster.

      This also allows us to better track and answer your questions to ensure we don't miss any for you.

      You can start a new thread here:

      https://premium.wpmudev.org/forums/#question

      Thanks
      Ash

Thank NAME, for their help.

Let NAME know exactly why they deserved these points.

Gift a custom amount of points.