繁体   English   中英

为什么我会在此 php 代码上收到间歇性语法错误?

[英]Why do I get an Intermittent syntax error on this php code?

执行下面的 PHP 代码时,我间歇性地收到此错误。 该查询每次都在 PHPMyAdmin 中工作。 我曾尝试更改引号并将 spotId 更改为不同类型的变量,但似乎没有任何解决方法。

错误:

错误描述:你的SQL语法有错误; 检查与您的 MariaDB 服务器版本相对应的手册,了解在“INSERT INTO 点(`userId`、`desc`、`lat`、`ln​​g`、`type`)附近使用的正确语法(第 2 行的“3wBVC92S7VTGBOdg”)

PHP代码:

  <?php

    include 'connect.php';

    $userId = $_POST['userId'];
    $desc = $_POST['desc'];
    $lat = (float) $_POST['lat'];
    $lng = (float) $_POST['lng'];
    $type = $_POST['type'];
    $difficulty = (int) $_POST['difficulty'];
    $hostility = (int) $_POST['hostility'];
    $spotId = null;
    // upload spot

    $sql = "BEGIN; 
    INSERT INTO spots (`userId`,`desc`,`lat`,`lng`,`type`) VALUES ('$userId','$desc','$lat','$lng','$type');
    SET $spotId = LAST_INSERT_ID();
    INSERT INTO diffrating (`rating`) VALUES ('$difficulty');
    INSERT INTO userdiffrating (`ratingId`,`userId`,`spotId`) VALUES (LAST_INSERT_ID(),'$userId','$spotId');
    INSERT INTO hostrating (`rating`) VALUES ('$hostility');
    INSERT INTO userhostrating (`ratingId`,`userId`,`spotId`) VALUES (LAST_INSERT_ID(),'$userId','$spotId');
    COMMIT;";


    //echo $sql;
    if(mysqli_query($con,$sql)){
        echo("Spot uploaded successfully.");
     }
     else{

     echo 'Try Again';
     echo "Error: Unable to connect to MySQL." . PHP_EOL;
     echo "Debugging errno: " . mysqli_connect_errno() . PHP_EOL;
     echo "Debugging error: " . mysqli_connect_error() . PHP_EOL;
     echo $spotId;
     echo("Error description: " . mysqli_error($con));
     exit;

     }

    ?>

数据库布局: 数据库布局 有没有人有办法解决吗?

要使用mysqli执行此操作,您需要对其进行调整以使用占位符值。 这并不难:

$con->begin_transaction(); // Equivalent to BEGIN;

$spots_stmt = $con->prepare('INSERT INTO spots (`userId`,`desc`,`lat`,`lng`,`type`) VALUES (?,?,?,?,?)');
$spots_stmt->bind_param('isdds', $userId, $desc, $lat, $lng, $type);
$spots_stmt->execute();

$spotId = $spots_stmt->insert_id; // Grabs LAST_INSERT_ID()

$rating_stmt = $con->prepare('INSERT INTO userdiffrating (`ratingId`,`userId`,`spotId`) VALUES (?,?,?)');
$rating_stmt->bind_param('iii', $ratingId, $userId, $spotId);
$rating_stmt->execute();

// ...

$con->commit();

如果您使用带有占位符值的准备好的语句,那么转义问题就会完全消失。 您必须专注于确保正确绑定值,但仅此而已。

第一次和每次都应该编写这样的查询这样您创建的错误就不会再发生了。 这不仅仅是安全问题,这是关于尊重您的时间。 您浪费在追查这些错误上的每一秒都是完全可以避免的。

我故意在这里做的一件事是使用单引号 这会禁用通常的字符串插值,所以如果你因为旧习惯重铺而做类似'INSERT ... VALUES ("$x")'的事情,那么发生的最糟糕的事情就是你在那个领域得到了字面上的$x ,你没有有一个注入错误。 这个错误真的很容易发现,因为它永远不会正常工作,但它基本上是无害的并且很容易修复。 注入错误可能会被忽视,然后会导致灾难性的问题。

还值得注意的是,如果您对mysqli不太投入,那么您可能想考虑 PDO。 它支持命名占位符、除 MYSQL 以外的数据库,并且使用起来更加愉快。

命名占位符意味着您可以针对关联数组准备和执行,没有绑定步骤。 作为一个加号,弄乱插入的顺序或无意中使用错误的类型要困难得多。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM