Wojtek
Wojtek

Reputation: 51

Write into csv in php (class php)

I'm using php class to write data to CSV. Link to class: http://www.jongales.com/blog/2009/09/24/php-class-to-write-csv-files/

Class code:

<?php
/** 
 * Simple class to properly output CSV data to clients. PHP 5 has a built 
 * in method to do the same for writing to files (fputcsv()), but many times 
 * going right to the client is beneficial. 
 * 
 * @author Jon Gales 
 */  

class CSV_Writer {  

    public $data = array();  
    public $deliminator;  

    /** 
     * Loads data and optionally a deliminator. Data is assumed to be an array 
     * of associative arrays. 
     * 
     * @param array $data 
     * @param string $deliminator 
     */  
    function __construct($data, $deliminator = ",")  
    {  
        if (!is_array($data))  
        {  
            throw new Exception('CSV_Writer only accepts data as arrays');  
        }  

        $this->data = $data;  
        $this->deliminator = $deliminator;  
    }  

    private function wrap_with_quotes($data)  
    {  
        $data = preg_replace('/"(.+)"/', '""$1""', $data);  
        return sprintf('"%s"', $data);  
    }  

    /** 
     * Echos the escaped CSV file with chosen delimeter 
     * 
     * @return void 
     */  
    public function output()  
    {  
        foreach ($this->data as $row)  
        {  
            $quoted_data = array_map(array('CSV_Writer', 'wrap_with_quotes'), $row);  
            echo sprintf("%s\n", implode($this->deliminator, $quoted_data));  
        }  
    }  

    /** 
     * Sets proper Content-Type header and attachment for the CSV outpu 
     * 
     * @param string $name 
     * @return void 
     */  
    public function headers($name)  
    {  
        header('Content-Type: application/csv');  
        header("Content-disposition: attachment; filename={$name}.csv");  
    }  
}  
?>

and php code:

if($_GET['action']=="csv") {
$data = array(array("one","two","three"), array(4,5,6));  
$csv = new CSV_Writer($data);  
$csv->headers('test');  
$csv->output();  
}

The problem is the resulting file. I have a CSV file instead of the array is only the HTML content page. Why is this happening?

The content of the CSV file:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>title</title>
<link href="../css/style.css" rel="stylesheet" type="text/css" media="screen" />
<script type="text/javascript" src="jscripts/tiny_mce/tiny_mce.js"></script>
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js"></script>
<script type="text/javascript" src="jscripts/picnet.table.filter.min.js"></script>
<link href="style.css" rel="stylesheet" type="text/css" media="screen" />
<script type="text/javascript">
...

Thx for help.

Upvotes: 1

Views: 2944

Answers (1)

Nate Cook
Nate Cook

Reputation: 93276

You have two issues:

  1. You're reinventing the wheel, as PHP already has fputcsv. Don't do that!
  2. From what I can see, you didn't stop executing the script, so PHP is going to go ahead and render the rest of the HTML document. I can't tell exactly why you're not seeing the HTML preceded by CSV info, but maybe the output cache is being flushed somehow. The fix for this is to add an exit(); line at the end of that block:
if($_GET['action']=="csv") {
    $data = array(array("one","two","three"), array(4,5,6));  
    $csv = new CSV_Writer($data);  
    $csv->headers('test');  
    $csv->output();
    exit();
}

Upvotes: 1

Related Questions