Php mysql_last_id()的竞争条件

Php mysql_last_id()的竞争条件,php,mysql,sql,transactions,lastinsertid,Php,Mysql,Sql,Transactions,Lastinsertid,我花了一天的大部分时间试图找到答案,但似乎没有答案。我需要一个函数,它在表中创建一行,从插入的行中检索自动增量,然后使用该值在第二个表中插入另一行。在功能上类似于以下php的内容: $mysql_query("INSERT INTO table1 SET columns='values'"); $id = mysql_insert_id(); $mysql_query("INSERT INTO table2 SET id='$id', columns='values'"); 我遇到的问题是,在

我花了一天的大部分时间试图找到答案,但似乎没有答案。我需要一个函数,它在表中创建一行,从插入的行中检索自动增量,然后使用该值在第二个表中插入另一行。在功能上类似于以下php的内容:

$mysql_query("INSERT INTO table1 SET columns='values'");
$id = mysql_insert_id();
$mysql_query("INSERT INTO table2 SET id='$id', columns='values'");
我遇到的问题是,在我的应用程序中,所有类之间共享一个MySQL连接,因此我担心这可能会导致竞争条件,即另一个类在运行上述第1行和第2行之间插入一行

我能想到的最简单的解决方案是让任何使用
mysql\u insert\u id()
的函数打开一个新的、唯一的连接,但这似乎是一个巨大的不必要的开销。我尝试过的其他答案包括插入一个唯一值(可能是用
UUID()
创建的)并使用该值代替自动递增值,或者可能将第一次插入和对
LAST\u insert\u ID()
的调用放在存储函数中(尽管我不确定这是否会解决可能的争用条件)

我也一直在研究事务,看看它们是否有帮助,但是关于
mysql\u insert\u id()
如何与它们交互的文档很少。据我所知,它们在这里可能没有帮助,因为另一个与任何事务的锁都不冲突的
INSERT
仍然能够执行,并且可能导致相同的竞争条件


那么,假设我没有犯上述任何错误(如果我有错误,请纠正我),什么是确保第二个
INSERT
使用正确值的100%的最佳方法?

php脚本的执行是线性的,而不是多线程的。
因此,当一个对象与另一个对象同时执行时,不可能有一个条件


唯一可能的问题是持久连接。但似乎同一个连接无论如何都不能被两个单独的调用使用。即使它是持久的,如果它已经在使用中,它也不能被其他脚本使用。因此,也不会有任何问题。

尝试使用if-conditional

范例

if(mysql_query(query)){
    $id = mysql_last_id();
    mysql_query(query using $id);
}

相信我,我花在阅读手册上的时间远远超过了几分钟。我知道,
mysql\u insert\u id()
是特定于连接的,但正如我在原始帖子中所说的,我的应用程序的所有类目前都使用相同的连接(有一个单独的db类存储连接,所有的类都通过
global$db;
使用它。现在,如果php代码的多个部分不能同时运行,而仍然使用同一个连接,这确实会简化这个过程,但我还没有找到任何支持或拒绝它的方法。W关于AJAX脚本如何同时加载多个php文件?我知道php不直接支持多线程,但浏览器/服务器是否会导致类似的行为?@MikeF别担心,这是不可能的-这就是他所说的执行是线性的。如果我通过AJAX加载一个页面,每个页面都报告相同的资源连接的ce编号,因此如果它们同时运行,我可能会遇到问题。我仍然不知道它们在哪里被阻止同时使用相同的连接。是不是在服务器级别的某个地方,直到前面的XHR加载完成,XHR才得以实现?注意:不要试图与您的ans争论wers,只是想更深入地了解引擎盖下发生的事情。@Mike相同的资源数量是巧合,我认为它们是按每个脚本计算的。新的PHP请求是新的PHP请求,无论是否通过Ajax。同时的请求不共享同一个数据库连接。您没有什么可担心的请注意,您显示的代码将始终运行良好