简体   繁体   English

添加CSV文件后下载的zip存档为空

[英]Downloaded zip archive empty after adding csv file

Can skip About and Goal if necessary. 如有必要,可以跳过关于和目标。 They provide context/background about program. 它们提供有关程序的上下文/背景。

The Problem: 问题:
When I download a zip archive that is supposed to have a csv file in it, I get an empty archive or invalid archive. 当我下载应该包含csv文件的zip存档时,我得到了一个空的存档或无效的存档。 Now, I can make the zip archive with the csv in it, on the server and download via FileZilla. 现在,我可以在服务器上制作包含csv的zip存档,并通过FileZilla下载。 This is not the desired use case. 这不是所需的用例。 User wants to download automatically after clicking a button. 用户想要在单击按钮后自动下载。

About program: 关于程序:
Agents sign up for event (ie RSVP to it) and provide a set of photos. 代理注册事件(即对事件进行RSVP)并提供一组照片。 For every agent, there are +1 photos. 每位特工都有+1张照片。 User wants to download a list of all RSVPs for each event (ie the sign up data). 用户想要为每个事件下载所有RSVP的列表(即注册数据)。 For each RSVP, User also wants to see the photos they uploaded to the server. 对于每个RSVP,用户还希望查看他们上传到服务器的照片。

Goal of program: 计划目标:

  1. Create csv file on server of mysql query (each row is an RSVP) 在mysql查询的服务器上创建csv文件(每行都是一个RSVP)
  2. For each row, create zip archive for that row's/RSVP's photos. 对于每一行,为该行的/ RSVP的照片创建zip存档。
  3. Wanted: 1 csv file and multiple zip archives all in one big archive 想要的:1个csv文件和多个zip存档全部集中在一个大存档中
  4. End result: Add all files into one zip archive and download to User. 最终结果:将所有文件添加到一个zip存档中,然后下载到User。
  5. Addendum: This big zip file needs to be freshly generated every time it is requested. 附录:每次请求时都需要重新生成此大zip文件。

Current Status of Program: 计划的现状:
CSV file created. CSV文件已创建。 Below it is added to ZipArchive object. 在其下方将添加到ZipArchive对象。 Downloaded zip file and found it empty . 下载了zip文件,发现它为

//store the result of the query. Included to show process
$result = mysqli_query($dbh, $sql);
//open the file to write the information to.
$file = fopen('event-report.csv', 'w');
$txt .= 'Title Company,' .'Event ID,' . 'Event Time,' . 'First Name,' . 'Last Name,' . 'Email,' . 'Agent Company,' . 'Phone Number,' . 'Listing ID,' . 'URL,' . 'Address,' . 'ZIP,' . "\n";
while ($row = mysqli_fetch_row($result)){
    for ($i=0; $i<12; $i++){
        $txt .= $row[$i] . ',';             //About the agent attending
    }
    $txt .= "\n";
    $listings[$listing_count] = $row[8];    
}
fputs($file, $txt); //store into csv file
fclose($file);        //verified on server; contains desired output

$zip = new ZipArchive();
$dir = 'tmp';                  //create temporary directory with write access
if ( !file_exists($dir) ) {
    mkdir ($dir, 0755);        //Everything for owner, read/execute for others
}
if($zip->open('test.zip', ZIPARCHIVE::CREATE) === TRUE ){

    $zip->addFile('event-report.csv');
    if (file_exists($zip->getFromName('event-report.csv'))){
        echo "Exists";
    }
    else{
        echo "Does Not Exist";
        echo $_SERVER['DOCUMENT_ROOT'];
    }
}
else {
    echo "Failed code";
}
$zip->close();
if(!$return){
    echo " You do not have write access to current folder.";
}
else{
    echo "You do have access.";  //without headers, the zip containing csv successfully created on server.
}

header('Content-disposition: attachment; filename=download.zip');
header('Content-type: application/zip');
readfile($dir.'/test.zip');     //When downloaded: still empty/invalid.

Possible Problem(s) 可能的问题

  1. Zip is not finding the file because it is being created at the same time. Zip找不到文件,因为它是同时创建的。
    1a. 1A。 Solved :. 解决了 :。 Files created can be put into zip archive right after closing. 关闭后,可以立即将创建的文件放入zip存档。
  2. addFile parameter(s) are incorrect or lacking. addFile参数不正确或缺少。
    2a. 2A。 Man page says for this parameter: "path to the file to add" 手册页针对此参数说:“要添加的文件的路径”
    2b. 2B。 Tried putting the path after the domain name but no success: 尝试将路径放在域名之后,但未成功:
    $zip->addFile('/f1/f2/f3/f.csv');
    2c. 2c。 PHP Manual > ZipArchive::addFile PHP手册> ZipArchive :: addFile
      i. 一世。 Solved : The parameter is just the name of the file. 已解决 :参数只是文件名。 No path is needed in this case. 在这种情况下,不需要任何路径。

Questions 问题

  1. How do I add a csv file, a zip archive, or any file in general to another zip archive so that it will not be empty when I download it? 如何将一个csv文件,一个zip存档或一般的任何文件添加到另一个zip存档中,以便在下载时不会为空?
  2. Is this implementation incorrect because I am trying to add a file to a zip archive right after creating it? 此实现是否不正确,因为我试图在创建文件后立即将其添加到zip存档中? See Possible Problem(s) 1. 请参阅可能的问题1。
  3. If this question can be solved by a little reading, then what resources can you link that can guide me along? 如果您可以通过一些阅读来解决这个问题,那么您可以链接哪些资源来指导我? I have spent an entire day reading in regards to this issue and do not feel like I understand what I am missing here. 我整天都在阅读有关此问题的内容,感觉好像我不明白我在这里缺少什么。
    3a. 3a。 file permissions 文件权限

添加到归档文件时,您必须使用绝对路径来明确显示。

$zip->addFile($abs_path, $relative_path); 

Solution: flush headers before calling readfile(). 解决方案:在调用readfile()之前刷新标头。 I learned that I do not need flush() but I left it in there anyways. 我了解到我不需要flush(),但无论如何我还是把它留在那里。 See SO post that helped me include these two statements here 看到这样的帖子,它帮助我在此处包括了这两个声明

header('Content-type: application/zip');
header('Content-disposition: attachment; filename=test.zip');
ob_clean();   // discard any data in the output buffer (if possible)
flush();      // flush headers (if possible)
readfile('tmp/test.zip');
exit();

I also changed some minor things with the error checking that I thought I would mention below: 我还通过错误检查更改了一些小事情,我认为我会在下面提到:
I made a directory with certain permissions that will hold the files I want to put into the archive. 我创建了一个具有某些权限的目录,该目录将保存我要放入存档的文件。 This is done at the beginning before the csv and zip are created. 这是在创建csv和zip的开始时完成的。

$dir = 'tmp/';
if ( !file_exists($dir) ) {
    mkdir ($dir, 0777);
}

Opening the file has changed too. 打开文件也已更改。 It now involves the new directory I make: 现在,它涉及到我创建的新目录:

$zip = new ZipArchive;
if($zip->open($dir.'test.zip', ZIPARCHIVE::CREATE) === TRUE ){

    $res = $zip->addFile('tmp/event-report.csv', 'event-report.csv');                           //add the report csv file.
    if ($res){
        echo "Exists ";
    }
    else{
        echo "Does Not Exist ";
        //echo $_SERVER['DOCUMENT_ROOT'];
    }
}

Thanks to everyone that contributed or just viewed this question. 感谢所有贡献者或刚刚看过这个问题的人。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM