Невозможно предотвратить функцию, использующую сохранение после запуска дважды
Я использую save_post
для функции отправки электронного письма, когда сообщение обновляется пользователем. Это срабатывает дважды, и я знаю, что это связано с изменениями после публикации и автосохранениями.
Я пытался предотвратить это, заключив свой wp_mail
в условный оператор, но это все равно срабатывает дважды. Какие изменения мне нужно внести, чтобы убедиться, что это срабатывает только один раз, когда пользователь обновляет сообщение?
function updated_search_notification($post_id)
{
$post_type = get_post_type($post_id);
if ($post_type === 'utility-search') {
if ((wp_is_post_revision($post_id)) || (wp_is_post_autosave($post_id))) {
// post is autosave
} else {
// Message Variables
$siteurl = get_option('siteurl');
$post_url = '' . $siteurl . '/wp-admin/post.php?post=' . $post_id . '&action=edit';
$new_search_name = '';
//$new_search_email = get_option( 'new_search_email' );
$new_search_email = '[email]';
$utility_search_customer = '';
$subject = 'Your search has been updated';
// Message Contents
$message = "[Message Contents]";
// Send Email
wp_mail($new_search_email, $subject, $message);
}
}
}
add_action('save_post', 'updated_search_notification', 10, 3);
3 answers
Во-первых, вы можете использовать этот крючок только для одного пользовательского типа:
https://developer.wordpress.org/reference/hooks/save_post_post-post_type/
Этот крючок (и save_post
) вызывается в первый раз, когда вы нажимаете "создать...", а затем крючок вызывается с помощью $update = FALSE
.
Затем, чтобы отправлять электронную почту только при обновлении объекта, вы можете проверить $update
следующим образом:
const UTILITY_SEARCH_POST_TYPE = "utility-search";
add_action("save_post_" . UTILITY_SEARCH_POST_TYPE, function ($post_ID, $post, $update) {
if (wp_is_post_autosave($post_ID)) {
return;
}
if (!$update) { // if new object
return;
}
// preparing e-mail
...
// sending e-mail
wp_mail(...);
}, 10, 3);
Одобренный ответ не сработал для меня. В итоге я попробовал несколько условий, и электронное письмо все равно было отправлено дважды:
function xxx_send_mail($id, $post, $update){
if (defined('DOING_AUTOSAVE') && DOING_AUTOSAVE ) {
return;
}
if (wp_is_post_revision($id)) {
return;
}
if (wp_is_post_autosave($id)) {
return;
}
// if new post
if (!$update) {
return;
}
wp_mail('[email protected]', 'The subject', 'The message');
}
add_action( 'save_post_{the_post_type}', 'xxx_send_mail', 10, 3 );
В итоге я исправил это, добавив удобную функцию, предоставляемую WP, под названием did_action():
function xxx_send_mail($id, $post, $update){
if (defined('DOING_AUTOSAVE') && DOING_AUTOSAVE ) {
return;
}
if (wp_is_post_revision($id)) {
return;
}
if (wp_is_post_autosave($id)) {
return;
}
// if new post
if (!$update) {
return;
}
$times = did_action('save_post_{the_post_type}');
if( $times === 1){
wp_mail('[email protected]', 'The subject', 'The message');
}
}
add_action( 'save_post_{the_post_type}', 'xxx_send_mail', 10, 3 );
Надеюсь, это кому-то поможет
Попробуйте этот фрагмент кода внутри вашей функции:
if ( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) return;
В качестве альтернативы вы можете использовать publish_post крюк. Если вы просто хотите активировать эту функцию, когда статус публикации - публикация.