Php 处理MSSQL数据库中的PNG图像时出现问题

Php 处理MSSQL数据库中的PNG图像时出现问题,php,sql-server,Php,Sql Server,我在保存/查看存储在MsSQL数据库中的PNG文件时遇到问题,如下所示: 我正在使用下一个代码获取文件: function manualDIRECTimg(){ ini_set('mssql.textlimit', '100000000'); ini_set('mssql.timeout', '9999'); ini_set('mssql.compatability_mode', '1'); ini_set('mssql.textsize', '100000000'); set_time_lim

我在保存/查看存储在MsSQL数据库中的PNG文件时遇到问题,如下所示:

我正在使用下一个代码获取文件:

function manualDIRECTimg(){
ini_set('mssql.textlimit', '100000000');
ini_set('mssql.timeout', '9999');
ini_set('mssql.compatability_mode', '1');
ini_set('mssql.textsize', '100000000');
set_time_limit(0);
header('Content-Type: image/png');

$codPRODUSerp = $_GET['id'];

$rowerp=mssql_fetch_array(mssql_query("EXECUTE spWEBSelectFoto ".$codPRODUSerp.", 1"));
$img=$rowerp['0'];  // The image is stored in column0

if($img!=''){

global $defaultPRODUCTimagePATH;
$imagineprodusTMP = $defaultPRODUCTimagePATH.'_0_TMPzz.jpg';

$file = fopen( $imagineprodusTMP, "w" );
fwrite( $file, $img);
fclose( $file);
readfile($imagineprodusTMP);
unlink($imagineprodusTMP);
}else{echo "There's no image found in the database";}

}
但输出是一个图像,在10%后被“剪切”。。。从MsSQL中提取JPG图像时不会发生此行为。。。有什么想法吗

我尝试过使用while循环,但最终会得到一个巨大的文件,这可能是因为在服务器端限制生效(脚本执行时间等)之前,它一直处于循环状态

即使我对$img字符串进行编码,在尝试PNG图像时仍然会得到相同的结果

同样,JPG/JPEG图像也可以。。。此问题仅在PNG上发生

p.S.实际文件如下: (一张确定的JPEG图像)

(糟糕的PNG…)

这不是原始(数据库)图像大小的问题,以kb为单位。它的大小以像素为单位,我有一个小的500x500px和一个1000x1000px的PNG,以同样的方式工作。我必须说,当使用它的实际软件正确输出时,存储的图像工作正常:
这里有几个问题,例如使用全局变量和不推荐的数据库函数,以及不必要的费力输出方法。以下是我的做法:

// database is passed as a parameter; assume it's PDO:
// $db = new PDO("mssql:host=db_host;dbname=db_name");
// ID is also passed to the function instead of using a global

function manualDIRECTimg($db, $id) {
    $sql    = "EXECUTE spWEBSelectFoto ?, 1";
    $params = array($id);
    $stmt   = $db->prepare($sql, $params);
    $stmt->exec();
    if ($img = $stmt->fetchColumn()) {
        // Are all of these images guaranteed to be PNG?
        // If not you'll need to adjust this as needed
        header("Content-Type: image/png");
        echo $img;
        return true;
    }    
    return false;
}
如果数据库获取一个图像的时间超过默认脚本超时时间, 把它交给数据库管理员。用户不会为一张图片等待60秒,禁用超时不是一个合理的方法


不过,一定要抛弃那些旧的mssql函数。它们早已被弃用,甚至在现代版本的PHP中都没有出现。

这里有几个问题,例如使用全局变量和弃用的数据库函数,以及不必要的费力输出方法。以下是我的做法:

// database is passed as a parameter; assume it's PDO:
// $db = new PDO("mssql:host=db_host;dbname=db_name");
// ID is also passed to the function instead of using a global

function manualDIRECTimg($db, $id) {
    $sql    = "EXECUTE spWEBSelectFoto ?, 1";
    $params = array($id);
    $stmt   = $db->prepare($sql, $params);
    $stmt->exec();
    if ($img = $stmt->fetchColumn()) {
        // Are all of these images guaranteed to be PNG?
        // If not you'll need to adjust this as needed
        header("Content-Type: image/png");
        echo $img;
        return true;
    }    
    return false;
}
如果数据库获取一个图像的时间超过默认脚本超时时间, 把它交给数据库管理员。用户不会为一张图片等待60秒,禁用超时不是一个合理的方法


不过,一定要抛弃那些旧的mssql函数。它们早就被弃用了,甚至在现代版本的PHP中都没有出现。

由于这似乎是一个SQL server如何传递数据的问题,我已设法对miken32的代码进行了一些更改,并最终得出以下结论:

function manualPDOdirectIMG() {
set_time_limit(0);
$codPRODUSerp = $_GET['id'];
$db = new PDO("dblib:host=xxx.xxx.xxx.xxx;dbname=DATABASE", "USER", "PWD");
    $sql    = "EXECUTE spWEBSelectFoto ".$codPRODUSerp.", 1";
    $stmt   = $db->prepare($sql);
    $stmt->execute();
    if ($img = $stmt->fetchColumn()) {
        header("Content-Type: image/png");
        echo $img;
        return true;
    }    
    return false;
}
同样的“切割”图像结果

你们所有人的帮助让我感到很惊讶

至于我的问题,答案是:


在本例中,这是远程MSSQL错误配置的问题。

由于这似乎是SQL server如何传递数据的问题,我已设法对miken32的代码进行了一些更改,并最终得出以下结论:

function manualPDOdirectIMG() {
set_time_limit(0);
$codPRODUSerp = $_GET['id'];
$db = new PDO("dblib:host=xxx.xxx.xxx.xxx;dbname=DATABASE", "USER", "PWD");
    $sql    = "EXECUTE spWEBSelectFoto ".$codPRODUSerp.", 1";
    $stmt   = $db->prepare($sql);
    $stmt->execute();
    if ($img = $stmt->fetchColumn()) {
        header("Content-Type: image/png");
        echo $img;
        return true;
    }    
    return false;
}
同样的“切割”图像结果

你们所有人的帮助让我感到很惊讶

至于我的问题,答案是:


在本例中,这是远程MSSQL错误配置的问题。

经过一段时间,我发现了导致图像被截断的问题,在我的初始测试中,我使用了一个简单的

ini_集合('mssql.textlimit','5242880'); ini_集合('mssql.textsize','5242880')

这不会产生任何影响,因此传输的数据在60KB后被截断。。。经过一些研究,我发现手动设置

mssql_查询(“设置文本大小5242880”)

在实际的mssql_fetch_数组查询之前,解决了我的问题! 因此,指示MSSQL覆盖TEXTLIMIT和TEXTSIZE可以确保sql和php之间的完整数据传输


谢谢大家的智慧

过了一段时间,我发现了导致图像被截断的问题,在我的初始测试中,我使用了一个简单的

ini_集合('mssql.textlimit','5242880'); ini_集合('mssql.textsize','5242880')

这不会产生任何影响,因此传输的数据在60KB后被截断。。。经过一些研究,我发现手动设置

mssql_查询(“设置文本大小5242880”)

在实际的mssql_fetch_数组查询之前,解决了我的问题! 因此,指示MSSQL覆盖TEXTLIMIT和TEXTSIZE可以确保sql和php之间的完整数据传输


谢谢大家的智慧

您在SQL Server中存储的字段的数据类型和长度是多少?很抱歉,您还需要多帮我一点忙,我对PHP-MSSQL完全不熟悉。。。在我的案例中使用的ERP软件的开发人员给了我一组指令,这些指令具有从MS SQL server提取数据的功能,在本例中,执行spWEBSelectFoto“$codPRODUSerp.”,1。。。其中codPRODUSerp是唯一标识符,1是一组10中的第一个映像(在我的示例中,仅使用文件numer1),我不知道如何获取存储在单元格中的数据类型或长度,我使用它浏览MySQL、MSSQL服务器。。。虽然我保存了管理员为PNG制作的“导出”。。。如果有帮助(以CSV作为分隔符),您能否在SQL server上运行以下命令并显示结果(无引号)?“sp_helptext spWEBSelectFoto”发生这种情况是因为您的数据库堆栈无法处理超过64K(2^16字节)的数据;数据在该点被切断。JPEG图像符合此限制,PNG图像不符合此限制。至于到底哪里失败了,我不能说。
mssql.*
函数非常古老,依赖于更古老的access库。请尝试提供的库。您在SQL Server中存储的字段的数据类型和长度是多少?很抱歉,您还需要多帮我一点忙,我对PHP-MSSQL完全不熟悉。。。在我的案例中使用的ERP软件的开发人员给了我一组指令,这些指令具有从MS SQL server提取数据的功能,在本例中,执行spWEBSelectFoto“$codPRODUSerp.”,1。。。其中codPRODUSerp是唯一标识符,1是一组10中的第一个映像(在我的示例中,仅使用文件numer1),我不知道如何获取存储在单元格中的数据类型或长度,我使用它浏览MySQL、MSSQL服务器。。。虽然我保存了管理员为PNG制作的“导出”。。。如果有帮助(CSV作为分隔符)Ca