如何修复 JSON、jQuery、AJAX 和 PHP 之间的错误

Posted

技术标签:

【中文标题】如何修复 JSON、jQuery、AJAX 和 PHP 之间的错误【英文标题】:How to fix error between JSON, jQuery, AJAX and PHP 【发布时间】:2021-08-19 05:17:27 【问题描述】:

我无法弄清楚我的 json 有什么问题。我使用了 php 的 json_encode。所以,在每个页面上,我都有一些需要在每个页面上发送到不同电子邮件地址的表单。但是,如果我评论 jQuery 文件,那么表单会正确提交,所有数据都正确插入数据库,并且代替 jQuery AJAX 响应,我会得到有效的 JSON,例如

"response":"success","content":"3":"Thanks John Doe! Your message is successfully sent to owner of property Hotel Milano!"

如果我想用 jQuery 读取和处理这些数据而不是得到有效的响应,我只会得到空 [] 我尝试了很多选项,所以如果我添加 JSON_FORCE_OBJECT 而不是得到空 [] 我得到空 。但是,如果我在 if (is_array($emails) && count($emails) > 0) 的结束标记之后编写需要编码的 json 数据,那么 json 数据就会正确编码,并且当提交表单时,我会得到有效的响应,但在这种情况下,不会发送表单并且不会插入数据进入分贝。下面是我的 PHP 代码:

<?php
 
ini_set('display_errors', 1);
ini_set('display_startup_errors', 1);
error_reporting(E_ALL);
// define variables and set to empty values
$fname = $tel = $email_address_id = "";
$error = false;
$response = [];
 
//Load the config file
$dbHost = "localhost";
$dbUser = "secret";
$dbPassword = "secret";
$dbName = "booking";
$dbCharset = "utf8";

try 
    $dsn = "mysql:host=" . $dbHost . ";dbName=" . $dbName . ";charset=" . $dbCharset;
    $pdo = new PDO($dsn, $dbUser, $dbPassword);
    $pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
 catch (PDOException $e) 
    $response['response'] = 'error';
    $response['errors'][] = $e->getMessage();
    echo json_encode($response);
    die();

 
use PHPMailer\PHPMailer\PHPMailer;
 
require 'PHPMailer/PHPMailer.php';
require 'PHPMailer/SMTP.php';
require 'PHPMailer/Exception.php';
 
if ($_SERVER['REQUEST_METHOD'] == 'POST') 
    if (isset($_POST['submit'])) 
        //print_r($_POST);
        $fname = $_POST['fname'];
        $tel = $_POST['tel'];
 
        if (empty($fname)) 
            $response['response'] = 'error';
            $error = true;
            $response['errors'][] = 'Name can not be empty!';
         else 
            if (!preg_match("/^[a-zšđčćžA-ZŠĐČĆŽ\s]*$/", $fname)) 
                $response['response'] = 'error';
                $error = true;
                $response['errors'][] = 'Name can contain just letters and white space!';
            
        

        if (empty($tel)) 
            $response['response'] = 'error';
            $error = true;
            $response['errors'][] = "Phone can not be empty!";
         else 
            if (!preg_match('/^[\+]?[0-9]9,15$/', $tel)) 
                $response['response'] = 'error';
                $error = true;
                $response['errors'][] = "Phone can contain from 9 to 15 numbers!";
            
        
 
        if (!$error) 
            // Instantiate a NEW email
            $mail = new PHPMailer(true);
            $mail->CharSet = "UTF-8";
            $mail->isSMTP();
            $mail->Host = 'secret.com';
            $mail->SMTPAuth = true;
            //$mail->SMTPDebug = 2;
            $mail->Username = 'booking@secret.com';
            $mail->Password = 'secret';
            $mail->Port = 465; // 587
            $mail->SMTPSecure = 'ssl'; // tls
            $mail->WordWrap = 50;
            $mail->ishtml(true);
            $mail->setFrom('booking@secret.com');
            $mail->clearAddresses();
            $mail->Subject = "New message from secret.com";
 
            $query = "SELECT owners_email.email_address_id, email_address, owner_name, owner_property, owner_sex, owner_type FROM booking.owners_email INNER JOIN booking.pages ON (pages.email_address_id = owners_email.email_address_id) WHERE `owner_sex`='M' AND `owner_type`='other' AND `pages_id` = ?";
            $dbstmt = $pdo->prepare($query);
            $dbstmt->bindParam(1, $pages_id);
            $dbstmt->execute();
            //var_dump($dbstmt);
            $emails = $dbstmt->fetchAll(PDO::FETCH_ASSOC);
 
            if (is_array($emails) && count($emails) > 0) 
 
                foreach ($emails as $email) 
                    //var_dump($email['email_address']);
                    $mail->addAddress($email['email_address']);
                    $body = "<p>Dear $email['owner_name'], <br>" . "You just received a message from <a href='https://www.secret-booking.com'>secret-booking.com</a><br>The details of your message are below:</p><p><strong>From: </strong>" . ucwords($fname) . "<br><strong>Phone: </strong>" . $tel . "</p>";
                    $mail->Body = $body;
                    if ($mail->send()) 
                        $mail = "INSERT INTO booking.contact_owner (fname, tel, email_address_id) VALUES (:fname, :tel, :email_address_id)";
                        $stmt = $pdo->prepare($mail);
                        $stmt->execute(['fname' => $fname, 'tel' => $tel, 'email_address_id' => $email['email_address_id']]);
 
                        $response['response'] = "success";
                        $response['content'][$email['email_address_id']] = "Thanks " . ucwords($fname) . "! Your message is successfully sent to owner of property $email['owner_property']!";
      
                    //end if mail send
                    else 
                        $response['response'] = "error";
                        $response['content'][$email['email_address_id']] = "Something went wrong! Try again..." . $mail->ErrorInfo;
                    
                //end foreach for email addresses
             //end if for array of emails
/* If use this else for response I allways get this response. Even, if I write JSON for success hier I get it but data isn't sent and isn't inserted into db
else 
                $response['response'] = 'error';
                $response['error'][] = '$emails is either not an array or is empty'; // jQuery just read this
            //end if else for array of emails
*/
        //end if validation
    //end submit
    echo json_encode($response);
//end REQUEST METHOD = POST

这是 submitHanfdler 的 jQuery

 submitHandler: function (form) 
      //Your code for AJAX starts    
      var formData = jQuery("#contactOwner").serialize();
      console.log(formData); //this work
      jQuery.ajax(
        url: '/classes/Form_process.class.php',
        type: 'post',
        data: formData,
        dataType: 'json',
        cache: false,
        success: function (response) 
         
          jQuery("#response").text(response['content']);
         // debbuger;
          console.log(response);
          //console.log(response.hasOwnProperty('content'));
        , 
        error: function (response) 
    
         // alert("error");
         jQuery("#responseOwner").text("An error occurred");
          console.dir("Response: " + response);
        
      ); //Code for AJAX Ends
      // Clear all data after submit
      var resetForm = document.getElementById('contactOwner').reset();
      return false;
     //submitHandler

提前感谢您的任何帮助,我们将不胜感激!

【问题讨论】:

【参考方案1】:

我怀疑问题出在 dataType: 'json' 属性上。这是因为 serialize 函数不提供 json 数据。看看这是否有效:

jQuery.ajax(
    url: '/classes/Form_process.class.php',
    method: 'POST',
    data: jQuery("#contactOwner").serialize()
).done(function (response) 
    console.log(response);
).fail(function (error) 
    console.log(error);
);

或者,如果你想使用 dataType: 'json',你需要发送 json 数据:

jQuery.ajax(
    url: '/classes/Form_process.class.php',
    method: 'POST',
    data: 
      firstName: jQuery("#contactOwner .first-name").val(),
      lastName: jQuery("#contactOwner .last-name").val(),
      ...
    
    dataType: 'json',
    cache: false,
).done(function (response) 
    console.log(response);
).fail(function (error) 
    console.log(error);
);

如果您使用如上所示的对象添加数据,这应该与 dataType: 'json' 一起使用。

【讨论】:

我尝试了所有两种方法,但是在所有两种方法中,它都跳过了 jQuery 验证,因此需要检查为什么会发生这种情况以及错误是什么。但是,jQuery 使用 type:POST 而不是 od 方法,并且我正在更改它,但是还有其他一些原因导致该文件被跳过,所以有些问题。已经看到了,你在完成之前关闭了 AJAXY,我有返回 false,所以有一些问题....我现在会深入检查

以上是关于如何修复 JSON、jQuery、AJAX 和 PHP 之间的错误的主要内容,如果未能解决你的问题,请参考以下文章

如何使用 AJAX 和 JQuery 使用 JSON 数据实现 PUT 调用?

如何从MVC5中的jquery ajax调用中获取部分视图和JSON数据?

如何通过 Ajax 在 jQuery DataTables 中显示 JSON 数据?

如何使用 ajax、查询、json 加载页面? [复制]

通过 jQuery Ajax 发送 Json 数组

如何使用 jQuery AJAX 和 JSON 通过 Bootbox 确认表单提交