在 PHP 中检查上传表单中的文件扩展名

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/10456113/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-24 22:12:15  来源:igfitidea点击:

Check file extension in upload form in PHP

phpfile-upload

提问by BBKing

I check the file extension for upload or not uploaded. My example methods worked, but now I need to understand if my methods (using pathinfo) is true. Is there another better and faster way?

我检查上传或未上传的文件扩展名。我的示例方法有效,但现在我需要了解我的方法(使用pathinfo)是否正确。还有另一种更好更快的方法吗?

$filename = $_FILES['video_file']['name'];
$ext = pathinfo($filename, PATHINFO_EXTENSION);
if ($ext !== 'gif' || $ext !== 'png' || $ext !== 'jpg') {
    echo 'error';
}

回答by Baba

Using if( $ext !== 'gif') might not be efficient. What if you allow like 20 different extensions?

使用if( $ext !== 'gif') 可能效率不高。如果您允许 20 个不同的扩展怎么办?

Try:

尝试:

$allowed = array('gif', 'png', 'jpg');
$filename = $_FILES['video_file']['name'];
$ext = pathinfo($filename, PATHINFO_EXTENSION);
if (!in_array($ext, $allowed)) {
    echo 'error';
}

回答by Reza S

Checking the file extension is not considered best practice. The preferred method of accomplishing this task is by checking the files MIME type.

检查文件扩展名不被视为最佳实践。完成此任务的首选方法是检查文件MIME 类型

From PHP:

来自 PHP:

<?php
    $finfo = finfo_open(FILEINFO_MIME_TYPE); // Return MIME type
    foreach (glob("*") as $filename) {
        echo finfo_file($finfo, $filename) . "\n";
    }
    finfo_close($finfo);
?>

The above example will output something similar to which you should be checking.

上面的示例将输出类似于您应该检查的内容。

text/html
image/gif
application/vnd.ms-excel

Although MIME types can also be tricked (edit the first few bytes of a file and modify the magic numbers), it's harder than editing a filename. So you can never be 100% sure what that file type actually is, and care should be taken about handling files uploaded/emailed by your users.

尽管 MIME 类型也可以被欺骗(编辑文件的前几个字节并修改幻数),但它比编辑文件名更难。因此,您永远无法 100% 确定该文件类型实际上是什么,并且应注意处理用户上传/通过电子邮件发送的文件。

回答by Hyman

Personally,I prefer to use preg_match()function:

就个人而言,我更喜欢使用preg_match()函数:

if(preg_match("/\.(gif|png|jpg)$/", $filename))

or in_array()

in_array()

$exts = array('gif', 'png', 'jpg'); 
if(in_array(end(explode('.', $filename)), $exts)

With in_array()can be useful if you have a lot of extensions to validate and perfomance question. Another way to validade file images: you can use @imagecreatefrom*(), if the function fails, this mean the image is not valid.

in_array()如果您有很多扩展来验证和性能问题,With会很有用。另一种验证文件图像的方法:您可以使用@imagecreatefrom*(),如果函数失败,这意味着图像无效。

For example:

例如:

function testimage($path)
{
   if(!preg_match("/\.(png|jpg|gif)$/",$path,$ext)) return 0;
   $ret = null;
   switch($ext)
   {
       case 'png': $ret = @imagecreatefrompng($path); break;
       case 'jpeg': $ret = @imagecreatefromjpeg($path); break;
       // ...
       default: $ret = 0;
   }

   return $ret;
}

then:

然后:

$valid = testimage('foo.png');

Assuming that foo.pngis a PHP-script file with .pngextension, the above function fails. It can avoid attacks like shell update and LFI.

假设这foo.png是一个带有.png扩展名的 PHP 脚本文件,上述函数将失败。它可以避免 shell update 和LFI等攻击。

回答by Conrad Warhol

pathinfo is cool but your code can be improved:

pathinfo 很酷,但您的代码可以改进:

$filename = $_FILES['video_file']['name'];
$ext = pathinfo($filename, PATHINFO_EXTENSION);
$allowed = array('jpg','png','gif');
if( ! in_array( $ext, $allowed ) ) {echo 'error';}

Of course simply checking the extension of the filename would not guarantee the file type as a valid image. You may consider using a function like getimagesizeto validate uploaded image files.

当然,仅检查文件名的扩展名并不能保证文件类型为有效图像。您可以考虑使用诸如getimagesize验证上传的图像文件之类的功能。

回答by priyam

file type can be checked in other ways also. I believe this is the easiest way to check the uploaded file type.. if u are dealing with an image file then go for the following code. if you are dealing with a video file then replace the image check with a video check in the if block.. have fun

也可以通过其他方式检查文件类型。我相信这是检查上传文件类型的最简单方法。如果您正在处理图像文件,请使用以下代码。如果您正在处理视频文件,则在 if 块中用视频检查替换图像检查.. 玩得开心

     $img_up = $_FILES['video_file']['type'];
$img_up_type = explode("/", $img_up);
$img_up_type_firstpart = $img_up_type[0];

if($img_up_type_firstpart == "image") { // image is the image file type, you can deal with video if you need to check video file type

/* do your logical code */ }

回答by liz

Not sure if this would have a faster computational time, but another option...

不确定这是否会有更快的计算时间,但另一种选择......

$acceptedFormats = array('gif', 'png', 'jpg');

if(!in_array(pathinfo($filename, PATHINFO_EXTENSION), $acceptedFormats))) {
    echo 'error';
}

回答by Onwu Bishop Gideon

i think this might work for you

我认为这可能对你有用

//<?php
    //checks file extension for images only
    $allowed =  array('gif','png' ,'jpg');
    $file = $_FILES['file']['name'];
    $ext = pathinfo($file, PATHINFO_EXTENSION);
        if(!in_array($ext,$allowed) ) 
            { 
//?>
<script>
       alert('file extension not allowed');
       window.location.href='some_link.php?file_type_not_allowed_error';
</script>

//<?php
exit(0);
    }
//?>

回答by Rotimi

To properly achieve this, you'd be better off by checking the mime type.

为了正确实现这一点,您最好检查一下 mime 类型。

function get_mime($file) {
  if (function_exists("finfo_file")) {
    $finfo = finfo_open(FILEINFO_MIME_TYPE); // return mime type ala mimetype extension
    $mime = finfo_file($finfo, $file);
    finfo_close($finfo);
    return $mime;
  } else if (function_exists("mime_content_type")) {
    return mime_content_type($file);
  } else if (!stristr(ini_get("disable_functions"), "shell_exec")) {
    // http://stackoverflow.com/a/134930/1593459
    $file = escapeshellarg($file);
    $mime = shell_exec("file -bi " . $file);
    return $mime;
  } else {
    return false;
  }
}
//pass the file name as
echo(get_mime($_FILES['file_name']['tmp_name']));

回答by Rotimi

How to validate file extension (jpg/jpeg only) on a form before upload takes place. A variation on another posted answer here with an included data filter which may be useful when evaluating other posted form values. Note: error is left blank if empty as this was an option for my users, not a requirement.

如何在上传之前验证表单上的文件扩展名(仅限 jpg/jpeg)。此处发布的另一个答案的变体,其中包含数据过滤器,这在评估其他发布的表单值时可能很有用。注意:如果为空,则错误为空,因为这是我的用户的一个选项,而不是一个要求。

<?php
if(isset($_POST['save'])) {

//Validate image
if (empty($_POST["image"])) {
$imageError = "";
} else {
$image = test_input($_POST["image"]);
$allowed =  array('jpeg','jpg');
$ext = pathinfo($image, PATHINFO_EXTENSION);
if(!in_array($ext,$allowed) ) {
$imageError = "jpeg only";
}
}

}

// Validate data
function test_input($data) {
$data = trim($data);
$data = stripslashes($data);
$data = htmlspecialchars($data);
return $data;
}
<?

Your html will look something like this;

你的 html 看起来像这样;

<html>
<head>
</head>

<body>
<!-- Validate -->
<?php include_once ('validate.php'); ?>

<!-- Form -->
<form method="post" action="">

<!-- Image -->
<p>Image <?php echo $imageError; ?></p>
<input type="file" name="image" value="<?php echo $image; ?>" />

<p><input type="submit" name="save" value="SAVE" /></p>
</form>

</body>
</html>

回答by Sajjad Asaad

use this function

使用这个功能

 function check_image_extension($image){

        $images_extentions = array("jpg","JPG","jpeg","JPEG","png","PNG");

        $image_parts = explode(".",$image);

        $image_end_part = end($image_parts);

        if(in_array($image_end_part,$images_extentions ) == true){

            return time() . "." . $image_end_part;


        }else{

            return false;
        }


    }