Bonjour,
J'utilise EasyPHP/5.3.3, donc PHP/5.3.1 pour générer des fichiers zip "à la volée", dont le contenu dépend de la requête que reçoit mon serveur web:
Extrait de mon code:
$zip = new ZipArchive();
$zipfname = "xxx.zip";
if($zip->open($zipfname, ZIPARCHIVE::CREATE) == TRUE)
{
foreach(...)
{
$zip->addFile($file, $file);
}
$zip->close();
header("Content-Type: application/zip");
header("Content-Disposition: attachment; filename=".$zipfname);
header("Content-Transfer-Encoding: binary");
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Pragma: public');
header("Expires: 0");
readfile($zipfname);
}
Tout ceci marche très bien, mais de temps en temps (5% du temps approximativement), readfile plante avec l'erreur suivante:
readfile(xxx.zip) [<a href='function.readfile'>function.readfile</a>]: failed to open stream: No such file or directory in <b>D:\...\ttt.php</b> on line <b>227</b><br />
Si je me rends dans le répertoire dans lequel j'ai préparé le zip, je trouve, en plus du .zip que j'attendais, un fichier .zip.aXXXXX, où XXXXX est un entier à 5 chiffres. Ce fichier est identique au zip, sauf qu'il est un peu plus ancien de quelques secondes à quelques dizaines de secondes.
J'ai placé une boucle d'attente (pas beau) qui fait des usleep de plusieurs centaines de millisecondes et qui vérifie à chaque boucle la présence du .zip avant le premier appel à header(), mais rien n'y fait, le zip se fait attendre alors que le .zip.aXXXXX est bien là...
En gros, on pourrait croire que le retour de l'appel à close() ne suffit pas pour dire que le fichier zip est prêt à être utilisé.
De plus, si le fichier .zip.aXXXXX est un fichier temporaire utilisé par la classe ZipArchive, pourquoi est-il laissé dans mon répertoire et pas détruit après la copie vers le .zip.
Une idée de comment régler mon problème?
Merci d'avance.
Sylvain