372 votes

Comment obtenir le type de média d'un fichier (type MIME) ?

Comment obtenir un type de média (type MIME) à partir d'un fichier en utilisant Java ? Jusqu'à présent, j'ai essayé JMimeMagic et Mime-Util. Le premier m'a donné des exceptions de mémoire, le second ne ferme pas ses flux correctement.

Comment sonder le fichier pour déterminer son type réel (pas seulement sur la base de l'extension) ?

5 votes

Un bon aperçu des bibliothèques disponibles est donné à l'adresse suivante rgagnon.com/javadetails/java-0487.html

0 votes

J'ai utilisé le cours qui a été posté comme réponse ici : stackoverflow.com/a/10140531/293280

4 votes

Tika devrait être la réponse maintenant. Les autres réponses ci-dessous font état de nombreuses dépendances avec Tika, mais je n'en vois aucune avec tika-core.

344voto

Chris Mowforth Points 3120

En Java 7, vous pouvez maintenant utiliser Files.probeContentType(path) .

0 votes

Cela a été très utile puisque le site web de mime-util semble être en panne et je ne peux pas dire si la bibliothèque est maintenue du tout !

0 votes

Cela fonctionne bien, mais je n'ai pas trouvé de moyen d'ajouter d'autres types de fichiers, à ma connaissance. Par exemple, une image ISO renvoie un résultat nul, tout comme une archive .zip et même un fichier de configuration ini.

0 votes

C'est une chose de toute beauté.

235voto

Joshua Fox Points 4505

Malheureusement,

mimeType = file.toURL().openConnection().getContentType();

ne fonctionne pas, car cette utilisation de l'URL laisse un fichier verrouillé, de sorte que, par exemple, il est indélébile.

Cependant, vous avez ceci :

mimeType= URLConnection.guessContentTypeFromName(file.getName());

et aussi la suivante, qui a l'avantage d'aller au-delà de la simple utilisation de l'extension de fichier, et de jeter un coup d'œil au contenu

InputStream is = new BufferedInputStream(new FileInputStream(file));
mimeType = URLConnection.guessContentTypeFromStream(is);
 //...close stream

Cependant, comme le suggère le commentaire ci-dessus, le tableau intégré des types de mime est assez limité, n'incluant pas, par exemple, MSWord et PDF. Donc, si vous voulez généraliser, vous devrez aller au-delà des bibliothèques intégrées, en utilisant, par exemple, Mime-Util (qui est une excellente bibliothèque, utilisant à la fois l'extension de fichier et le contenu).

8 votes

Une solution parfaite - qui m'a beaucoup aidé ! Emballage FileInputStream en BufferedInputStream est une partie cruciale - sinon guessContentTypeFromStream renvoie à null (passé InputStream l'instance doit supporter les marques)

15 votes

Howerver, URLConnection a un ensemble très limité de types de contenu qu'il reconnaît. Par exemple, il n'est pas en mesure de détecter application/pdf .

0 votes

@kpentchev il détecte les pdf pour moi. Mais il ne détecte pas les fichiers Office, par exemple *.doc.

52voto

Mamuf Points 371

L'API JAF fait partie du JDK 6. Regardez javax.activation paquet.

Les classes les plus intéressantes sont javax.activation.MimeType - un titulaire réel de type MIME - et javax.activation.MimetypesFileTypeMap - classe dont l'instance peut résoudre le type MIME comme String pour un fichier :

String fileName = "/path/to/file";
MimetypesFileTypeMap mimeTypesMap = new MimetypesFileTypeMap();

// only by file name
String mimeType = mimeTypesMap.getContentType(fileName);

// or by actual File instance
File file = new File(fileName);
mimeType = mimeTypesMap.getContentType(file);

4 votes

Malheureusement, comme le montre la javadoc de getContentType(File) États : Retourne le type MIME de l'objet fichier. L'implémentation dans cette classe appelle getContentType(f.getName()) .

3 votes

Et n'oubliez pas que vous pouvez étendre cette fonctionnalité avec le fichier META-INF/mime.types, ce qui est parfait si vous êtes obligé d'utiliser Java 6. docs.oracle.com/javaee/5/api/javax/activation/

9 votes

Vous pouvez éviter de créer un nouvel objet en MimetypesFileTypeMap.getDefaultFileTypeMap().getContentType(‌​file)

26voto

Pawan Points 173

Si vous êtes un développeur Android, vous pouvez utiliser une classe utilitaire android.webkit.MimeTypeMap qui fait correspondre les types MIME aux extensions de fichiers et vice versa.

L'extrait de code suivant peut vous aider.

private static String getMimeType(String fileUrl) {
    String extension = MimeTypeMap.getFileExtensionFromUrl(fileUrl);
    return MimeTypeMap.getSingleton().getMimeTypeFromExtension(extension);
}

3 votes

Cela fonctionne également si on essaie avec des chemins de fichiers locaux tels que "/sdcard/path/to/video.extension". Le problème est que si le fichier local contient un espace dans son chemin, il renvoie toujours null.

19voto

Desde roseindia :

FileNameMap fileNameMap = URLConnection.getFileNameMap();
String mimeType = fileNameMap.getContentTypeFor("alert.gif");

7 votes

La personne qui a voté contre la réponse est priée d'ajouter un commentaire afin que je puisse apprendre à publier de meilleures réponses.

3 votes

Je n'ai pas voté pour vous mais, getFileNameMap ne fonctionne pas pour de nombreux types de fichiers de base, par exemple 'bmp'. URLConnection.guessContentTypeFromName renvoie également la même chose.

5 votes

Fonction très incomplète. Depuis Java 7, les extensions html, pdf et jpeg renvoient le type de mime correct mais js et css renvoient null !

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X