web-dev-qa-db-fra.com

Comment définir le nom de fichier contenant des espaces dans l'en-tête Content-Disposition

J'ai ce morceau de code:

resp.addHeader("Content-Disposition", "inline; filename=" + fileName);

Lorsque le nom du fichier est "a_b_c.doc" ou "abc.doc", le nom du fichier téléchargé s'affiche correctement. Cependant, lorsque le nom du fichier est "a b c .doc", le nom du fichier téléchargé n'est que "a".

Comment pouvons nous résoudre ceci?

42
Huy Than

Utilisez des guillemets:

resp.addHeader("Content-Disposition", "inline; filename=\"" + fileName + "\"");
66
Moritz Petersen

Selon la norme HTTP vous entourez la chaîne de guillemets doubles et vous échappez de toutes guillemets ou barres obliques inverses en les précédant d'une seule barre oblique inverse.

Content-Disposition: attachment; filename="Very \"interesting\" file \\ files.txt"

Cela vous invitera à enregistrer en tant que Very "interesting" file \ files.txt. Notez que la présence d'une barre oblique inverse ne suggère pas un dossier, elle suggère que la barre oblique inverse fait partie du nom de fichier (qui est parfaitement valide sur Linux et certaines autres plates-formes, mais pas sur Windows.)

11
Malvineous

si vous citez votre nom de fichier avec chr(34) cela fonctionnera:

resp.addHeader("Content-Disposition", "inline; filename=" + chr(34) + fileName + chr(34));
0
Raphaël

Les étapes suivantes sont nécessaires:

  • RI-encode le nom du fichier
  • Remplacez les espaces dans le nom de fichier encodé (nous utilisons un encodeur URL au lieu d'un encodeur URI, mais l'encodage URL utilise + comme espace codé au lieu de %20, nous devons donc les remplacer manuellement par %20).
  • Définissez le nom du fichier encodé dans l'en-tête. Ici, nous avons deux variantes: une qui spécifie l'encodage, et une qui n'en a pas. Pour une compatibilité maximale, nous pouvons spécifier les deux.

Code:

String fileName = ...;
String encodedFileName = URLEncoder.encode(fileName, 
    StandardCharsets.UTF_8.name()).replace("+", "%20");

response.setHeader("Content-Disposition", 
    String.format("inline; filename*=UTF-8''%1$s; filename=%1$s", encodedFileName));

Exemple d'en-tête: inline; filename*=UTF-8''Hello%20World.doc; filename=Hello%20World.doc

Testé avec succès avec

  • Firefox ✔
  • Chrome ✔
  • Bord ✔
  • Internet Explorer ✔
0
Peter Walser