Array to csv download in PHP - php

I am trying to turn my array in PHP into a csv to download.
Currently the array looks something like this
Array[0] = "Name,age,ID"
Array[1] = "Alex,26,1"
Array[2] = "Ryan,12,2"
Array[3] = "Steph,56,7"
etc
I was unsure how to make this download as a csv, where each array position is its own line is csv obviously.
I set the headers to the following :
header("Content-type: text/csv");
header("Content-Disposition: attachment; filename=file.csv");
then I tried to echo each element of the array, hoping this would work. as follows:
header("Content-type: text/csv");
header("Content-Disposition: attachment; filename=file.csv");
foreach ($lines as &$line) {
echo $line;
}
Where $lines was my array.
However it did all one line in the csv. Is there a way I can turn this array to print properly in csv?

You have to add a newline
echo $line . "\n";
Even better
echo $line . PHP_EOL; //constant for correct line-ending depending on OS.

One of solution is fputcsv function.
header("Content-type: text/csv");
header("Content-Disposition: attachment; filename=file.csv");
$output = fopen('php://output', 'w');
foreach ($lines as $line) {
$row = explode(',', $line);
fputcsv($output, $row);
}
fclose($output);

Related

csv file is not downloading within for loop

Comparing two multidimensional array and get the result by matching values. How to create and download the csv file for those respective values. I have tried this code below
$mycsvfile_result = array();
foreach ($mycsvfile as $arr1)
{
foreach ($mycsvfile_log as $arr2)
{
if($arr2[2] == $arr1[0])
{
$mycsvfile_result[] = array($arr2[2], $arr2[7]);
}
}
}
tried code 1 for fputcsv
header('Content-type: application/csv');
header('Content-Disposition: attachment; filename="demo.csv"');
header('Pragma: no-cache');
header('Expires: 0');
$fp = fopen('php://output', 'w');
$data=$mycsvfile_result;
foreach ( $data as $line )
{
fputcsv($fp, $line);
}
fclose($fp);
exit();
tried code 2 for fputcsv
$csv = "col1,col2 \n";//Column headers
foreach ($mycsvfile_result as $record)
{
$csv.= $record[0].','.$record[1]."\n"; //Append data to csv
}
$csv_handler = fopen ('demo.csv','w');
fwrite ($csv_handler,$csv);
fclose ($csv_handler);
echo 'Data saved to demo.csv';
The above code 1 results in
id1,email1 id2,email2 id3,email3
The above code 2 results in
col1,col2 id1,email1 id2,email2 id3,email3 Data saved to demo.csv
I'm working in linux machine, I forget to give the folder permission to upload the csv file. After giving folder permission it works like a charm :)

Trying to automatically open a dynamically generated CSV file from PHP script?

I'm successfully getting the desired output in console, but the browser isn't automatically downloading the CSV file.
header('Content-Type: application/csv');
$filename = 'Totals Report for ' . $name . ' All-Time.csv';
header('Content-Disposition: attachment; filename="'.$filename.'";');
$output = fopen('php://output', 'rb');
// output the column headings
fputcsv($output, array('Procedure Name', 'Totals'));
foreach ($rows as $row){
fputcsv($output, $row);
}
fopen($filename);
fclose($output);
A sample wich running in my browser:
$csv= '"Procedure Name", Totals'."\n";
$rows= array(
array('aaa', 'bbb'),
array('123', '456')
);
foreach ($rows as $row){
$csv .= implode(",",$row)."\n";
}
$filename= 'Totals Report for '.$name.' All-Time.csv';
header('Content-Type: text/csv');
header('Content-Disposition: attachment; filename="'.$filename.'";');
die($csv);
Bah, this got unruly in the comments. I took it a step further and made it loop through the values too!
// Set headers
header('Content-Type: text/csv');
$filename = 'Totals Report for ' . $name . ' All-Time.csv';
header('Content-Disposition: attachment; filename="'.$filename.'";');
// Column titles
echo 'Procedure Name,Totals' . "\n"; // Don't forget the newlines!
// Data
foreach ($rows as $row) {
foreach ($row as $index => $value) {
echo $value;
if ($index < count($row) - 1) {
echo ',';
}
}
echo "\n";
}
You could also buffer it into a file so you can use fputcsv. That would work almost exactly as your current code, but at the end you'd have echo file_get_contents($the_buffer_file);
The main point is that all you need to do is output your data in CSV format, i.e. separate values by commas and a new line is a new row. It would also be smart to escape the values with quotation marks (not shown in my code).

HTML to CSV PHP

I've been trying to export MySQL fields to CSV and can get all them exporting correctly except the filed which contains HTML.
My MySQL table is made up as follows:
Name: Address: Profile:
Name is simply text as with address, but profile is HTML
My array is:
$array = array ( array ( "Name" => "$name", "Address" => "$address", "Profile" => $profile )
);
Made using:
$name = $info['name'];
$address = $info['address'];
$profile = $info['profile'];
I have a "Tab" \t delimiter and every exports into the CSV correctly bar the HTML which I would like to keep as pure HTML but in one Excel field, at the moment is splits across multi rows and fields.
CSV code is as follows:
header("Content-type: application/octet-stream");
header("Content-Disposition: attachment; filename=$filename");
header("Pragma: no-cache");
header("Expires: 0");
$titleArray = array_keys($array[0]);
$delimiter = "\t";
$filename="profiles.xls";
foreach ($array as $subArrayKey => $subArray) {
$dataRowString = implode($delimiter, $subArray);
print $dataRowString . "\r\n";
}
Any help or advise would be highly welcomed.
You need to escape the field values. You can use fputcsv:
$stdout = fopen('php://stdout', 'w');
fputcsv($stdout, $subArray, "\t");
$filename="profiles.xls";
header("Content-type: application/octet-stream");
header("Content-Disposition: attachment; filename=$filename");
header("Pragma: no-cache");
header("Expires: 0");
$titleArray = array_keys($array[0]);
$delimiter = "\t";
$stdout = fopen('php://stdout', 'w');
foreach ($array as $subArrayKey => $subArray) {
fputcsv($stdout, $subArray, $delimiter);
}

File download for csv works in local host but not when live

I am creating a csv file from nested array and it works fine with a download link to the csv file in the localhost, but on live host it won't download. This is what is in my php file:
The headers declared:
/**
* Declare headers for CSV
*/
header("Content-type: text/csv");
header("Content-Disposition: attachment; filename=registration.csv");
header("Pragma: no-cache");
header("Expires: 0");
The Function that outputs the csv file:
/**
* Function will output the scsv file
* #param the csv $data in nested array form array(array("","",""),array("",""...)...)
*/
function outputCSV($data) {
$outstream = fopen("php://output", "w");
function __outputCSV(&$vals, $key, $filehandler) {
fputcsv($filehandler, $vals); // add parameters if you want
}
array_walk($data, "__outputCSV", $outstream);
fclose($outstream);
}
The link that I used in local:
Download CSV
Won't work on Live site. Instead of downloading it just takes me to the csv.php page and outputs the array in a string like this.
...ID,"Coach One","Coach Two",Work,Cell,Email,...
Try hardcoding the csv into the code. Replace these lines with the ones you have to see if your data being passed has bad characters. Maybe specifying the charset will help.
header('Content-Type: text/csv; charset=utf-8');
header('Content-Disposition: attachment; filename=data.csv');
$output = fopen('php://output', 'w');
fputcsv($output, array('Column 1', 'Column 2', 'Column 3'));
As described here:
http://code.stephenmorley.org/php/creating-downloadable-csv-files/
I'm not setup to really debug your code. You can try this though if you like. I know it works.
$out = fopen("php://temp", 'r+');
while (($row = $res->fetch(Zend_Db::FETCH_NUM)) != false) {
fputcsv($out, $row, ',', '"');
}
rewind($out);
$csv = stream_get_contents($out);
header("Content-Type: application/csv;");
header("Content-Disposition: attachment; filename=\"foo.csv\"");
header("Pragma: no-cache");
header("Expires: 0");
echo $csv;
exit(0);
Adjust the loop as needed to iterate on your results.

php://output results in empty file

I have a Wordpress theme template file in use by a page. The template queries the db for an array and then attempts to output the result to a csv file. No output to the browser is expected. Here is code:
/***
* Output an array to a CSV file
*/
function download_csv_results($results, $name = NULL)
{
if( ! $name)
{
$name = md5(uniqid() . microtime(TRUE) . mt_rand()). '.csv';
}
header('Content-Type: text/csv');
header('Content-Disposition: attachment; filename='. $name);
header('Pragma: no-cache');
header("Expires: 0");
$outstream = fopen("php://output", "w");
foreach($results as $result)
{
fputcsv($outstream, $result);
}
fclose($outstream);
}
The file is written to the user's downloads directory as expected, but it is empty. I've debugged to verify there is a result of 117 elements. The loop above is executing. It's as though the output buffer is not being flushed or is being cleared by Wordpress.
Could you try to use :
$outstream = fopen("php://output", "a");
instead of :
$outstream = fopen("php://output", "w");

Categories