My code kinda weird, i don't know what would be the problem of my code.. here's my code.
$project_name = $_POST['project_name'];//example the retrieved data is Testing Project
$quote_id = $_POST['quote_id'];//example the retrieved data is 34425
$date = date("M/d/y");
$as_agent = $_POST['as_agent'];//example the retrieved data is John Doe
$name_for_project = $project_name.' '.$quote_id.' '.$date.' '.$as_agent;
header("Content-Type: application/vnd.ms-excel");
header("Expires: 0");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("content-disposition: attachment;filename='".$name_for_project.".xls'");
ob_start();
//The rest of the code is Workbook
echo"
<?xml version='1.0'?>
<?mso-application progid='Excel.Sheet'?>
<Workbook
xmlns='urn:schemas-microsoft-com:office:spreadsheet'
xmlns:o='urn:schemas-microsoft-com:office:office'
xmlns:x='urn:schemas-microsoft-com:office:excel'
xmlns:ss='urn:schemas-microsoft-com:office:spreadsheet'
xmlns:html='http://www.w3.org/TR/REC-html40'>
<DocumentProperties xmlns='urn:schemas-microsoft-com:office:office'>
<Version>11.8036</Version>
</DocumentProperties>
<ExcelWorkbook xmlns='urn:schemas-microsoft-com:office:excel'>
<WindowHeight>6795</WindowHeight>
<WindowWidth>8460</WindowWidth>
<WindowTopX>120</WindowTopX>
<WindowTopY>15</WindowTopY>
<ProtectStructure>False</ProtectStructure>
<ProtectWindows>False</ProtectWindows>
</ExcelWorkbook>";
//so on and so fort...
When this code runs it only capture the $project_name value.. Please Help me... Thank you..
The following line header("... will prompt to save a file with apostrophes to the beginning and end of the file.
Example: 'project_quote_id_2013-08-31_as_agent.xls'
header("content-disposition: attachment;filename='".$name_for_project.".xls'");
which should be changed to:
header("content-disposition: attachment;filename=".$name_for_project.".xls");
The code below will produce/echo a saveable file called: project_quote_id_2013-08-31_as_agent.xls (as of today's date for testing).
If, and as Aiden stated in his answer, you are using slashes as your seperator for your $date variable, you will encounter problems.
Try to avoid using spaces for seperators, use hyphens and/or underscores to seperate your values.
For example, this will save to prompt to a file with some dummy content.
<?php
$date = gmdate('Y-m-d', time() - 3600 * $hours);
$project_name = "project";
$quote_id = "quote_id";
$as_agent = "as_agent";
$name_for_project = $project_name.'_'.$quote_id.'_'.$date.'_'.$as_agent;
$file = $name_for_project.".xls";
// start buffering
ob_start();
// sample dynamically generated data
echo '<table border="1"> ';
echo '<tr><th>Name</th><th>Age</th></tr>';
for ($i=0; $i<=5; $i++) { echo "<tr><td>Name$i</td><td>".($i+1)."</td></tr>";
}
echo '</table>';
$content = ob_get_contents();
ob_end_clean();
header("Expires: 0");
header("Last-Modified: " . gmdate("D, d M Y H:i:s") . " GMT");
header("Cache-Control: no-store, no-cache, must-revalidate");
header("Cache-Control: post-check=0, pre-check=0", false);
header("Pragma: no-cache");
header("Content-type: application/vnd.ms-excel;charset:UTF-8");
header('Content-length: '.strlen($content));
header('Content-disposition: attachment; filename='.basename($file));
// output all contents
echo $content;
exit;
?>
will produce a file called: project_quote_id_2013-08-31_as_agent.xls (as of today's testing date) and will prompt the user to save it under that name.
The rest of the code that is to insert the actual content, will need to be inserted accordingly, because there was nothing else posted in regards to variables or text associated with the question/code.
Do any of your other variables contain invalid characters for a file name? E.g. If you declared your $date as 30/08/2013 then php will not concatenate your variables past the invalid character.
Spaces affect in naming filename. what i do is transform my code into.
$project_name = $_POST['project_name'];//example the retrieved data is Testing Project
$quote_id = $_POST['quote_id'];//example the retrieved data is 34425
$date = date("M/d/y");
$as_agent = $_POST['as_agent'];//example the retrieved data is John Doe
$proj_name = str_replace(' ', '', $project_name);
$as_agent = str_replace(' ', '', $as_agent);
$name_for_project = $proj_name."-".$quote_id."-".$date."-".$as_agent;
header("Content-Type: application/vnd.ms-excel");
header("Expires: 0");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("content-disposition: attachment;filename=$name_for_project.xls");
Thanks to #Fred -ii-
Related
We run queries using CodeIgniter against our MySQL database, and display those results on the page. Sometimes, we want to download those as a CSV. The guy before me set up this download button, but it does not function at all. Never has.
This is the existing code for the download:
public function download_csv_search(){
$dbresults = $this->do_search();
$results = $dbresults['results'];
$csv = "First Name, Last Name, MI, Age, Details(RA), Status, Home Phone, Gender, Notes\n";
$filename = "data_export";
//header('Content-Type: text/csv; charset=utf-8');
//header('Content-Disposition: attachment; filename=data.csv');
//$output = fopen('php://output', 'w');
//fputcsv($output, array('First Name', 'Last Name', 'Middle Name', 'DOB', 'Details(RA)', 'Status', 'Home Phone', 'Gender', 'Notes'));
foreach($results as $result) {
$birthday_timestamp = strtotime($result->VoterDOB);
$age = date('md', $birthday_timestamp) > date('md') ? date('Y') - date('Y', $birthday_timestamp) - 1 : date('Y') - date('Y', $birthday_timestamp);
$csv .= $result->VoterFN.",".$result->VoterLN.",".$result->VoterMN.",".$dob.",".$result->Street.",".$result->VoterStatusID.",".$result->phone.",N/A,\n";
// $dataArray = array('VoterFN'=>$result->VoterFN, 'VoterLN'=>$result->$VoterLN, 'VoterMN'=>$result->VoterMN,'VoterDOB'=>$result->date('m/d/Y', strtotime($result->VoterDOB)), 'Street'=>$result->Street, "VoterStatusID"=>$result->VoterStatusID,'phone'=>$result->phone);
//fputcsv($output, $dataArray);
}
//OUPUT HEADERS
header("Pragma: public");
header("Expires: 0");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("Cache-Control: private",false);
header("Content-Type: application/octet-stream");
header("Content-Disposition: attachment; filename=\"$filename.csv\";" );
header("Content-Transfer-Encoding: binary");
//OUTPUT CSV CONTENT
echo($csv);
exit();
}
I'm guessing I need to use the download helper + the force_download function, but I can't seem to get it. Any ideas?
I think you have so many headers, but more important, if the file is a CSV, why sending it as a binary file? Why aren't you using text/csv? I only use the following code, I suppose that Cache-Control is to avoid downloading the same file without hit the server. Anyway, only with:
header('Content-type: text/csv');
header("Content-Disposition: attachment; filename=\"$filename.csv\";" );
should work. After a bit of research in SO, depending on what browser you use you may have problems with your Cache headers:
Creating and downloading CSV with PHP, so research a bit that in order to avoid future issues.
I have a simple web page which pulls some data from DB and displays it in a html table and stores the data in some session variables.
I have a button "Export to csv" which calls a page which exports the results to a csv file.
The code for ExportToCsv file is:
<?php
session_start();
include "conn/sqlserverConn.php";
function download_send_headers($filename) {
// disable caching
$now = gmdate("D, d M Y H:i:s");
header("Expires: Tue, 03 Jul 2001 06:00:00 GMT");
header("Cache-Control: max-age=0, no-cache, must-revalidate, proxy-revalidate");
header("Last-Modified: {$now} GMT");
// force download
header("Content-Type: application/force-download");
header("Content-Type: application/octet-stream");
header("Content-Type: application/download");
// disposition / encoding on response body
header("Content-Disposition: attachment;filename={$filename}");
header("Content-Transfer-Encoding: binary");
}
$data = $_SESSION['data'];
$rows = $_SESSION['row'];
$header = $_SESSION['header'];
download_send_headers("data_export_" . date("Y-m-d") . ".csv");
$file = fopen("php://output", 'w');
fputcsv($file,$header);
for($i=0; $i<$rows; ++$i)
{
$valuesArray=array();
foreach($data[$i] as $name => $value)
{
$valuesArray[]=$value;
}
fputcsv($file,$valuesArray);
}
fclose($file);
die();
?>
My code is working flawlessly in firefox but it is not working in chrome or IE. On chrome and IE it is showing error 404 (Object not found!). Please tell me what is the problem ?
As outlined in the blog article at: http://www.exchangecore.com/blog/php-output-array-csv-headers/, I tested the following and it worked in IE8-11, and in chrome version 34. I presume it will work in other browsers fine as well.
Headers to use:
header('Pragma: public');
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Cache-Control: private', false);
header('Content-Type: text/csv');
header('Content-Disposition: attachment;filename=' . $fileName);
I am trying to export some data to CSV using PHP.
My code:
function download_send_headers($filename) {
// disable caching
$now = gmdate("D, d M Y H:i:s");
header("Expires: Tue, 03 Jul 2001 06:00:00 GMT");
header("Cache-Control: max-age=0, no-cache, must-revalidate, proxy-revalidate");
header("Last-Modified: {$now} GMT");
// force download
header("Content-Type: application/force-download");
header("Content-Type: application/octet-stream");
header("Content-Type: application/download");
// disposition / encoding on response body
header("Content-Disposition: attachment;filename={$filename}");
header("Content-Transfer-Encoding: binary");
}
$givenTerm = $_POST['TextBoxList'];
$sql_query = "select * from some_table where key=".$givenTerm;
$result = sqlsrv_query($conn,$sql_query);
$r1 = array();
$file = fopen("php://output", 'w');
while ($row = sqlsrv_fetch_array($result, SQLSRV_FETCH_NUMERIC)){
$valuesArray=array();
foreach($row as $name => $value)
{
$valuesArray[]=$value;
}
fputcsv($file,$valuesArray);
}
fclose($file);
download_send_headers("data_export_" . date("Y-m-d") . ".csv");
die();
Here I am receiving a search-value from a form in another page and then triggering a query based on it. The code is working fine for smaller data-sets(up to 100). But when the number of rows is more in the result (around 600-700) then the code crashes. Please tell me how to fix this.
P.S. I am using Sql Server 2012 for the database.
Instead of first getting all results in a single array and then outputting it, you could also fetch it row by row and outputting each row directly.
That way you won't need the massive amount of memory to fit the entire array in.
I can't get the browser to prompt for download. The output gets displayed on the screen instead. I've tried so many other threads regarding this topic on this site but to no avail. I could change the fopen("php://output","w") to fopen("export.csv","w") but that will save a copy of the export.csv file on the server, which I don't want. I want the file to be downloaded on the client without it being saved on the server. Here's my code:
$sql = mysql_query($_SESSION["export-query"]);
$fields = mysql_num_fields($sql);
$header = array();
for ($i = 0; $i < $fields; $i++) {
$header[] = mysql_field_name($sql, $i);
}
$f = fopen("php://output","w");
header('Content-Type: text/csv');
header('Content-Disposition: attachment; filename=export.csv');
header('Pragma: public');
header('Expires: 0');
header('Cache-Control: must-revalidate');
fputcsv($f, $header);
while ($row = mysql_fetch_row($sql)) {
fputcsv($f, $row);
}
fclose($f);
Please help! Much appreciated.
Your code is really close to mine, but I have this
header("Content-type: application/vnd.ms-excel");
for the content type. I think this works because browsers know how to handle text/csv but they don't know how to handle excel. It will prompt to download because it doesn't open this type of file itself.
I also don't have "must-revalidate," but I don't think that makes a difference.
EDIT:
Here are my full headers, which have worked 100% of the time. There are minor differences from yours, so maybe one of them is the reason.
header("Content-type: application/vnd.ms-excel");
header("Content-disposition: attachment; filename=".$filename.".csv");
header("Pragma: no-cache");
header("Expires: 0");
EDIT 2:
Judging from your comment on your answer, you are putting all of this code as an ajax call inside a div. The reason that doesn't work is that you can only set headers on the initial call to a page. Setting headers on an ajax call will be ignored.
Here is how my system handles csv generation. Because I needed specific information that could vary between different csv files, I put the name of the generator file into the "action" of a form and provided a submit button:
<form action="thegeneratorpage.php" method="get"><fieldset>
<p>Download [...] in .csv (Excel) form. You can narrow by [...].</p>
<!-- code here that allows users to narrow down what is in the csv -->
<input type="submit" value="Download" />
</fieldset></form>
If the information doesn't vary, you can just do this:
Download CSV
All the code we have been discussing would be on thegeneratorpage.php.
Rather than using the fputcsv function, I would suggest just echoing the rows of the CSV file like so (note that the headers I use are slightly different from yours):
header("Pragma: public");
header("Expires: 0");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("Cache-Control: private",false);
header("Content-Type: application/octet-stream");
header("Content-Disposition: attachment; filename={$fileName}");
header("Content-Transfer-Encoding: binary");
while ($row = mysql_fetch_row($sql)) {
// optionally enclose data if necessary
foreach ($row as $k => $v) {
if (strpos($v, ',') !== false) {
$row[$k] = '"' . $v . '"';
}
}
echo implode(',', array_values($row));
}
I have this simple code
<?php
//header info for browser
header("Content-type: application/octet-stream");
header("Content-Disposition: attachment; filename=file.xls");
header("Cache-Control: cache, must-revalidate");
header("Pragma: public");
header("Expires: 0");
echo pack("CCC",0xef,0xbb,0xbf);//utf-8
/* * *****Start of Formatting for Excel****** */
$data = "text1 \t text2 \t";
print($data);
?>
That creates an excel file. My problem is that the \t tab character is not working. Everything is in the first column of the excel file. What is wrong?
I'm use "\r\n" escs not so long:
$data = "text1 \\t text2 \\t";
echo '<pre>';
var_dump($data);
echo '</pre>';
If anyone has the same problem, I found a solution
<?php
//header info for browser
header("Content-type: application/octet-stream");
header("Content-Disposition: attachment; filename=file.xls");
header("Cache-Control: cache, must-revalidate");
header("Pragma: public");
header("Expires: 0");
$data = "text1 \t text2 \t";
$data = mb_convert_encoding($data, 'UTF-16LE', 'UTF-8');
$data = "\xFF\xFE" . $data;
echo $data;
?>