免责声明 - Perl的新手 -
我需要将一个连接的会话字符串传递给准备好的查询,看起来像这样
my $uniqueSessions="SELECT DISTINCT SESSION
FROM $table";
my $queryUniques = $connect->prepare($uniqueSessions);
$queryUniques->execute();
$queryUniques->bind_columns(\$session);
my $query="SELECT session, action
FROM $table
WHERE session
IN (?)
ORDER BY session, id";
my $queryPrep = $connect->prepare($query);
while($queryUniques->fetch()) {
if($counter == 1) {
$sessionString = "'" . $session . "'";
} else {
$sessionString = $sessionString . ", '" . $session . "'";
}
$counter++;
if(($counter % 5) == 0) {
$counter = 1;
$queryPrep->execute($sessionString);
my @test = $queryPrep->fetchall_arrayref();
}
}
然而,这没有返回任何内容,我在我的数据库客户端中尝试了确切的查询,它有效,有什么想法吗?
编辑:对不起似乎已经削减了太多我编辑了代码以确保所有信息都存在;
返回的字符串是引用单引号和逗号之间的会话。
答案 0 :(得分:1)
正如其他人所说:
use strict;
use warnings;
此外,每次进行DBI调用时,您应该这样做:
if ($sth->err()) {
die "ERROR: " . $sth->errstr() . "\n";
}
即使在取了之后。这将解决您可能遇到的许多问题。
我简化了你的程序:
use strict;
use warnings;
use DBI;
my $connect = DBI->connect("$connectString", "$user", "$id");
if (not $connect) {
die qq(connection error\n);
}
my $table = "session";
my $uniqueSessions = "SELECT DISTINCT SESSION
FROM $table";
print qq(\$uniqueSessions = "$uniqueSessions"\n);
my $queryUniques = $connect->prepare($uniqueSessions);
if ($queryUniques->err()) {
die "ERROR: " . $queryUniques->errstr() . "\n";
}
$queryUniques->execute();
if ($queryUniques->err()) {
die "ERROR: " . $queryUniques->errstr() . "\n";
}
my $session;
$queryUniques->bind_columns(\$session);
my $counter = 1;
my $sessionString;
while(my $hashref = $queryUniques->fetch()) {
print "Fetching Row\n";
if($counter == 1) {
$sessionString = "'" . $session . "'";
} else {
$sessionString = $sessionString . ", '" . $session . "'";
}
$counter++;
}
if ($queryUniques->err()) {
print "ERROR = " . $queryUniques->errstr . "\n";
}
print "$sessionString\n";
我基本上拿出第二个查询并在这里和那里修改了一些东西。最后一行打印出$sessionString
,它是所有会话的引用分隔列表。这部分有效。
第二部分是事情变得奇怪的地方。您正在使用$sessionString
并将其作为SQL语句传递。除非我没有看到,$sessionString
只是一个会话列表,而不是一个SQL语句。
正如我所说,检查每个DBI调用的错误,看看你是否在某个地方出错。
您还可以添加如下所示的行:
print qq(DEBUG: SQL Query = '$sqlStatement'\n);
在运行$sth->prepare($sqlStatement)
之前,你可以看到你的SQL语句是什么。
在你弄清(?)
应该是什么之前(我假设你是$ sessionString的组),看起来你正在准备第二个查询。
您需要使用(?)
替换会话,然后执行DBI-> prepare()。
像这样(未经过测试):
(my $sessionQuery = $query) =~ s/\(\?\)/$sessionString/;
my $querySth = $connect->prepare($sessionQuery);
$querySth->execute();
my @test = $queryPrep->fetchall_arrayref();
请记住,qq()
引用语法是您的朋友。我经常使用它:
print qq(DEBUG: \$foo = "$foo"\n);
有时,我只是复制并粘贴一个语句,然后引用它:
print qq(DEBUG: while (my $foo = foobar($bar)) };\n);
令人惊讶的是,我能捕捉到多少错误。然后,我可以在我的程序中搜索DEBUG:
并删除这些行。
请记住,一次写一下你的程序,看看你是否可以$sessionString
工作。然后尝试查看是否可以将其替换为$query
,然后尝试执行计算的查询。
Perl是一种优秀而强大的语言,但语法有时可能有点夸张 - 特别是如果你不习惯面向对象的Perl。
答案 1 :(得分:0)
问自己两个问题:
1)在$sessionString
来电之前,execute()
的价值是多少?
2)execute
方法的返回值是什么?
尝试:
$queryPrep->execute($sessionString) or die $queryPrep->errstr;
答案 2 :(得分:-1)
$ session来自哪里? 首先,我建议把
use strict;
在你的perl程序中,这样你就可以在它们发生之前捕获许多容易的bug。
问题的关键在于您尝试构建用逗号分隔的单引号字符串。在这种情况下,我会使用一个数组来存储您需要的值,然后在发出查询之前加入它们。例如:
my @sessions = ();
# perhaps you meant this?
while(my $session = $queryUniques->fetch()) {
push @sessions, $session
if((scalar @sessions) % 5 == 0) {
my $sessionString = join ",", map { "'$_'" } @sessions;
@sessions = ();
$queryPrep->execute($sessionString);
my @test = $queryPrep->fetchall_arrayref();
}
}