当压力测试mod_perl数据库连接正在消失时,我遇到了一个问题。我怀疑进程正在共享数据库连接,导致问题。
但是我已经遵循了Apache :: DBI的所有说明,并且无法解决这个问题。
我正在子进程中建立连接,而不是在startup.pl中建立连接。但是当我检查每个孩子从DBI-> connnect返回的$ dbh时,每个httpd进程的地址都是相同的。 首先,如果这是正常工作并为每个进程重新连接,那么DBI-> connect返回的地址是否应该针对每个子进程不同?我假设是这样,但据我所知,DBI中的核心C代码(dbih_setup_handle)正在管理它并返回相同的地址。所以也许我不明白重新联系孩子意味着什么。
如果$ dbh句柄相同,我是否正确重新连接?
答案 0 :(得分:0)
听起来您正在启动配置中的<perl>...</perl>
部分或启动时加载的模块中建立数据库连接,并保持它,直到分叉进程尝试使用它。
不幸的是,你无法逃避这一点。您需要以某种方式确保新进程获得新连接。
我对此问题的解决方案是获取dbh的核心功能,该dbh跟踪建立连接时$$
(当前进程ID)的内容。如果在移交连接时,函数发现$$
已更改,它将处理任何现有连接而不关闭它们,并创建一个新连接:
my $_dbh;
my $pid;
sub dbh {
if($pid != $$) {
$_dbh = DBI->connect(...);
$pid = $$;
}
return $_dbh;
}
任何想要使用数据库的代码都会首先调用dbh()
来获取数据库句柄,并在必要时让它创建一个新句柄,或者如果可以使用它,则移交先前建立的连接。