web-dev-qa-db-fra.com

Type MIME des fichiers .rar et .Zip

Je développe un simple script de téléchargement php, et les utilisateurs ne peuvent télécharger que des fichiers Zip et RAR.

Quels types MIME je devrais utiliser pour vérifier $_FILES[x][type]? (une liste complète s'il vous plaît)

Je vous remercie..

120
mrdaliri

Les réponses de freedompeace, Kiyarash et Sam Vloeberghs:

.rar    application/x-rar-compressed, application/octet-stream
.Zip    application/Zip, application/octet-stream, application/x-Zip-compressed, multipart/x-Zip

Je voudrais aussi vérifier le nom du fichier. Voici comment vérifier si le fichier est un fichier RAR ou Zip. Je l'ai testé en créant une application rapide en ligne de commande.

<?php

if (isRarOrZip($argv[1])) {
    echo 'It is probably a RAR or Zip file.';
} else {
    echo 'It is probably not a RAR or Zip file.';
}

function isRarOrZip($file) {
    // get the first 7 bytes
    $bytes = file_get_contents($file, FALSE, NULL, 0, 7);
    $ext = strtolower(substr($file, - 4));

    // RAR magic number: Rar!\x1A\x07\x00
    // http://en.wikipedia.org/wiki/RAR
    if ($ext == '.rar' and bin2hex($bytes) == '526172211a0700') {
        return TRUE;
    }

    // Zip magic number: none, though PK\003\004, PK\005\006 (empty archive), 
    // or PK\007\008 (spanned archive) are common.
    // http://en.wikipedia.org/wiki/Zip_(file_format)
    if ($ext == '.Zip' and substr($bytes, 0, 2) == 'PK') {
        return TRUE;
    }

    return FALSE;
}

Notez que cela ne sera toujours pas certain à 100%, mais c'est probablement suffisant.

$ rar.exe l somefile.Zip
somefile.Zip is not RAR archive

Mais même WinRAR détecte les fichiers non RAR en tant qu’archives SFX:

$ rar.exe l somefile.srr
SFX Volume somefile.srr
210
Gfy

Pour uploader:

Une liste officielle des types de mime est disponible sur Autorité IANA (Internet Assigned Numbers Authority) . Selon leur liste, Content-Type, l'en-tête de Zip est application/Zip.

Le type de support pour les fichiers rar n'est pas officiellement enregistré auprès de l'IANA, mais la valeur non officielle de type mime couramment utilisée est application/x-rar-compressed.

application/octet-stream signifie autant que: "Je vous envoie un flux de fichiers et le contenu de ce flux n'est pas spécifié" _ (il est donc vrai qu'il peut s'agir également d'un fichier Zip ou rar). Le serveur est censé détecter le contenu réel du flux. 

Remarque: Pour le téléchargement, il n'est pas sûr de s'appuyer sur le type MIME défini dans l'en-tête Content-Type. L'en-tête est défini sur le client et peut être défini sur n'importe quelle valeur aléatoire. À la place, vous pouvez utiliser les informations de fichier php functions pour détecter le type de fichier mime sur le serveur. 


Pour le téléchargement:

Si vous souhaitez télécharger un fichier Zip et rien d'autre, vous ne devez définir qu'une seule valeur d'en-tête Accept. Toute valeur supplémentaire définie sera utilisée comme solution de secours au cas où le serveur ne pourrait pas satisfaire votre type mime demandé dans l'en-tête Accept.

Selon les spécifications WC3 this: 

application/Zip, application/octet-stream 

sera interprété comme: "Je préfère un type mime application/Zip, mais si vous ne pouvez pas le fournir, un application/octet-stream (un flux de fichier) convient également".

Donc, un seul:

application/Zip

Vous garantira un fichier Zip (ou une réponse 406 - Not Acceptable au cas où le serveur ne pourrait pas répondre à votre demande).

26
Wilt

Vous ne devez pas faire confiance à $_FILES['upfile']['mime'], vérifiez le type MIME vous-même. Pour cela, vous pouvez utiliser fileinfo extension , activé par défaut à partir de PHP 5.3.0.

  $fileInfo = new finfo(FILEINFO_MIME_TYPE);
  $fileMime = $fileInfo->file($_FILES['upfile']['tmp_name']);
  $validMimes = array( 
    'Zip' => 'application/Zip',
    'rar' => 'application/x-rar',
  );

  $fileExt = array_search($fileMime, $validMimes, true);
  if($fileExt != 'Zip' && $fileExt != 'rar')
    throw new RuntimeException('Invalid file format.');

REMARQUE: N'oubliez pas d'activer l'extension dans votre php.ini et de redémarrer votre serveur:

extension=php_fileinfo.dll
4
fibriZo raZiel

Dans une question liée , il existe du code Objective-C pour obtenir le type mime d'une URL de fichier. J'ai créé une extension Swift basée sur ce code Objective-C pour obtenir le type mime:

import Foundation
import MobileCoreServices

extension URL {
    var mimeType: String? {
        guard self.pathExtension.count != 0 else {
            return nil
        }

        let pathExtension = self.pathExtension as CFString
        if let preferredIdentifier = UTTypeCreatePreferredIdentifierForTag(kUTTagClassFilenameExtension, pathExtension, nil) {
            guard let mimeType = UTTypeCopyPreferredTagWithClass(preferredIdentifier.takeRetainedValue(), kUTTagClassMIMEType) else {
                return nil
            }
            return mimeType.takeRetainedValue() as String
        }

        return nil
    }
}
0