将图像保存在mssql数据库中为varbinary(max),无需进行转换

时间:2018-09-04 16:50:48

标签: php sql-server laravel

我们公司的ERP软件将员工的图片作为斑点存储在我们的MSSQL数据库中。

我的任务是找到一种将图片存储到同一数据库表中的方式,使其可以在ERP程序中显示。

尝试#1

$content = file_get_contents('my_path\my_file.png');
INSERT INTO my_table VALUES (CAST('{$data}' AS varbinary(max)))

产生此错误:

SQLSTATE[IMSSP]: An error occurred translating the query string to UTF-16

检查我的编码:

mb_internal_encoding()是UTF-8,但是
mb_detect_encoding($content, 'UTF-8, ISO-8859-1', true)是ISO-8859-1。

尝试#2
将内容编码转换为UTF-8:

$content = file_get_contents('my_path\my_file.png');
$data = iconv('', 'UTF-8//TRANSLIT', $content);
INSERT INTO my_table VALUES (CAST('{$data}' AS varbinary(max)))

可以处理小的黑色正方形图像。
但是,在较小的 red 正方形图像上尝试此操作会产生以下错误:

iconv(): Detected an illegal character in input string

尝试#3 (a / b / c)
许多翻译或简单摆脱这些非法字符的方法:

$data = iconv('', 'UTF-8//IGNORE', $content);
$data = base64_encode($data);
$data = mb_convert_encoding($data, 'UTF-8', 'ISO-8859-1');

其中的允许我们将其保存到数据库中,但这对我们没有帮助,因为数据已更改并且ERP程序无法读取它们。

其他选项
我们已经考虑过
BulkColumn FROM OPENROWSET(Bulk‘ C: \temp\ nextup.jpg’, SINGLE_BLOB) AS BLOB
一种将文件插入数据库的方法,但是由于需要我们首先将文件存储在数据库服务器的磁盘上而不希望这样做而将其解散了。

问题
因此,问题仍然存在:如何在不修改内容的情况下将上传的图像文件放入我们的UTF-16 varbinary字段中?

2 个答案:

答案 0 :(得分:0)

这个简单的示例演示了如何将图像插入SQL Server的varbinary(max)列中,然后取回图像并将其保存到磁盘。示例使用PHP Driver for SQL Server。在您的情况下,最好使用参数化查询。

表格:

CREATE TABLE [dbo].[ImageTable] (
    [ImageData] varbinary(max) NULL
)

PHP:

<?php
# Connection
$server = 'server\instance,port';
$database = 'database';
$uid = 'user';
$pwd = 'password';
$cinfo = array(
    "Database" => $database,
    "UID" => $uid,
    "PWD" => $pwd
);
$conn = sqlsrv_connect($server, $cinfo);
if( $conn === false )
{
    echo "Error (sqlsrv_connect): ".print_r(sqlsrv_errors(), true);
    exit;
}

# Insert image using CONVERT()
$image = file_get_contents('image.jpg');
$sql = "INSERT INTO ImageTable (ImageData) VALUES (CONVERT(varbinary(max), ?))";
$params = array(
    array($image, SQLSRV_PARAM_IN)
);
$stmt = sqlsrv_query($conn, $sql, $params);
if ($stmt === false) {
    echo "Error (sqlsrv_query): ".print_r(sqlsrv_errors(), true);
    exit;
}

# Insert image using SQLSRV_PHPTYPE_STREAM(SQLSRV_ENC_BINARY)
$image = file_get_contents('image.jpg');
$sql = "INSERT INTO ImageTable (ImageData) VALUES (?)";
$params = array(
    array($image, SQLSRV_PARAM_IN, SQLSRV_PHPTYPE_STREAM(SQLSRV_ENC_BINARY))
);
if ($stmt === false) {
    echo "Error insert (sqlsrv_query): ".print_r(sqlsrv_errors(), true);
    exit;
}

# Get image from first row and save it again on disk. 
$sql = "SELECT ImageData FROM ImageTable";
$stmt = sqlsrv_query($conn, $sql);
if ($stmt === false) {
    echo "Error (sqlsrv_query): ".print_r(sqlsrv_errors(), true);
    exit;
}
if (sqlsrv_fetch($stmt)) {
    $image = sqlsrv_get_field($stmt, 0, SQLSRV_PHPTYPE_STREAM(SQLSRV_ENC_BINARY));
    file_put_contents('image2.jpg', $image);
}

# End
echo 'Image inserted.'
?>

答案 1 :(得分:-1)

只是一个想法。

<meta http-equiv="Content-Type" content="text/html; charset=utf-8" >

此外,您可以在连接到数据库后立即尝试执行此查询:

"SET NAMES 'utf8'"