gpt4 book ai didi

php - 绑定(bind)大插入或更新的更有效方法?

转载 作者:行者123 更新时间:2023-12-04 04:45:07 26 4
gpt4 key购买 nike

好的,我对绑定(bind)很陌生,这里有一些有效的代码。我从教程中学习了这种格式,但我想有更有效的方法可以做到这一点。在我的示例中,有 4 个名称,但实际上我将在我正在处理的项目中进行大量插入和更新,该项目将有 20 个左右的字段。我喜欢这种方法的清晰性,但很明显,当您谈论 20 个或更多字段时,它确实需要大量的空间。让我们先看看我的代码。

以下是它使用的功能:

// prepare the statement
public function query($query){
$this->stmt = $this->dbh->prepare($query);
}

public function bind($param, $value, $type = null){
if (is_null($type)) {
switch (true) {
case is_int($value):
$type = PDO::PARAM_INT;
break;
case is_bool($value):
$type = PDO::PARAM_BOOL;
break;
case is_null($value):
$type = PDO::PARAM_NULL;
break;
default:
$type = PDO::PARAM_STR;
}
}
// run the binding process
$this->stmt->bindValue($param, $value, $type);
}

// execute the prepared statement
public function execute(){
return $this->stmt->execute();
}

现在是实际的代码
$database->query("
INSERT INTO users(
user_name,
user_password_hash,
user_email,
user_activation_hash
)

VALUES(
:user_name,
:user_password_hash,
:user_email,
:user_activation_hash
)
");

// bind the values
$database->bind(":user_name", "$this->user_name");
$database->bind(":user_password_hash", "$this->user_password_hash");
$database->bind(":user_email", "$this->user_email");
$database->bind(":user_activation_hash", "$this->user_activation_hash");

// execute the statement and insert the values into the database
$database->execute();

它只是呼唤一个循环,特别是因为我有一个习惯叫帖子字段,输入字段,变量和占位符同名,不确定这是好事还是坏事,但我发现它在处理时对我很有帮助我会的大表格。

无论如何,我可以做这样的事情:
$placeholder_array = array(
"user_name" => "\$this->user_name",
"user_password_hash" => "\$this->user_password_hash",
"user_email" => "\$this->user_email",
"user_activation_hash" => "\$this->user_activation_hash"
);

// well use this copy to edit the array keys and keep original for the binding
$placeholder_copy = $placeholder_array;


// turn the array into a string i.e user_name, user_password_hash....
$fields = implode (", ", array_keys($placeholder_array));

// foreach to add : placeholder prefix for binding
foreach ($placeholder_copy as $key => $value){
$placeholder_copy [':'.$key] = $value;
unset($placeholder_copy[$key]);
}

// turn the copy array which has prefix :user_name into a string
$placeholders = implode (", ", array_keys($placeholder_copy));

$database->query("
INSERT INTO users($fields)
VALUES($placeholders)
");

// bind the values
foreach ($placeholder_copy as $bind_values => $value){
echo '$database->bind("'.$bind_values.'", "'.$value.'");' . "<br />";
}

// execute the statement and insert the values into the database
$database->execute();

然后我可以把它变成一个带有参数的函数,用于传递关联数组和表名,以使我的主代码更简洁。

现在想象一下,我将做任何数量的这些,因为我正在从事的项目涉及大量向用户提交数据的大型表单。我是 PDO 的新手并试图掌握它,因此可能有一种更简单的方式来构建这些类型的查询,我查看了 google 和 stackflow,但我并没有真正了解他们在做什么,所以我认为自己做一个会允许人们更好地向我解释发生了什么,我宁愿在开始我的项目时正确地做到这一点,而不是必须回去改变一切。那么有没有更好的方法或者这个可以吗?

非常感谢任何反馈,我很高兴现在我在这里接受了人们的建议并转向 PDO。

最佳答案

不,遗憾的是,PDO 对此事没有提供任何帮助。
然而,在我看来,您自己的方法也不是一种有效的方法。

首先,让我表明您的功能集毫无用处。我理解没有这样直接重写 API 函数。 PDO 已经在做所有这些事情。

使用原始 PDO,您可以获得更简洁的代码:

$stm  = $pdo->prepare("INSERT INTO users VALUES(NULL,?,?,?,?)");
$data = array($this->user_name,
$this->user_password_hash,
$this->user_email,
$this->user_activation_hash
);
$stm->execute($data);

关于您的动态查询构建,我觉得它太臃肿了 仍然不安全 .有些缺陷是
  • 没有必要打扰 ":named"占位符,因为它们应该是人类可读的,但没有人应该在这里阅读它们。更不用说 PDO 在发送到 mysql
  • 之前会将它们转换回 ?s
  • 对命名占位符的另一个反对意见 - 虽然 Mysql(以及 HTTP)可以让您在字段名称中有一个空格,但带有空格的占位符只会使您的查询崩溃。
  • 没有真正的好处在这段代码中,来自您的同名方法-您必须手工编写它们十多次 , 提个醒。
  • 但是,如果要使用它,您将没有白名单检查您的字段列表,可能是 严重的安全漏洞
  • 代码太多
  • 不支持UPDATE查询可能是 非常也很方便(如果您使用的是 mysql)
  • 当你把这段代码放入函数中时,你会陷入和其他人一样的糟糕境地,被拯救你的可能性所诱惑整两个字!

  • Here is my earlier approach for the matter :
    $allowed = array(
    "user_name", "user_password_hash", "user_email", "user_activation_hash"
    );
    $sql = "INSERT INTO users SET ".pdoSet($allowed, $values);
    $stmt = $dbh->prepare($sql);
    $stmt->execute($values);

    这里是 my current approach ,最好的(虽然使用 mysqli,而不是 PDO 实现),对数组数据使用自定义占位符:
    $placeholder_array = array(
    "user_name" => $this->user_name,
    "user_password_hash" => $this->user_password_hash,
    "user_email" => $this->user_email,
    "user_activation_hash" => $this->user_activation_hash
    );
    $db->query("INSERT INTO users SET ?u", $placeholder_array);

    或者,在表单字段和 SQL 列之间直接连接的情况下
    $allowed = array(
    "user_name", "user_password_hash", "user_email", "user_activation_hash"
    );
    $insert = $db->filterArray($_POST,$allowed);
    $db->query("INSERT INTO users SET ?u", $insert);

    这样让我用 INSERT IGNORE , INSERT DELAYED , INSERT.. ON DUPLICATE UPDATE , UPDATE , UPDATE带有连接和无数其他选项,支持 已满 SQL 语言。

    关于php - 绑定(bind)大插入或更新的更有效方法?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18326790/

    26 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com