使用imagecreatefromjpeg()上传jpg图像文件的问题

问题描述 投票:0回答:1

当我尝试对手机中的某些 jpg 文件使用 imagecreatefromjpeg() 到我的网站时,我遇到一些问题,无法验证它们是实际的 jpg 图像。

我尝试时遇到的错误:

PHP Warning:  imagecreatefromjpeg(): gd-jpeg: JPEG library reports unrecoverable error: Not a JPEG file: starts with 0x00 0x00
PHP Warning:  imagecreatefromjpeg(): "/tmp/phpBGoiQg" is not a valid JPEG file

到目前为止,我自己能弄清楚的是,一些错误的照片的最大区别是这些照片是在你编辑后来自 Instagram 的,这个问题与以下任一方面有关:元数据、编码或压缩。如果我在手机上编辑它们并再次保存图像,它会上传得很好,但这就是问题所在。

我找不到解决此问题的真正解决方案,因此我的用户不必担心编辑照片以上传它们。如果有人能给我指出正确的方向,我很乐意自己找出答案。

目前,我设置了一项检查,仅通知用户特定照片已被跳过。但我真的希望能够以某种方式修复它们?

if (exif_imagetype($file_temp_name) === IMAGETYPE_JPEG) {
//do resize, else skip and report issue.
}

更新

因此,在处理完此问题并弄清楚 jpg 似乎确实是 jpg2000 图像(由于十六进制为 00 00 00 开始)后,我一直在尝试弄清楚如何通过 php 上传来处理它。

我尝试了一些 imagick 的东西,比如 exec() 函数来尝试转换图像,并且还尝试重新保存为不同的格式。没有运气。

我不知道从这里该去哪里,因为我找不到任何类似的情况。也许我不擅长谷歌搜索,但我真的很感激任何指点。

代码片段:

case 'image/jpeg': //case 'image/pjpeg':
if (exif_imagetype($file_temp_name) === IMAGETYPE_JPEG) {
    $image_res = imagecreatefromjpeg($file_temp_name);
} else {
    // Check for the JPEG 2000 magic number (00 00 00)
    $fileContents = file_get_contents($file_temp_name);
    if (substr($fileContents, 0, 3) === "\x00\x00\x00") {
        $uploadedFile = $file_temp_name;
        $outputFilename = "NEW-$file_name";

        if (file_exists($uploadedFile)) {
            $command = "convert $uploadedFile $outputFilename";
            exec($command);

            if (file_exists($outputFilename)) {
                $_report .= "Image conversion successful! ";

                $image_res = imagecreatefromjpeg($outputFilename);
            } else {
                $_report .= "Image conversion failed. [$uploadedFile to $outputFilename] ";

                exec($command, $output, $returnCode);
                $_report .= "Error: " . implode("\n", $output); // Log the error messages
            }
        } else {
            $_report .= "Image doesn't exist. [$uploadedFile to $outputFilename] ";
        }
    }
}
break;
php jpeg
1个回答
1
投票
某些程序用于识别 JPEG 文件的

签名FF D8 FF

 开头。您可以验证是否使用
十六进制编辑器打开 JPEG 文件。如果您的文件确实以 00 00
 开头(值得检查),那么它要么已损坏,要么根本不是 JPEG 图片。它可能是一个 
JPEG 2000 文件,尽管名称如此,但实际上是不同的格式:

00 00 00 0C 6A 50 20 20 0D 0A 87 0A
值得注意的是,一些代理会自动以不同格式(例如 webp)重新编码原始文件以节省带宽但保留原始名称,因此您最终会得到一个名为 

foo.jpg

 的文件,它实际上根本不是 JPEG。

© www.soinside.com 2019 - 2024. All rights reserved.