遵循指南here我想在我的perl
代码中放置一个DBI连接处理子例程。我认为BEGIN
块是一个合理的位置,所以如果我遇到DBI
连接的问题,它将在移动剩余(这是相当长的)之前失败。
BEGIN {
my $dbh;
use constant {
my_host => 'database=MYDB;host=MYHOST',
my_user => 'USER',
my_pass => 'PASSWORD'
};
sub get_db_handle {
unless (defined ($dbh)) {
my $dbh = DBI->connect(
('DBI:mysql:' . my_host),
my_user, my_pass,
{PrintError => 0, AutoCommit => 0}
) or die $DBI::errstr;
}
return $dbh;
}
}
...
# Everything works fine without it being in the BEGIN
my $db = get_db_handle();
my $sth = $db->prepare($sql);
运行时,我得到预期的错误:
无法调用方法"准备"在未定义的值
为了解决这个问题,我在声明use constant
值之后立即运行DBI连接字符串并且它有效,但这似乎不是最好的方法,并且作者没有任何关于这个实施发布了。
是否有一个典型的用法说明这种方法,创建DBI处理程序和一个sub来传递我应该查看的脚本,或者是否有更好的方法来defined
语句,这将允许我使用上面的方法?
答案 0 :(得分:5)
删除第2个my $dbh
:
sub get_db_handle {
unless (defined ($dbh)) {
$dbh = DBI->connect(# <- no "my" here
('DBI:mysql:' . my_host),
my_user, my_pass,
{PrintError => 0, AutoCommit => 0}
) or die $DBI::errstr;
}
答案 1 :(得分:3)
问题是您在$dbh
块中声明了两个 BEGIN
变量。
unless
检查外部 $dbh
是否已定义,如果没有,则声明新的$dbh
,为其分配数据库句柄,以及然后扔掉它。
子程序返回外部 $dbh
的值,该值始终为undef
。
解决方案是从my
语句的开头删除connect
;然后在任何地方都会引用相同的变量。
答案 2 :(得分:2)
您要声明两个名为$dbh
的变量。使用$dbh
代替my $dbh
来使用现有变量。
此外,您实际上并不想在编译时尝试连接,而忘记检查prepare
是否成功。修正:
use constant {
MY_HOST => 'database=MYDB;host=MYHOST',
MY_USER => 'USER',
MY_PASS => 'PASSWORD',
};
{
my $dbh;
sub get_db_handle {
$dbh ||= DBI->connect(
'DBI:mysql:' . MY_HOST,
MY_USER, MY_PASS,
{ PrintError => 0, AutoCommit => 0 },
)
or die $DBI::errstr;
return $dbh;
}
}
# Make sure DB errors are discovered early.
BEGIN { get_db_handle(); }
...
my $dbh = get_db_handle();
my $sth = $dbh->prepare($sql)
or die $DBI::errstr;
如果您使用RaiseError => 1
,则可以缩短为
use constant {
MY_HOST => 'database=MYDB;host=MYHOST',
MY_USER => 'USER',
MY_PASS => 'PASSWORD',
};
{
my $dbh;
sub get_db_handle {
return $dbh ||= DBI->connect(
'DBI:mysql:' . MY_HOST,
MY_USER, MY_PASS,
{ RaiseError => 1, PrintError => 0, AutoCommit => 0 },
);
}
}
# Make sure DB errors are discovered early.
BEGIN { get_db_handle(); }
...
my $dbh = get_db_handle();
my $sth = $dbh->prepare($sql);
不确定缓存启用了事务的句柄有多大意义。