IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Langage PHP Discussion :

Forcer le téléchargement d'un fichier


Sujet :

Langage PHP

  1. #1
    Membre actif Avatar de baggie
    Profil pro
    Inscrit en
    Octobre 2007
    Messages
    755
    Détails du profil
    Informations personnelles :
    Âge : 35
    Localisation : France, Rhône (Rhône Alpes)

    Informations forums :
    Inscription : Octobre 2007
    Messages : 755
    Points : 262
    Points
    262
    Par défaut Forcer le téléchargement d'un fichier
    Bonjour,

    je crée une application où l'utilisateur peut télécharger les documents qui sont listés sur une page. Pour ça, aucun problème sauf si mon fichier est au format PDF. Il s'ouvre directement et ne me propose pas l'habituelle fenêtre "ouvrir avec ... / Enregistrer sous ...".

    J'ai cherché sur le web comment faire et j'ai trouvé un code que j'ai appliqué :

    Page php de listage des documents :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    $dossier = 'dossiers/'.$nomcli.'/'.$nom.'/';
    $filename = $datas['lien_document'];
    echo '<td>&nbsp;&nbsp;<a href="download.php?dossier='.$dossier.'&filename='.$filename.'">Télécharger</a></td></tr>';
    Le lien vers le document est le bon, $dossier et $filename sont corrects.

    Page download.php :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
    <?php
    header("Content-type: application/force-download");
    header("Content-Disposition: attachment; filename=".$filename);
    readfile($dossier.$filename);
    ?>
    Sauf qu'en faisant ça, le navigateur me propose de télécharger la page "download.php" et non mon fichier !

    Est-ce que j'ai fait une erreur quelque part ?

  2. #2
    Expert confirmé
    Avatar de Doksuri
    Profil pro
    Développeur Web
    Inscrit en
    Juin 2006
    Messages
    2 477
    Détails du profil
    Informations personnelles :
    Âge : 54
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web

    Informations forums :
    Inscription : Juin 2006
    Messages : 2 477
    Points : 4 688
    Points
    4 688
    Par défaut
    j'avais eu le meme probleme avec les fichiers txt.
    je n'arrive plus a retrouver une discution ou j'en parle (et je ne parviens plus a retrouver mon code non plus...d'ailleur ca m'inquiete de ne pas le retrouver)
    il me semble que cette explication devrait fonctionner

    Voici comment forcer téléchargement d'un fichier à l'aide du PHP.
    Pour que le script fonctionne il ne faut pas d'instruction qui affiche quelques choses à l'écran avant les lignes header.
    Par exemple créer un fichier" telecharger.php" avec comme contenu :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    <?php 
     
    // on essaie de reconnaitre l'extension pour que le téléchargement corresponde au type de fichier afin d'éviter les erreurs de corruptions 
     
    switch(strrchr(basename($Fichier_a_telecharger), ".")) {
     
    case ".gz": $type = "application/x-gzip"; break;
    case ".tgz": $type = "application/x-gzip"; break;
    case ".zip": $type = "application/zip"; break;
    case ".pdf": $type = "application/pdf"; break;
    case ".png": $type = "image/png"; break;
    case ".gif": $type = "image/gif"; break;
    case ".jpg": $type = "image/jpeg"; break;
    case ".txt": $type = "text/plain"; break;
    case ".htm": $type = "text/html"; break;
    case ".html": $type = "text/html"; break;
    default: $type = "application/octet-stream"; break;
     
    }
     
    header("Content-disposition: attachment; filename=$Fichier_a_telecharger"); 
    header("Content-Type: application/force-download"); 
    header("Content-Transfer-Encoding: $type\n"); // Surtout ne pas enlever le \n
    header("Content-Length: ".filesize($chemin . $Fichier_a_telecharger)); 
    header("Pragma: no-cache"); 
    header("Cache-Control: must-revalidate, post-check=0, pre-check=0, public"); 
    header("Expires: 0"); 
    readfile($chemin . $Fichier_a_telecharger); 
    ?>
    Ensuite faire un fichier test.php ou test.html suivant ses préférences.

    On appelle le fichier telecharger.php en passant en paramètre le nom du fichier à télécharger ainsi que le chemin.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    <html>
    <head>
    <title>Forcer le téléchargement d'un fichier</title>
    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
    </head>
    <body>
     
    <?php
    // Test du téléchargement d'un fichier avec reconnaissance du type de fichier 
    echo "<a href=\"telecharger.php?Fichier_a_telecharger=monfichier.txt&chemin=test/\">Télécharger</a>";
    ?>
     
    </body>
    </html> 
     
    Ou simplement si l'on ne veut utiliser que du html 
     
    <html>
    <head>
    <title>Test du téléchargement d'un fichier</title>
    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
    </head>
     
    <body>
     
    <a href="telecharger.php?Fichier_a_telecharger=monfichier.txt&chemin=test/">Télécharger</a> 
     
    </body>
    </html>

  3. #3
    Membre actif Avatar de baggie
    Profil pro
    Inscrit en
    Octobre 2007
    Messages
    755
    Détails du profil
    Informations personnelles :
    Âge : 35
    Localisation : France, Rhône (Rhône Alpes)

    Informations forums :
    Inscription : Octobre 2007
    Messages : 755
    Points : 262
    Points
    262
    Par défaut
    Salut Doksuri et merci pour ta réponse !

    J'ai testé le code que tu m'as donné, et rien à faire j'ai toujours le même résultat : la possibilité de télécharger download.php.

    J'ai quand même ouvert cette page avec le bloc-notes vu que le navigateur me le propose, et voici ce qu'il y a dans download.php :

    <b>Notice</b>: Undefined variable: filename in <b>C:\Program Files\EasyPHP5.3.0\www\download.php</b> on line <b>5</b><br />
    <br />
    <b>Notice</b>: Undefined variable: filename in <b>C:\Program Files\EasyPHP5.3.0\www\download.php</b> on line <b>13</b><br />
    <br />
    <b>Notice</b>: Undefined variable: filename in <b>C:\Program Files\EasyPHP5.3.0\www\download.php</b> on line <b>16</b><br />
    <br />
    <b>Notice</b>: Undefined variable: dossier in <b>C:\Program Files\EasyPHP5.3.0\www\download.php</b> on line <b>16</b><br />
    <br />
    <b>Notice</b>: Undefined variable: filename in <b>C:\Program Files\EasyPHP5.3.0\www\download.php</b> on line <b>20</b><br />
    <br />
    <b>Notice</b>: Undefined variable: dossier in <b>C:\Program Files\EasyPHP5.3.0\www\download.php</b> on line <b>20</b><br />
    <br />
    <b>Warning</b>: readfile() [<a href='function.readfile'>function.readfile</a>]: Filename cannot be empty in <b>C:\Program Files\EasyPHP5.3.0\www\download.php</b> on line <b>20</b><br />
    Pourtant mon dossier existe bien, mon fichier aussi et le chemin d'accès est correct.

    EDIT : j'ai lu ce post et apparement ça fonctionnerait une fois en ligne ?? oO

  4. #4
    Membre expert Avatar de Fench
    Homme Profil pro
    Chercheur en informatique
    Inscrit en
    Mai 2002
    Messages
    2 353
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Groenland

    Informations professionnelles :
    Activité : Chercheur en informatique
    Secteur : Administration - Collectivité locale

    Informations forums :
    Inscription : Mai 2002
    Messages : 2 353
    Points : 3 390
    Points
    3 390
    Par défaut
    Bonjour,

    Et tu as mis quoi dans ton fichier download.php, parceque php a l'air de lire du code au lieu de ton fichier ...

  5. #5
    Membre actif Avatar de baggie
    Profil pro
    Inscrit en
    Octobre 2007
    Messages
    755
    Détails du profil
    Informations personnelles :
    Âge : 35
    Localisation : France, Rhône (Rhône Alpes)

    Informations forums :
    Inscription : Octobre 2007
    Messages : 755
    Points : 262
    Points
    262
    Par défaut
    Mon fichier download.php :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
     
    <?php
     
    // on essaie de reconnaitre l'extension pour que le téléchargement corresponde au type de fichier afin d'éviter les erreurs de corruptions
     
    switch(strrchr(basename($filename), ".")) {
     
    case ".zip": $type = "application/zip"; break;
    case ".pdf": $type = "application/pdf"; break;
    default: $type = "application/octet-stream"; break;
     
    }
     
    header("Content-disposition: attachment; filename=$filename");
    header("Content-Type: application/force-download");
    header("Content-Transfer-Encoding: $type\n"); // Surtout ne pas enlever le \n
    header("Content-Length: ".filesize($dossier . $filename));
    header("Pragma: no-cache");
    header("Cache-Control: must-revalidate, post-check=0, pre-check=0, public");
    header("Expires: 0");
    readfile($dossier . $filename);
    ?>
    Comme j'ai édité précédemment, j'ai lu un post avec le même problème et apparement ça fonctionnerait une fois en ligne, mais comme la personne a posé la question, n'y-a-t-il pas un moyen pour que ça fonctionne en local ?

    [EDIT]
    Problème résolu ! Si jamais ça peut en aider certains, j'ai utilisé ce code :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
     
    $dossier = $_GET['dossier'];
    $filename = $_GET['filename'];
     
    $file = $dossier.$filename;
     
    //First, see if the file exists
    if (!is_file($file)) { die("<b>404 File not found!</b>"); }
     
    //Gather relevent info about file
    $len = filesize($file);
    $filename = basename($file);
    $file_extension = strtolower(substr(strrchr($filename,"."),1));
     
    //Begin writing headers
    header("Pragma: public");
    header("Expires: 0");
    header("Cache-Control: no-cache, must-revalidate, post-check=0, pre-check=0");
    header("Cache-Control: public");
    header("Content-Description: File Transfer");
     
    //Use the switch-generated Content-Type
    header('Content-Type: application/octet-stream');
     
    //Force the download
    $header="Content-Disposition: attachment; filename=".$filename.";";
    header($header);
    header("Content-Transfer-Encoding: binary");
    header("Content-Length: ".$len);
    @readfile($file);
    exit;
    et l'appel sur ma page php :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    echo '<td>&nbsp;&nbsp;<a href="download.php?dossier='.$dossier.'&filename='.$filename.'">Télécharger</a></td></tr>';
    [/EDIT]

  6. #6
    Membre expert Avatar de Fench
    Homme Profil pro
    Chercheur en informatique
    Inscrit en
    Mai 2002
    Messages
    2 353
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Groenland

    Informations professionnelles :
    Activité : Chercheur en informatique
    Secteur : Administration - Collectivité locale

    Informations forums :
    Inscription : Mai 2002
    Messages : 2 353
    Points : 3 390
    Points
    3 390
    Par défaut
    Re Baggie,

    J'ai passé un peu plus de temps mais je voulais bien comprendre la solution

    De plus, je voulais avoir une différence d'ouverture en fonction du type

    Alors voilà mon résultat 'en light':
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
     
    $dossier = $_GET['dossier'];
    $filename = $_GET['filename'];
     
    $ext = strrchr( $filename, "." );
    switch( $ext ) {
        case ".zip": $type = "application/zip"; break;
        case ".txt": $type = "text/plain"; break;
        case ".pdf": $type = "application/pdf"; break;
        default: $type = "application/octet-stream"; break;
    }
     
    // Constitution de l'header suivant le type
    header("Content-Description: File Transfer");
    header("Content-Type: $type\n");
    header("Content-Transfer-Encoding: binary");
    header("Content-disposition: attachment; filename=$filename");
    header("Content-Length: ".filesize( $dossier.$filename ) );
     
    // Lecture et Affichage
    readfile( $dossier.$filename );
    Cette solution marche avec les remarques suivantes suivant le pb initial:
    - Les get pour récupérer les valeurs car zone en Php
    - Le Switch pour différencier les types
    - Mise en place de l'header (version le plus simple) avec les arguments du content-type fonction du type de notre fichier et un transfert en binaire de taille longueur du fichier. Le fichier naturellement en attachement.

    Voilà

  7. #7
    Membre actif Avatar de baggie
    Profil pro
    Inscrit en
    Octobre 2007
    Messages
    755
    Détails du profil
    Informations personnelles :
    Âge : 35
    Localisation : France, Rhône (Rhône Alpes)

    Informations forums :
    Inscription : Octobre 2007
    Messages : 755
    Points : 262
    Points
    262
    Par défaut
    Merci Fench ! C'est vrai que c'est plus light mais ça fonctionne quand même parfaitement ! Je prends

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 4
    Dernier message: 13/06/2007, 16h27
  2. Réponses: 2
    Dernier message: 30/05/2006, 16h07
  3. Comment forcer le téléchargement d'un fichier avec IE.
    Par karibouxe dans le forum Servlets/JSP
    Réponses: 2
    Dernier message: 24/05/2006, 12h51
  4. forcer le téléchargement - problème ouverture fichier
    Par grinder59 dans le forum Langage
    Réponses: 8
    Dernier message: 09/03/2006, 16h59
  5. [Configuration] problème pour forcer le téléchargement d'un fichier
    Par All Bran dans le forum EDI, CMS, Outils, Scripts et API
    Réponses: 3
    Dernier message: 02/01/2006, 17h23

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo