Fork+DBI 和语句句柄
Fork+DBI and statement handles
情况
所以我知道连接在进程之间共享,我不能在子进程中使用我在分叉之前打开的连接。
我也知道当我尝试做这样的事情时 perl 会抱怨:
my $sth = $dbConn->prepare($sql);
$sth->execute();
$dbConn->disconnect();
while(my @row = $sth->fetchrow_array){
print @row,"\n";
}
因为我在语句句柄仍处于活动状态时尝试断开连接。
为什么这样行得通:
my $sth = $dbConn->prepare($sql);
$sth->execute();
while(my @row = $sth->fetchrow_array){
my $pid = fork;
if(not defined $pid){
warn "Could not fork\n";
next; # abort loop
}
if($pid){
#Parent: Do nothing
}
else{
#do stuff
exit;
}
}
如果子进程在退出时关闭它,perl 不应该抱怨语句句柄仍然处于活动状态吗?我还确保在循环完全迭代之前某些进程的执行已经结束,并认为它可能会抱怨,但事实并非如此。在这种情况下,我不应该获取数组引用并使用它们迭代而不是我演示的方法吗?
更新
您在上面的评论中说子进程 do 关闭了父进程的数据库句柄,所以唯一的问题是为什么没有关于与句柄的关闭
那是因为子进程会也先关闭终止时的语句句柄,然后再关闭数据库句柄,所以不会报错
你没有说你使用的是什么数据库驱动程序,我猜你只是碰巧有一个表现良好的驱动程序
DBI
模块的文档是这样说的
For some drivers, when the child process exits the destruction of inherited handles cause the corresponding handles in the parent process to cease working.
所以您使用的驱动程序可能不是这些驱动程序之一
另一种方法是连接到数据库的代码设置 AutoInactiveDestroy
标志。它强制 DESTROY
方法检查当前 PID 是否与创建数据库和语句句柄的 PID 相同,无论如何都是推荐所有新代码的做法
情况
所以我知道连接在进程之间共享,我不能在子进程中使用我在分叉之前打开的连接。
我也知道当我尝试做这样的事情时 perl 会抱怨:
my $sth = $dbConn->prepare($sql);
$sth->execute();
$dbConn->disconnect();
while(my @row = $sth->fetchrow_array){
print @row,"\n";
}
因为我在语句句柄仍处于活动状态时尝试断开连接。
为什么这样行得通:
my $sth = $dbConn->prepare($sql);
$sth->execute();
while(my @row = $sth->fetchrow_array){
my $pid = fork;
if(not defined $pid){
warn "Could not fork\n";
next; # abort loop
}
if($pid){
#Parent: Do nothing
}
else{
#do stuff
exit;
}
}
如果子进程在退出时关闭它,perl 不应该抱怨语句句柄仍然处于活动状态吗?我还确保在循环完全迭代之前某些进程的执行已经结束,并认为它可能会抱怨,但事实并非如此。在这种情况下,我不应该获取数组引用并使用它们迭代而不是我演示的方法吗?
更新
您在上面的评论中说子进程 do 关闭了父进程的数据库句柄,所以唯一的问题是为什么没有关于与句柄的关闭
那是因为子进程会也先关闭终止时的语句句柄,然后再关闭数据库句柄,所以不会报错
你没有说你使用的是什么数据库驱动程序,我猜你只是碰巧有一个表现良好的驱动程序
DBI
模块的文档是这样说的
For some drivers, when the child process exits the destruction of inherited handles cause the corresponding handles in the parent process to cease working.
所以您使用的驱动程序可能不是这些驱动程序之一
另一种方法是连接到数据库的代码设置 AutoInactiveDestroy
标志。它强制 DESTROY
方法检查当前 PID 是否与创建数据库和语句句柄的 PID 相同,无论如何都是推荐所有新代码的做法