Perl用户输入SQL Like语句

时间:2017-11-17 05:44:47

标签: sql perl sql-like

我试图获取用户输入并将其发送到SQL Like语句。但我得到错误:无法在未定义的方法上调用方法“bind_param”。 我的原始代码:

#!/usr/bin/perl
use DBI;
#use DBD::Oracle;
use strict;
use warnings;
use CGI;


print "Enter INCD number : ";

my $input = <>;
chomp $input;    

my $DSN = 'driver={SQL Server};Server=ddsfs1; database=sdfds;TrustedConnection=Yes'; 
my $dbh = DBI->connect("dbi:ODBC:$DSN") 
    #print "connected.."
    or die "$DBI::errstr\n";

my $query = $dbh->prepare("SELECT TOP 20 Id
      ,Created
      ,Updated
      ,Message
      FROM FrameworkDEV3.Log.Entry
     where Message  like ?                             
     and Created >= DATEADD(day, -10, GETDATE())
        order by Created desc");
$sth->bind_param(1, '%$input%');

print $sth;
$sth->execute;
#DBI::dump_results($sth);

while( my @data = $query->fetchrow_array())
{
    foreach(@data) {
    print "[$_]";
    }
    print "\n\n";
}

$sth->finish;
$dbh->disconnect;
#print "Connected..";
print "\n";

以下代码根据Dave和Jim的评论修复:

my $sth = $dbh->prepare("SELECT TOP 20 Id
      ,Created
      ,Updated
      ,Message
      FROM FrDEVsd.Log.Entry
     where Message  like ?                             
     and Created >= DATEADD(day, -10, GETDATE())
        order by Created desc");
  $sth->bind_param(1, "%$input%");
print $sth;
$sth->execute;
#DBI::dump_results($sth);
while( my @data = $sth->fetchrow_array())
{
    foreach(@data) {
    print "[$_]";
    }
    print "\n\n";
}

$sth->finish;
$dbh->disconnect;

打印“\ n”;

我现在得到的错误是

  

DBI :: ST = HASH(0x2a9a480)

2 个答案:

答案 0 :(得分:3)

在您的代码中:

my $query = $dbh->prepare("SELECT TOP 20 Id
      ,Created
      ,Updated
      ,Message
      FROM sdada.ada.asd
      where Message  like ?                             
      and Created >= DATEADD(day, -10, GETDATE())
      order by Created desc");
my $sth->bind_param(1, "%$input%");

请注意,预准备语句存储在名为$query的变量中,但您尝试使用从未设置且未定义的$sth进行绑定。这就是错误消息告诉你的。

两个地方使用相同的变量名(以后执行语句时)以解决问题。

答案 1 :(得分:2)

你已经获得了一条鱼。也许我们可以告诉你如何在未来抓住你自己。

这是你的错误:

  

无法在未定义的

上调用方法“bind_param”

你在这一行打电话给bind_param()

my $sth->bind_param(1, "%$input%");

所以你要定义一个变量(称为$sth)并立即期望该变量成为可以调用方法的对象。当您使用my定义变量时,变量会初始化为undef,除非您为此分配内容:

my $var = 'something';

您的代码与此相当。

my $sth = undef;
$sth->my $sth->bind_param(1, "%$input%");

你现在看到问题吗?

在DBI代码中,您经常会看到用于存储我们用于执行语句的语句句柄的变量$sth。我怀疑你是从一些示例DBI代码中复制了这个并从那里获取变量名。如果$sth是一个语句句柄,那么您当然可以在其上调用bind_param()方法。

所以$sth需要是一个语句句柄。我们通过在数据库句柄上调用prepare()方法来创建其中一个。

my $sth = $dbh->prepare($some_sql);

哦,但是等等......你已经有了一条看起来很像的那条线:

my $query = $dbh->prepare("SELECT ...");

所以我看起来就像你开始编写自己的代码一样,使用$query作为变量来保存语句句柄。然后,您从一些示例代码中复制了bind_param()行。这没有编译,因为它使用了你未声明的$sth,所以你只是在它前面插了一个my来解决这个问题?听起来完全准确吗?

您真正想要的是在您已创建的语句句柄上调用bind_param()

$query->bind_param(1, "%$input%");

但是,说实话,我认为坚持使用与DBi相关的变量的“标准”名称是一个好主意。这就是你的维护程序员(可能在六个月后你就好了!)希望看到的。

所以我将prepare()行更改为:

my $sth = $dbh->prepare("SELECT ...");

按原样保留bind_param()来电。您还需要更改fetchrow_array()上要调用的$sth