【问题标题】:Validate base64 encoded image from mime byte从 mime 字节验证 base64 编码图像
【发布时间】:2018-04-01 03:39:06
【问题描述】:

我正在尝试从 mime 类型字节验证一些 Base64 编码的图像,除了 .png 文件之外,它们都在正确验证

png字节签名为89 50 4E 47 0D 0A 1A 0A

我有一个允许的字节签名数组

    'imageBytes'    => [
        "jpeg"  => "FFD8",
        "png"   => "89504E470D0A1A0A",
        "gif"   => "474946",
        "bmp"   => "424D"
    ],

我使用允许的数组将 base64 编码图像传递给此函数

    public function checkImageMimeBytes(string $imageData, array $imgByteArray) : string
        {
            if (!is_array($imgByteArray) || is_null($imgByteArray) || empty($imgByteArray)) {
                throw new \LogicException('undefined image security config');
            }

            foreach ($imgByteArray as $mime => $hexBytes) {
                $bytes = $this->getBytesFromHexString($hexBytes);
                if (substr($imageData, 0, strlen($bytes)) == $bytes) {
                    return $mime;
                } else {
                    throw new SecurityException;
                }
            }
            throw new \LogicException('Invalid Mime Byte');
        }

这个函数从十六进制字符串中获取字节

        public function getBytesFromHexString(string $hexData) : string
        {

            for ($count = 0; $count < strlen($hexData); $count += 2) {
                $bytes[] = chr(hexdec(substr($hexData, $count, 2)));
            }

            if (!isset($bytes) || !is_array($bytes) || empty($bytes) || is_null($bytes)) {
                throw new \LogicException;
            }

            return implode($bytes);
        }

在测试时,它总是会为 .png 图像引发安全异常

关于如何解决这个问题的任何信息?

添加了测试图片

编辑: 使用 FileReader() 从 javascript 编码前端

     let reader = new FileReader()
     reader.readAsDataURL(file)
        reader.onloadend = (readEvent) => {
          this.$emit('imageUploadReady', readEvent.currentTarget.result)
        }

【问题讨论】:

  • 我们不知道您的数据是什么样的。
  • 你试过使用base64_encode和base64_decode吗?
  • 为什么我需要对其进行编码和解码?我用javascript对其客户端进行编码并在服务器端对其进行解码?
  • 添加了测试图片
  • 图像没有帮助。显示数据。

标签: php security image-processing encoding base64


【解决方案1】:

简介

和你一样,我有一个 base64 图像 ($imageBase64Str)。

我需要获取这张图片的 mime 类型,它必须是有效的。

回答

输入:$imageBase64Str

function imgMime($imgBytes){
    if(is_null($imgBytes)){
        return(false);
    }
    if(strlen($imgBytes)<12){
        return(false);
    }
    $finfo = new finfo(FILEINFO_MIME_TYPE);
    $mime=$finfo->buffer($imgBytes);
    if(strncmp($mime, "image/", 6) != 0){
        return(false);
    }
    return($mime);
}

$imageBytes=base64_decode($imageBase64Str,true);
if(!$imageBytes){
    throw new Exception("cannot decode image base64");
}
$imageMime=imgMime($imageBytes);
if(!$imageMime){
    throw new Exception("cannot recognize image mime");
}

如果您希望将图像类型限制为比exif_imagetype 函数识别的更窄的一组MIME,您可以根据image_type_to_mime_type 函数返回的$imageMime 引发错误。像这样的:

$allowedMimes=["image/jpeg","image/png","image/gif","image/bmp"];
if(!in_array($imageMime,$allowedMimes,true)){
    throw new Exception("image mime not allowed: ".$imageMime);
}

结果

当我将$imageBase64Str 设置为从your example 提取的iVBORw0KGgoAAAANSUhEUgAAAQwAAABuCAYAAADSxy12AAAgAElEQVR4XtV9267jSpJd8CaSukvVv+LpA...Vxt5tFRObQnEEvPk4fVOUFg5tz2709kx8kLz9c0yWJqDQQqfvvSxPV0wVSYRMAAAAASUVORK5CYII= 时,我得到了一个有效的image/png mime。但是,我没有得到酷炫的黑白匿名奴才牛仔图像,而是下面的紫色/紫色旋转方块:

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-01-31
    • 2021-02-23
    • 1970-01-01
    • 1970-01-01
    • 2019-03-13
    • 2016-12-26
    相关资源
    最近更新 更多