web-dev-qa-db-fra.com

PHP générer un fichier à télécharger puis rediriger

J'ai une application PHP qui crée un fichier CSV que le téléchargement est forcé à l'aide d'en-têtes. Voici la partie pertinente du code:

header('Content-Type: application/csv'); 
header("Content-length: " . filesize($NewFile)); 
header('Content-Disposition: attachment; filename="' . $FileName . '"'); 
echo $content;
exit(); 

Ce que j'aimerais faire, c'est rediriger les utilisateurs vers une nouvelle page une fois le fichier créé et l'invite de téléchargement envoyée. Ajouter simplement header("Location: /newpage") à la fin n'a pas fonctionné, comme prévu, donc je ne suis pas sûr de savoir comment le configurer.

58
Evan

Je ne pense pas que cela puisse être fait - bien que je ne sois pas sûr à 100%.

La chose commune (par exemple dans les sites de téléchargement populaires) est l’inverse: vous allez d’abord sur la page after puis le téléchargement commence.

Alors redirigez vos utilisateurs vers la page final qui dit (entre autres):

Votre téléchargement devrait démarrer automatiquement. Sinon, cliquez sur [a href="create_csv.php"]here[/a].

En ce qui concerne le lancement du téléchargement (par exemple, appeler automatiquement create_csv.php), vous disposez de nombreuses options:

  • HTML: [meta http-equiv="refresh" content="5;url=http://site/create_csv.php"]
  • Javascript: location.href = 'http://site/create_csv.php';
  • iframe: [iframe src="create_csv.php"][/iframe]
81
daremon

très facile à faire dans le cas où il est vraiment nécessaire.

Mais vous aurez besoin de travailler un peu en JavaScript et les cookies:

dans PHP, vous devriez ajouter la configuration d'un cookie

header('Set-Cookie: fileLoading=true'); 

ensuite, sur la page où vous appelez le téléchargement, vous devez suivre avec JS (par exemple, une fois par seconde) si un cookie arrive comme ça (il existe un plugin jQuery cookie ici):

setInterval(function(){
  if ($.cookie("fileLoading")) {
    // clean the cookie for future downoads
    $.removeCookie("fileLoading");

    //redirect
    location.href = "/newpage";
  }
},1000);

Maintenant, si le fichier commence à être téléchargé, JS le reconnaît et redirige vers la page nécessaire après la suppression du cookie.

Bien sûr, vous pouvez dire que vous avez besoin d'un navigateur pour accepter les cookies, JavaScript, etc., mais cela fonctionne.

9
smnbbrv

L'en-tête que vous envoyez est un en-tête HTTP. Le navigateur prend cela comme une requête de page et la traite comme une page. Et dans votre cas, une page à télécharger.

Ajouter un en-tête de redirection complique donc le processus de téléchargement du fichier (puisque les en-têtes sont collectés, générés dans un en-tête puis envoyés au navigateur, vous pouvez essayer ceci en définissant plusieurs en-têtes de redirection IIRC)

8
Ólafur Waage

Gardez toutefois à l'esprit que le lancement automatique de fichiers téléchargeables pour les utilisateurs de IE déclenchera l'onglet d'alerte de sécurité. Les trois méthodes décrites par daremon afficheraient cet avertissement. Vous ne pouvez tout simplement pas contourner cela. Vous serez mieux servi si vous fournissez des liens réels.

2
martar

J'ai trouvé une solution de contournement basée sur javascript, qui n'est donc pas parfaitement sécurisée, mais qui semble fonctionner pour les sites critiques non sécurisés. 

Avoir un formulaire avec un bouton intitulé «télécharger» avec l'action définie pour pointer vers le script de téléchargement, puis en utilisant javascript mettre quelque chose sur le gestionnaire onsubmit qui supprime le bouton de téléchargement et remplace la messagerie à l'écran. Le téléchargement devrait quand même se produire et l'écran va changer. Évidemment, s'il y a un problème avec le script de téléchargement, il semble toujours que le téléchargement a réussi, même s'il ne se déclenche pas, mais c'est le meilleur que j'ai actuellement.

1
Darren Crabb

Vous pouvez essayer de rediriger vers l'URL plus un paramètre qui représente le contenu du fichier. Et dans la redirection, vous pouvez générer le contenu du fichier à télécharger.

0
user1251795

Lancez le fichier PHP contenant le téléchargement du fichier CSV en utilisant:

<a onclick="popoutWin(\'csvexport.php\')" >Download CSV File</a>

ou 

<input name="newThread" type="button" value="Download CSV File"
        onclick="popoutWin(\'csvexport.php\')" />

où la fonction JavaScript popoutWin est

/*
 * Popout window that self closes for use with downloads
 */
function popoutWin(link){
    var popwin = window.open(link);
    window.setTimeout(function(){
        popwin.close();
    }, 500);
}

Cela ouvrira une fenêtre pour afficher l'invite de téléchargement CSV, puis fermera immédiatement la fenêtre, ne laissant que l'invite.

0
Clinton

Voici la réponse:
C'est du travail!
Vous avez besoin de trois parties de code différentes:

HTML

<a id="download_btn" class="btn btn-primary" href="?file=filename&download=1">Download<&/a>


JQuery

$('#download_btn').click(function(){
    window.location.href = '<?=base_url()?>/?file=<?=$file;?>&download=1';
}).focusout (function(){
    window.location.href = '<?=base_url()?>';
    return false;
});


PHP

        if(isset($_GET['download']) && isset($_GET['file'])){

            $Zip_path = 'path_to/'.$_GET['file'].'.Zip';

            if(file_exists($Zip_path)){
                header('Content-Type: application/Zip');
                header('Content-Disposition: attachment; filename="'.basename($Zip_path).'"');
                header('Content-Length: ' . filesize($Zip_path));
                header('Location: '.$Zip_path);
            }

        }
0
Hisham Dalal

Hmmmm ...

Mettez le code ci-dessous dans le code javascript principal du site.

 if (window.location.pathname == '/url_of_redirect/') {
        window.open(location.protocol + '//' + location.hostname + '/url_of_download.Zip', '_parent');
    }

Expliquant: Il fait la redirection normale avec php vers une URL que vous allez difine et en javascipt il dit: Si le chemin est identique au chemin qui a été redirigé '/ url_of_redirect /', il ouvre l’url sur une nouvelle page , générant le téléchargement. 

0
FernandoGiroto

C'est un problème assez ancien, mais voici comment je l'ai réalisé via JS.

// Capture the "click" event of the link.
var link = document.getElementById("the-link");
link.addEventListener("click", function(evt) {
  // Stop the link from doing what it would normally do.
  evt.preventDefault();
  // Open the file download in a new window. (It should just
  // show a normal file dialog)
  window.open(this.href, "_blank");
  // Then redirect the page you are on to whatever page you
  // want shown once the download has been triggered.
  window.location = "/thank_you.html";
}, true);

Via - https://www.daniweb.com/web-development/php/threads/463652/page-not-redoting-after-sending-headers-in-php

0
Vaibhav Jain
<?php 
    function force_file_download($filepath, $filename = ''){
        if($filename == ''){
            $filename = basename($filepath);
        }

        header('Content-Type: application/octet-stream');
        header("Content-Transfer-Encoding: Binary"); 
        header("Content-disposition: attachment; filename=\"" . $filename . "\""); 
        readfile($filepath); // do the double-download-dance (dirty but worky)  
    }

    force_file_download('download.txt');
?>
<script type="text/javascript">
    location = 'page2.php'
</script>

Voici une solution utilisant javascript.

0
nikksan