【问题标题】:How to output blob data (not image) from mysql to php?如何将 blob 数据(不是图像)从 mysql 输出到 php?
【发布时间】:2016-03-21 19:25:46
【问题描述】:

我正在尝试以 BLOB 格式输出存储在表中的加密数据,但它不起作用。我使用准备好的语句插入它,当我在 mysql 命令行客户端上检查时,它显示条目已被记录,但 blob 字段为空,并且每个其他字段都有一些值。另外blob字段不能为空,因为我在建表的时候已经指定了,所以我认为命令行不能显示blob字段数据。

所以使用 php,我尝试返回 base64_encode 字段的 base64_encode 值,但没有帮助。它仍然是空的。我该怎么办?

P.S.:这不是图像,它是使用 AES-256 加密的文本。

$stmt = $conn->prepare("INSERT INTO data_store (eid,  ekey, ecipher) VALUES (?, ?, ?)");
if($stmt->bind_param("sbb", $eid, $ekey, $ecipher)) {
echo "Successful";

}

// set parameters and execute
$eid=$postedID;
$ekey=$postedKey;
$ecipher=$postedCipher;

$stmt->execute();
$stmt->close();
$conn->close();

之后,我尝试返回对其进行编码的 BLOB 值,但它什么也不返回,而作为字符串的 id 的值确实显示出来了。我该如何解决这个问题?我需要对数据进行加密,然后将其解密为网站的明文。

我如何实现这一目标? 非常感谢。

P.S.:我还没有尝试解密,我需要先加密的值,所以建议先解密不会很有帮助。

表格是这样的-

+-------------+---------------------+------+-----+---------+----------------+
| Field       | Type                | Null | Key | Default | Extra          |
+-------------+---------------------+------+-----+---------+----------------+
| eid         | varchar(255)        | NO   | PRI | NULL    |                |
| ekey        | blob                | NO   |     | NULL    |                |
| ecipher     | blob                | NO   |     | NULL    |                |
+-------------+---------------------+------+-----+---------+----------------+

【问题讨论】:

  • 这个表的架构是什么? SHOW CREATE TABLE 将提供详细信息。您要在该列中保存多少数据?
  • 我上面已经给出了表格描述。
  • 请记住BLOB 仅保存 65KB 的数据。如果您需要更多,您需要LONGBLOB
  • 您是否考虑过插入时 $ekey 和 $ecipher 可能为空的可能性?空字符串“”不为空。
  • 不,我想我找到了问题所在。变量不为空

标签: php mysql encryption blob


【解决方案1】:

当我将参数更改为string“s”时问题解决了,这似乎工作正常,因为我保存数据的变量是字符串,所以它适合。

所以修正后的代码是:

$stmt = $conn->prepare("INSERT INTO data_store (eid,  ekey, ecipher) VALUES (?, ?, ?)");
if($stmt->bind_param("sss", $eid, $ekey, $ecipher)) {
echo "Successful";

我并不是说这是一个完美的解决方案,但它现在似乎解决了我的问题,如果有人提出一种在 php 中使用 blob 而不是 string 的方法,我将非常有帮助。谢谢。

【讨论】:

  • 很奇怪。文档说 b 应该适用于 blob。 php.net/manual/en/mysqli-stmt.bind-param.php
  • 没错,这就是为什么我把'b'放在首位,记录似乎是空的。字符串现在似乎工作正常,但我认为既然它有 b 用于 blob,肯定有一个很好的理由,我想知道该怎么做。 @Phil_1984_
【解决方案2】:

指定b 告诉mysqli 将数据以单独的数据包发送到服务器。

Documentation here

但是,文档没有详细说明您应该如何指定数据包数据。有人会假设,与其他类型一样,您应该只设置一个包含数据的引用变量。原来你需要使用send_long_data

使用此功能,您实际上可以控制每个数据块,因此您需要确保不会发送太大而导致服务器无法处理的数据包。

试试这样的

$stmt = $conn->prepare("INSERT INTO data_store (eid,  ekey, ecipher) VALUES (?, ?, ?)");

//Initialise variables
$eid = $postedID;
$ekey = NULL;
$ecipher = NULL;

if($stmt->bind_param("sbb", $eid, $ekey, $ecipher)) {

    // Send blobs
    $ekey_chunks = str_split($postedKey, 8192);
    foreach ($ekey_chunks as $chunk) {
        $stmt->send_long_data(1, $chunk);
    }

    $ecipher_chunks = str_split($postedCipher, 8192);
    foreach ($ecipher_chunks as $chunk) {
        $stmt->send_long_data(2, $chunk);
    }

    $stmt->execute();
    $stmt->close();
}

$conn->close();

来源this blog

【讨论】:

  • 我的包大小有问题,如何根据需要重复发送?
  • 该代码中的 foreach 循环应自动以 8K 数据包的形式发送分块数据。对于默认设置 1MB,这应该足够小。
  • 我的max_packet 大小设置为1024 MB,它不会自动发送我的数据包,输出时的数据不完整。
  • 不知道是否有帮助,但我在答案的底部添加了来源。
  • 我认为str_split 是在这里使用的错误函数。
猜你喜欢
  • 2010-10-23
  • 2017-08-16
  • 1970-01-01
  • 1970-01-01
  • 2011-09-12
  • 2020-07-20
  • 1970-01-01
  • 2012-03-27
  • 1970-01-01
相关资源
最近更新 更多