使用没有引用的PHP MySQLi预处理语句?

xzabzqsa  于 2023-04-10  发布在  PHP
关注(0)|答案(3)|浏览(106)

有没有一种方法可以使用MySQLi预处理语句而不传递引用?
【背景:我对PHP和MySQL非常陌生,但我继承了一个私有的WordPress插件来维护,所以我边走边学。
我知道预处理语句are useful是为了防止SQL注入,也可能是为了加快查询速度(如果保留这些语句的话),但是需要引用变量似乎很奇怪。是否有人在前面调用bind_param,然后在进行后续查询时只将数据设置到这些绑定变量中,而不是与语句交互?
现在我重构的代码有17个变量,它传递到bind_param。我创建了一个类来包含所有的数据,所以我不再需要在函数之间传递17个变量,但是下面的代码显然失败了,因为我的类没有返回引用:

$stmt->bind_param('ssssssisssssssssi',
      $my_class->get(FIELD_ONE),
      $my_class->get(FIELD_TWO),
      /*...x15 more...*/)

考虑到代码当前在$stmt->execute()之后立即丢弃$stmt(因此没有长期变量需要跟踪),有没有什么方法可以让我使用预处理语句而不必创建临时变量,以便我可以绑定它们?有没有一个替代的类/接口我可以或应该使用?
谢谢!

xggvc2p6

xggvc2p61#

是的,有。
不久前PHP增加了一个非常宝贵的特性-参数解包操作符。它有十亿个用途,在这种情况下帮助你就是其中之一。
只需在值列表之前添加...[,在值列表之后添加]-瞧,它工作了!

$stmt->bind_param('ssssssisssssssssi', ...[
  $my_class->get(FIELD_ONE),
  $my_class->get(FIELD_TWO),
  /*...x15 more...*/
  ]);

提示:这个有用的运算符也可以使用to encapsulate that boring prepare/bind/execute process in a simple function

hzbexzde

hzbexzde2#

是否预先调用bind_param,然后在进行后续查询时,只将数据设置到这些绑定变量中,而根本不与语句交互?
是。带有绑定变量的预准备语句的典型操作是:

prepare statement;
bind params;
for (some loop) {
    assign values to params;
    execute statement;
}

MySQLi中,你只有bind_param的选项,所以只能传递引用。如果你不介意改变接口,你可以切换到PDO,它有一个bindValue函数,它将处理值而不是引用。PDO还可以让你避免调用bind参数/通过简单地将一个值数组传递给execute调用语句,可以将所有值都传递给execute

kb5ga3dv

kb5ga3dv3#

从PHP 8.1开始,有一种新的方法可以将参数传递给mysqli的预处理语句,而不需要通过引用绑定。您可以在mysqli_stmt::execute()中将参数作为数组传递。

$stmt->execute([
    $my_class->get(FIELD_ONE),
    $my_class->get(FIELD_TWO),
]);

相关问题