使用AJAX调用wp_mail()时页面仍刷新且邮件无法发送的求助
解决WordPress表单AJAX提交仍刷新的问题
问题根源
你的代码存在几个核心问题导致页面刷新且AJAX无效:
- 未阻止表单默认提交行为:点击提交按钮时,浏览器会优先执行原生表单跳转,AJAX请求还没完成页面就刷新了
- 函数职责混乱:
display_contact_form同时负责输出表单和处理邮件,不符合AJAX的前后端分离逻辑 - 未注册WordPress AJAX动作:WordPress需要显式注册AJAX处理函数,否则
admin-ajax.php无法识别请求 - AJAX请求未携带表单数据:原请求只传了
action,没提交用户填写的姓名、邮箱等内容 - 变量未定义:原函数中
$full_name、$message直接使用会触发PHP错误
修正方案
1. 修改functions.php:拆分函数并注册AJAX动作
将表单输出、AJAX处理、脚本注册拆分为独立函数,同时添加安全验证:
// 输出表单的短代码函数 function display_contact_form() { ob_start(); ?> <form id="contact-form"> <input type="hidden" name="contact_form"> <div class="input-wrapp"> <input type="text" id="full-name" name="full_name" placeholder="Name" required> </div> <div class="input-wrapp"> <input type="email" id="email" name="email" placeholder="Email" required> </div> <div class="input-wrapp"> <textarea id="message" name="message" placeholder="Write something..." required></textarea> </div> <button type="submit" id="contact-form-submit"> <svg width="20" height="20" viewBox="0 0 20 20" fill="none" xmlns="http://www.w3.org/2000/svg"> <path fill-rule="evenodd" clip-rule="evenodd" d="M1.81818 4.85279L9.39603 11.5887C9.74047 11.8948 10.2595 11.8948 10.604 11.5887L18.1818 4.85279V15.4547C18.1818 15.9567 17.7748 16.3637 17.2727 16.3637H2.72727C2.22519 16.3637 1.81818 15.9567 1.81818 15.4547V4.85279ZM3.1865 3.63647H16.8134L9.99995 9.69288L3.1865 3.63647Z" fill="white" /> </svg> Submit Message </button> </form> <?php return ob_get_clean(); } add_shortcode('contact_form', 'display_contact_form'); // AJAX处理邮件发送的函数 function handle_contact_form_ajax() { // CSRF验证 check_ajax_referer('contact_form_nonce', 'nonce'); // 清理并验证表单数据 $full_name = sanitize_text_field($_POST['full_name']); $email = sanitize_email($_POST['email']); $message = sanitize_textarea_field($_POST['message']); // 检查必填字段 if (empty($full_name) || empty($email) || empty($message)) { wp_send_json_error(['message' => '请填写所有必填字段']); } // 发送邮件 $admin_mail = get_option('admin_email'); $subject = 'New message from ' . $full_name; $mail_content = "Message: " . $message . "\n\nCustomer Email: " . $email; $headers = ['From: ' . $full_name . ' <' . $email . '>']; $mail_sent = wp_mail($admin_mail, $subject, $mail_content, $headers); $mail_sent ? wp_send_json_success(['message' => '消息发送成功']) : wp_send_json_error(['message' => '消息发送失败,请稍后重试']); } // 注册AJAX动作(支持登录/未登录用户) add_action('wp_ajax_handle_contact_form', 'handle_contact_form_ajax'); add_action('wp_ajax_nopriv_handle_contact_form', 'handle_contact_form_ajax'); // 注册脚本并传递必要参数 function enqueue_contact_form_scripts() { wp_enqueue_script('contact-form-script', get_template_directory_uri() . '/script.js', ['jquery'], '1.0', true); // 传递PHP变量到JS wp_localize_script('contact-form-script', 'contactFormData', [ 'ajaxUrl' => admin_url('admin-ajax.php'), 'nonce' => wp_create_nonce('contact_form_nonce') ]); } add_action('wp_enqueue_scripts', 'enqueue_contact_form_scripts');
2. 更新script.js:阻止默认行为并传递表单数据
jQuery(document).ready(function($) { $('#contact-form').on('submit', function(e) { // 核心:阻止表单默认提交跳转 e.preventDefault(); const submitBtn = $('#contact-form-submit'); const originalText = submitBtn.html(); // 禁用按钮防止重复提交 submitBtn.prop('disabled', true).html('发送中...'); // 收集表单数据 const formData = { action: 'handle_contact_form', nonce: contactFormData.nonce, full_name: $('#full-name').val(), email: $('#email').val(), message: $('#message').val() }; $.ajax({ type: 'POST', url: contactFormData.ajaxUrl, data: formData, dataType: 'json', success: function(res) { alert(res.data.message); $('#contact-form')[0].reset(); }, error: function(res) { alert(res.responseJSON.data.message); }, complete: function() { // 恢复按钮状态 submitBtn.prop('disabled', false).html(originalText); } }); }); });
关键注意点
e.preventDefault()是阻止页面刷新的核心,必须添加- 使用
wp_localize_script传递admin-ajax.php路径,避免硬编码适配不同站点 - 添加CSRF验证(nonce)提升安全性
- 对用户输入进行sanitize处理,防止恶意内容注入
内容的提问来源于stack exchange,提问作者yanksi_
相关产品推荐
相关产品推荐

