php file_get_contents():内容从2147483648截断到2147483647字节

时间:2015-04-06 09:19:24

标签: php file http-headers zip memory-limit

当我要创建2GB文件的zip文件时,如何找出问题。

错误

  

file_get_contents():内容从2147483648截断到2147483647   字节

     

致命错误:内存不足(分配2151677952)(试图分配   

中的18446744071562067968字节)

我正在使用专用服务器并已设置memory_limit,max_execution_time,max_upload_filesize,max_post_size。但它对我不起作用。请检查我的代码,让我知道我做错了什么 -

创建新的zip对象

    $zip = new ZipArchive();

    # create a temp file & open it
    $tmp_file = tempnam('.','');
    $zip->open($tmp_file, ZipArchive::CREATE);

    # loop through each file
    foreach($files as $file){
        # download file
        $download_file = file_get_contents($file_path.'/'.$file);
        #add it to the zip
        $zip->addFromString(basename($file_path.'/'.$file),$download_file);
    }

    # close zip
    $zip->close();
    $zip_name = $last_seg.'.zip';
    # send the file to the browser as a download
    header("Content-disposition: attachment; filename=$zip_name");
    header('Content-type: application/zip');
    readfile($tmp_file);

3 个答案:

答案 0 :(得分:5)

我将$zip->addFromString()更改为$zip->addFile(),因为您不需要阅读内容文件来添加文件,我用3部电影测试您的代码并且不能正常工作(我有同样的错误)但是当我使用$zip->addFile()时一切正常,我可以用3gb下载zip文件。

我需要使用set_time_limit(0);

如果您想测试此代码,只需更改以下值:

$files //Array of files name $file_path //Path where your files ($files) are placed $last_seg //The name of your zip file

<?php

    set_time_limit(0);

    $files = array('Exodus.mp4', 'the-expert.webm', 'what-virgin-means.webm');
    $file_path = 'zip';
    $last_seg = 'test';

    $zip = new ZipArchive();

    # create a temp file & open it
    $tmp_file = tempnam('.','');
    $zip->open($tmp_file, ZipArchive::CREATE);

    # loop through each file
    foreach($files as $file){
        $zip->addFile($file_path.'/'.$file, $file);
    }

    # close zip
    $zip->close();
    $zip_name = $last_seg.'.zip';
    # send the file to the browser as a download
    header("Content-disposition: attachment; filename=$zip_name");
    header('Content-type: application/zip');
    readfile($tmp_file);

?>

您可以在以下网址阅读更多内容:

  

http://php.net/manual/en/ziparchive.addfile.php

答案 1 :(得分:4)

您永远无法分配比PHP_INT_MAX更多的内存。因此,如果file_gets_content不在内部限制为有符号的int 32bits,那么Linux x64版本的PHP可以处理这个问题,但是在Windows或32位系统上,如果没有流式传输,你就没有机会实现这一点。

这样的事可能有用:(尚未测试)

$fr = fopen("http://...", "r");
$fw = fopen("zip://c:\\test.zip#test", "w");

while(false !== ($buffer = fread($fr, 8192)))
{
  fwrite($fw, $buffer, strlen($buffer));
}

fclose($fr);
fclose($fw);

好吧,我的糟糕显然PHP不提供模式&#34; + w&#34;对于一个zip流...你的最后一个选项是,然后将整个文件写入临时文件(通过像我一样流式传输,没有file_get_contents),然后再将它提供给外部程序(使用system()或popen调用)。 ..)或使用另一种压缩格式(显然是php支持zlib ant bzip2的写入流操作)或使用外部库进行php。

答案 2 :(得分:-3)

尝试将此行放在代码的开头:

ini_set("memory_limit", -1);

参考这个问题 Fatal error: Out of memory (allocated 1134559232) (tried to allocate 32768 bytes) in X:\wamp\www\xxx