Lors de l'utilisation de echo pour générer une grande chaîne binaire dans une réponse HTTP en PHP, le serveur renvoyait une réponse mal formée.
P粉328911308
2023-08-28 10:26:38
<p>J'essaie de générer de grands tableaux binaires vers une réponse HTTP en utilisant le code suivant : </p>
<pre class="brush:php;toolbar:false;">$bin = NULL;
$strLenToOutput = 8000 ;
pour ($i=0; $i < $strLenToOutput; $i++) {
$bin .= pack("C", 1);
}
header('Content-Description : Transfert de fichiers');
header("Content-Type: application/octet-stream");
header("Content-Disposition: attachment; filename=test.bin");
header("Content-Length: filesize=" . strlen($bin));
header("Cache-Control: no-cache");
echo $bin;</pre>
<p>Lorsque la chaîne à afficher est relativement courte, inférieure ou égale à 8 000, le code ci-dessus fonctionne correctement. Mais si la longueur de la chaîne passe à 8001, j'obtiens l'erreur suivante dans Postman : </p>
<pre class="brush:php;toolbar:false;">Erreur d'analyse : le serveur a renvoyé une réponse mal formée</pre>
<p>J'utilise PHP7.4 sur Apache V2.4.46, tous les paramètres sont par défaut. </p>
<p>Qu'est-ce que je fais de mal ici ? Est-ce le code PHP ou certains paramètres sur Apache2 qui doivent être modifiés ? </p>
<p>Veuillez nous fournir des conseils, merci d'avance. </p>
<p>Mise à jour : si je supprime la ligne suivante qui définit la longueur du fichier, le code PHP fonctionne correctement. Je suppose que le problème est que je devrais laisser PHP gérer cette partie lui-même. </p>
<pre class="brush:php;toolbar:false;">//header("Content-Length: filesize=" . strlen($bin));</pre></p>
Le problème est la façon dont l'en-tête Content-Length est défini. Le code d'origine définit un en-tête
devrait être configuré comme ceci :
Le texte supplémentaire "filesize=" dans l'en-tête ne fera que perturber l'analyse de la réponse par le client. Lorsque Content-Length est inférieur ou égal à 8000, le client peut avoir un moyen de récupérer, mais il ne peut pas gérer la situation lorsque Content-Length est supérieur ou égal à 8001