为啥我无法在 PHP 和 MySQL 中获取最后一个插入 ID?

Posted

技术标签:

【中文标题】为啥我无法在 PHP 和 MySQL 中获取最后一个插入 ID?【英文标题】:Why can't I get the last insert ID in PHP and MySQL?为什么我无法在 PHP 和 MySQL 中获取最后一个插入 ID? 【发布时间】:2012-03-29 18:49:38 【问题描述】:

我有一个创建课程的函数。我正在尝试获取最后插入 ID,但它不起作用:

public  function createCourse()

    require "/mysqli_connect.php";
    $course_q = "INSERT INTO course (....) VALUES (.....)";

    $course_r = mysqli_query($mysqli, $course_q);
    $course_n = mysqli_affected_rows($mysqli);
    if($course_n == 1)
    
        mysqli_close($mysqli);
        return true;
    
    mysqli_close($mysqli);
    return false;

这是检索我在与函数 createCourse 相同的类中创建的最后一个插入 ID 的函数:

public function getLastInsertID()

    require "/../mysqli_connect.php";

    $course_q= "SELECT LAST_INSERT_ID()";

    $course_r = mysqli_query($mysqli, $course_q);
    $course_n = mysqli_num_rows($course_r);

    //var_dump($course_n);
    if($course_n)
    
        $c = mysqli_fetch_assoc($course_r);
        mysqli_close($mysqli);

        return $c;
    
    mysqli_close($mysqli);
    return NULL;
   

这就是我调用函数的方式:

require "/mysqli_connect.php";
$course = new Course();
$c = $course->createCourse();
$id = $course->getLastInsertID();
var_dump($id);

"$id" 始终是"int(0)"

我也试过了:

require "/mysqli_connect.php";
$course = new Course();
$c = $course->createCourse();
**$id = mysqli_insert_id($mysqli);**

我也试过了:

$course_q= "SELECT LAST_INSERT_ID() from course";

但这也不起作用。大家能看出是什么问题吗? :( 函数 createCourse 本身很好。它创建了我需要的内容,并且在数据库中,但我无法获得最后一个插入 ID。

【问题讨论】:

做一个var_dump($mysqli)并在这里发帖 你关闭了mysql结果资源,才可以用于getLastInsertID,可能是这个原因。 我认为您与 mysqli 的链接为空.. 其中一篇文章回答了您的问题吗?如果是这样,您是否可以接受它以使未来的访客受益?谢谢! (见How do I ask a question here?。) 【参考方案1】:

虽然使用 MySQLi 检索插入 ID 的正确方法是使用 mysqli_insert_id(),但由于您正在执行关联提取,因此您需要为 LAST_INSERT_ID() 提供列别名

 $course_q= "SELECT LAST_INSERT_ID() AS insert_id";

 // Later...
 $c = mysqli_fetch_assoc($course_r);
 echo $c['insert_id'];

但是,这不起作用,因为您已经在 createCourse() 函数中关闭了与 mysqli_close() 的连接。相反,获取 createCourse() 中的插入 id 并返回它。

public  function createCourse()

    // Note: You should not establish the connection in each function call.
    // it only needs to be done once per script, and you can pass the connection
    // into the class constructor or into methods that use it.
    require "/mysqli_connect.php";
    $course_q = "INSERT INTO course (....) VALUES (.....)";

    $course_r = mysqli_query($mysqli, $course_q);
    $course_n = mysqli_affected_rows($mysqli);
    if($course_n == 1)
    
        // Get the insert id before closing the connection
        $insert_id = mysqli_insert_id($mysqli);


        // Note that there probably isn't a good reason to explicitly close the
        // connection here.  It will be closed when the script terminates.
        mysqli_close($mysqli);

        // And return it.
        return $insert_id;
    
    mysqli_close($mysqli);
    return false;


require "/mysqli_connect.php";
$course = new Course();
$c = $course->createCourse();
echo $c;
// $c contains the id

设计类以使用一种通用连接:

类在其构造函数中接收连接。

// Make classes accept the connection as a param:
class MyClass

  // property to hold the connection object
 public $db;

  // constructor receives the connection
  public function __construct($connection) 
    $this->db = $connection;
  
  
  // Methods call it as $this->db
  public function createCourse() 
    $course_r = mysqli_query($this->db, $course_q);
  
      

在控制脚本中只包含一次连接

require_once("/mysqli_connect.php");
// $mysqli is now defined...

// Pass it into the constructor
$course = new MyClass($mysqli);

【讨论】:

您提到在我返回之前关闭那里的连接不是一个很好的理由。那我什么时候应该关闭它?我所有本质上是模型类的类都在关闭 mysqli 然后返回。我把一切都搞砸了吗? :( @JohnathanAu 你没有搞砸,你可以从所有类中删除打开和关闭。打开和关闭连接是一个缓慢且耗费资源的过程,因此最好只执行一次,除非您有充分的理由关闭它。通常它在脚本顶部打开一次,您可以将连接传递给您的类构造函数。您通常不需要手动关闭它 - 脚本将在执行完成时执行此操作。 嗯,我最好尽快更改此设置,因为系统将处理来自世界各地的大量人员。我更震惊为什么我的主管从来没有对我提起过这件事!重申一下,我是否应该只使用一个连接,并且每次运行时只使用一个连接? @JohnathanAu,有时需要多个连接(例如连接到两个单独的数据库),但您通常只需要 一个 连接到任何 任何给定脚本中的一个 数据库。当然也有例外,但是当您遇到例外情况时,您可能会知道。【参考方案2】:

问题是您有多个到数据库的连接,并且最后插入的 ID 会在每个连接的基础上进行跟踪。

注意:您应该在每次运行查询时都连接到同一个数据库。只需在脚本开头连接,并在结尾关闭。不断连接和断开连接会导致您的脚本运行极其缓慢,尤其是在查询较多的情况下。

此外,最后插入的 ID 可通过 MySQLi 的 mysqli_insert_id() 函数获得。

【讨论】:

【参考方案3】:

很可能是因为您在 createCourse() 末尾关闭了 mysqli 连接。

要么不让createCourse() 负责关闭连接(将其移至其他位置),要么让createCourse() 在成功时返回插入ID(或false 在失败时)

【讨论】:

以上是关于为啥我无法在 PHP 和 MySQL 中获取最后一个插入 ID?的主要内容,如果未能解决你的问题,请参考以下文章

使用 PHP/CodeIgniter 在 MySQL 中获取最后执行的查询

为啥 PHP docker 容器无法查找 MYSQL 容器的主机名?

如何在 PHP 中获取 MySQL 表的最后插入 ID?

为啥我的 php 代码没有从数据库中获取多行 [重复]

为啥我无法连接到 mysql 数据库?

PHP 仅以登录形式从 MySQL DB 中获取最后一行