Как мне найти mime-тип файла с php?

Итак, у меня есть файл index.php, который должен обрабатывать много разных типов файлов. как я могу угадать тип файла на основе REQUEST_URI.

Если я запрашиваю http://site/image.jpg, и все запросы перенаправляются через index.php, это выглядит так

<?php
   include('/www/site'.$_SERVER['REQUEST_URI']);
?>

Как мне заставить это работать правильно?

Должен ли я тестировать на основе расширения запрошенного файла или есть способ узнать тип файла?

Вы можете перефразировать свой вопрос? Я надеюсь, что вы действительно не запускаете такой код на своем веб-сайте.

Till 25.09.2008 23:47

Нет, конечно, на самом деле это не так. Это был лучший способ донести мысль (так я думал).

Issac Kelly 26.09.2008 03:35
Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Symfony Station Communiqué - 7 июля 2023 г
Symfony Station Communiqué - 7 июля 2023 г
Это коммюнике первоначально появилось на Symfony Station .
Оживление вашего приложения Laravel: Понимание режима обслуживания
Оживление вашего приложения Laravel: Понимание режима обслуживания
Здравствуйте, разработчики! В сегодняшней статье мы рассмотрим важный аспект управления приложениями, который часто упускается из виду в суете...
Установка и настройка Nginx и PHP на Ubuntu-сервере
Установка и настройка Nginx и PHP на Ubuntu-сервере
В этот раз я сделаю руководство по установке и настройке nginx и php на Ubuntu OS.
Коллекции в Laravel более простым способом
Коллекции в Laravel более простым способом
Привет, читатели, сегодня мы узнаем о коллекциях. В Laravel коллекции - это способ манипулировать массивами и играть с массивами данных. Благодаря...
Как установить PHP на Mac
Как установить PHP на Mac
PHP - это популярный язык программирования, который используется для разработки веб-приложений. Если вы используете Mac и хотите разрабатывать...
49
2
110 608
13
Перейти к ответу Данный вопрос помечен как решенный

Ответы 13

Ответ принят как подходящий

Если вы уверены, что когда-либо работаете только с изображениями, вы можете проверить функцию PHP getimagesize ()exif_imagetype (), которая пытается вернуть mime-тип изображения.

Если вы не возражаете против внешних зависимостей, вы также можете проверить отличную библиотеку getID3, которая может определять mime-тип многих различных типов файлов.

Наконец, вы можете проверить функцию mime_content_type (), но она устарела для расширения Fileinfo PECL.

Вместо getimagesize () вызовите exif_imagetype (): us3.php.net/manual/en/function.exif-imagetype.php. Он предоставляет ту же информацию без потери производительности, связанной с выполнением других действий.

Xiong Chiamiov 17.01.2011 00:36

«Возвращаемое значение - это то же значение, которое getimagesize () возвращает в индексе 2, но exif_imagetype () работает намного быстрее». из приведенной выше ссылки, как опубликовал @XiongChiamiov

Tian Loon 28.01.2014 23:49

@leek: как получить mime-тип для любого контента .... stackoverflow.com/questions/21847663/…

Hitesh 21.02.2014 13:31

Я не использовал его, но есть Расширение PECL для получения mimetype файла. Официальная документация для него находится в руководство.

В зависимости от ваших целей расширение файла может быть приемлемым, но оно не очень надежно, поскольку его так легко изменить.

Согласно руководству по php, функция finfo-файл - лучший способ сделать это. Однако вам нужно будет установить расширение FileInfo PECL.

Если расширение не является вариантом, вы можете использовать устаревшую функцию mime_content_type.

Также. Расширение Fileinfo включено по умолчанию, начиная с PHP 5.3.

Stann 23.05.2011 22:02

@Stann Нет, это не так! PHP Version 5.4.7 + Fatal error: Call to undefined function finfo_open() in C:\XAMPP\htdocs\....

trejder 10.09.2013 16:53

если вы имеете дело только с изображениями, вы можете использовать функцию [getimagesize()][1], которая содержит всевозможную информацию об изображении, включая тип.

Более общий подход заключался бы в использовании расширения FileInfo от PECL. Документацию PHP для этого расширения можно найти по адресу: http://us.php.net/manual/en/ref.fileinfo.php

У некоторых людей есть серьезные жалобы на это расширение ... поэтому, если вы столкнетесь с серьезными проблемами или не можете установить расширение по какой-либо причине, вы можете проверить устаревшую функцию mime_content_type()

mime_content_type () устарел, поэтому вы не сможете рассчитывать на его работу в будущем. Существует расширение PECL "fileinfo", но я не слышал о нем хорошего.

Если вы работаете на сервере * nix, вы можете сделать следующее, что у меня отлично сработало:

$file = escapeshellarg( $filename );
$mime = shell_exec("file -bi " . $file);
$filename should probably include the absolute path.

Команда file может быть отключена (на общих хостах) по соображениям безопасности.

SAMPro 09.12.2013 21:33
Я не слышал об этом хорошего. - Would nice if we could read what you've heard ;)
yckart 08.07.2016 17:15

Вы говорите, что mime_content_type устарел на основании чего? Не кажется устаревшим согласно php.net/manual/en/function.mime-content-type.php.

Jānis Elmeris 03.06.2020 21:32

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;
  }
}

Для меня ничего из этого не работает - mime_content_type устарел, finfo не установлен, а shell_exec не разрешен.

я получил очень хорошие результаты, используя пользовательскую функцию из http://php.net/manual/de/function.mime-content-type.php @ '' Джон Дот Ховард на prismmg dot com 26 октября 2009 г., 03:43 ''

function get_mime_type($filename, $mimePath = '../etc') { ...

который не использует finfo, exec или устаревшую функцию

хорошо работает также с удаленными ресурсами!

Эта функция была устарел задолго до того, как вы написали этот ответ, поэтому предлагать это решение бессмысленно.

trejder 10.09.2013 17:32

Если вы работаете только с изображениями и вам нужен MIME-тип (например, для заголовков), то это самый быстрый и прямой ответ:

$file = 'path/to/image.jpg';
$image_mime = image_type_to_mime_type(exif_imagetype($file));

Он будет выводить настоящий mime-тип изображения, даже если вы переименуете файл изображения

Мне на самом деле надоело отсутствие в PHP методов сниффинга стандарт MIME. Установите fileinfo ... Используйте устаревшие функции ... Ох уж эти работы, но только для изображений! Мне это надоело, поэтому я провел небольшое исследование и нашел Спецификация WHATWG Mimesniffing - хотя я считаю, что это все еще черновик спецификации.

В любом случае, используя эту спецификацию, я смог реализовать mimesniffer на PHP. Производительность не проблема. Фактически, на моей скромной машине я смог открыть и проанализировать тысячи файлов до того, как истекло время ожидания PHP.

Вот MimeReader класс.

require_once("MimeReader.php");

$mime = new MimeReader(<YOUR FILE PATH>);
$mime_type_string = $mime->getType();     // "image/jpeg" etc.

Звучит здорово! Сейчас это Living Standard — Last Updated 11 June 2013, так что не черновик. Удалось ли вам загрузить / поделиться где-то свой PHP-код с помощью этого?

trejder 10.09.2013 16:56

Привет трейдер. Спасибо за это обновление и извините за поздний ответ. Вы можете найти все мои проекты на моем мини-сайте (я знаю, это немного). Я, наверное, выложу его на github, если он станет популярным. Все в проектах. Он выпущен в общественное достояние, поэтому не стесняйтесь очищать код (он нужен!) Или иным образом изменять по своему усмотрению. shane.social-library.org

Shane 20.09.2013 06:01

Спасибо! Я обязательно посмотрю на это! :]

trejder 20.09.2013 13:10

Привет, Сайед Кариб, спасибо, что сообщили мне. Я обновил ссылку на github, как вы предложили.

Shane 04.08.2015 06:00

У этого класса нет типа CSV.

Jarosław Osmólski 24.09.2015 14:38

Правильно - это потому, что файлы CSV представляют собой простой текст, это работает исключительно с магическим числом, так что с точки зрения класса это простой текст. Вы должны иметь возможность проверить эти простые текстовые файлы, если хотите различать, или, пожалуйста, создайте вилку. Спасибо

Shane 29.09.2015 06:47

@Shane, не работает ... Получаю ошибку: Fatal error: Call to undefined method MimeReader::get_type() in /home/***/public_html/editor.php on line 189

Yaakov Ainspan 08.09.2016 17:32

Привет, хитрости для Интернета, сколько лет версии, которую вы используете? Если у вас есть последняя копия, API немного изменился с snake_case на camelCase, поэтому теперь подходящей функцией является getType. Извините за путаницу!

Shane 09.09.2016 05:59

mime_content_type() кажется подходящим вариантом, несмотря на приведенные выше комментарии о том, что он устарел. Это не так - или, по крайней мере, эта версия mime_content_type() не устарела, согласно http://php.net/manual/en/function.mime-content-type.php. Это часть расширения FileInfo, но в документации PHP теперь говорится, что он включен по умолчанию, начиная с PHP 5.3.0.

Если вы используете Linux и у вас есть расширение, вы можете просто прочитать тип MIME из /etc/mime.types, создав массив хешей. Затем вы можете сохранить это в памяти и просто вызвать MIME по ключу массива :)

/**
 * Helper function to extract all mime types from the default Linux /etc/mime.types
 */
function get_mime_types() {
    $mime_types = array();
    if (
        file_exists('/etc/mime.types') &&
        ($fh = fopen('/etc/mime.types', 'r')) !== false
    ) {
        while (($line = fgets($fh)) !== false) {
            if (!trim($line) || substr($line, 0, 1) === '#') continue;
            $mime_type = preg_split('/\t+/', rtrim($line));
            if (
                is_array($mime_type) &&
                isset($mime_type[0]) && $mime_type[0] &&
                isset($mime_type[1]) && $mime_type[1]
            ) {
                foreach (explode(' ', $mime_type[1]) as $ext) {
                    $mime_types[$ext] = $mime_type[0];
                }
            }
        }
        fclose($fh);
    }
    return $mime_types;
}

Вы можете использовать finfo для этого, начиная с PHP 5.3:

<?php
$info = new finfo(FILEINFO_MIME_TYPE);
echo $info->file('myImage.jpg');
// prints "image/jpeg"

Флаг FILEINFO_MIME_TYPE не является обязательным; без него вы получите более подробную строку для некоторых файлов; (очевидно, некоторые типы изображений возвращают информацию о размере и глубине цвета). Использование флага FILEINFO_MIME возвращает тип mime и кодировку, если она доступна (например, image / png; charset = binary или text / x-php; charset = us-ascii). См. этот сайт для получения дополнительной информации.

Mime любого файла на вашем сервере может быть получен с помощью этого

<?php
function get_mime($file_path){
  $finfo = new finfo(FILEINFO_MIME_TYPE);
  $type  = $finfo->file(file_path);
}

$mime = get_mime('path/to/file.ext');

Другие вопросы по теме