【问题标题】:PHP file stream data coming back in Binary以二进制形式返回的 PHP 文件流数据
【发布时间】:2026-01-16 18:05:02
【问题描述】:

所以我有一个我无法使用的功能。发生的事情是它返回的是二进制数据,而不是实际文件。但是,在我返回的二进制文件中,特定文件的名称包含在字符串中。数据如下所示:

PK‹Mpt-BR/finalinport.html³)°S(ÉÈ,V¢‘ŒT…‚ü¢’ÒôÒÔâT…´Ì¼Ä ™” “I,QðT(ÏÌÉQ(-ÈÉOLQH„¨‡*Ê/B×]’X”žZ¢`£_`ÇPK.Ùô LePK‹M.Ùô Lept-BR/finalinport.htmlPKD

pt-BR 是目录,“finalinport.html”是我要下载的文件。如果我将 fwrite 的第二个参数替换为纯字符串,那么一切正常,我会得到我在 zip 文件中写入的字符串。但不是当我使用 Stream->getContents() 时,这让我相信这是流中发生的事情。我无法理解可能发生的事情。我已经做了一个半星期了,所以任何建议都会很棒。

public function downloadTranslations(Request $request, $id)
    {
        $target_locales = $request->input("target_locale");
        $has_source = $request->input("source");
        $client = new API(Auth::user()->access_token, ZKEnvHelper::env('API_URL', 'https://myaccount.com'));
        $document = Document::find($id);
        $job_document = JobDocument::where('document_id', $id)->first();
        $job = Job::find($job_document->job_id);

        $file = tempnam('tmp', 'zip');
        $zip = new ZipArchive();
        $zip->open($file, ZipArchive::OVERWRITE);
        $name_and_extension = explode('.', $document->name);

        if($target_locales == null){
            $target_locales = [];
            foreach ($job->target_languages as $target_language) {
                $target_locales[] = $target_language['locale'];
            }
        }

        foreach($target_locales as $target_locale){
            $translation = $client->downloadDocument($document->document_id, $target_locale);
            $filename = $name_and_extension[0] . ' (' . $target_locale . ').' . $name_and_extension[1];
            if($translation->get('message') == 'true') {
                //API brings back file in stream type
                $stream = Stream::factory($translation->get('body'));
                $newFile = tempnam(sys_get_temp_dir(), 'lingo');

                $handle = fopen($newFile, 'w');
                fwrite($handle, $stream->getContents());
                    $zip->addFile($newFile, 'eh.html');
                fclose($handle);
                }

                else if($translation->get('message') == 'false'){
                    //API brings back file contents
                    $zip->addFromString($filename, $translation->get('body'));
                }
            }
            $translation = $client->downloadDocument($document->document_id, null, null);

            $filename = $name_and_extension[0].  ' (Source).'.$name_and_extension[1];
            $zip->addFromString($filename, $translation->get('body'));
            sleep(10);
            $zip->close();

        return response()->download($file, $name_and_extension[0].'.zip')->deleteFileAfterSend(true);
}

我不熟悉 PHP 流,也没有设置调试器,所以我一直认为这与我处理流的方式有关。因为另一个条件(else if)作为文件内容(字符串)和 if 语句返回,所以数据作为流资源返回,我不熟悉。

【问题讨论】:

  • 开头的PK显示它是一个zip文件。编写代码是为了创建一个 zip 文件并将文件放入其中。它不应该那样做吗?
  • @SamiKuhmonen 所以最上面的 $file 应该是一个 zip。这部分似乎在大多数情况下都有效。 if/else if 语句中的两个文件是我放入 zip 中的文件,而 if 是给我带来问题的文件。所以我猜想 if 语句中的逻辑导致初始 zip 文件变成了这个奇怪的二进制字符串。

标签: php file networking stream


【解决方案1】:

流::工厂 在 Guzzle 5 中使用,在 Guzzle 6 中使用 json_encode。

【讨论】: