[php] TCPDF ERROR: Some data has already been output, can't send PDF file

I keep receiving this error when trying to add my own array into the code. Here is my array;

$array = array();

while (odbc_fetch_row($rs))
{
$array[] = odbc_result($rs,'Product Name');
} 
$test = print_r($array);

The original code is here. I'm using an example page to try it because I know the example page works fine.

http://www.tcpdf.org/examples/example_001.phps

This code is before the $html variable and when it is set I just add the $test variable into the $html variable. The odbc connection works fine and the example works fine before I add any code but when I run the script I get this error;

Array ( [0] => Test1 [1] => Test2 ) TCPDF ERROR: Some data has already been output, can't send PDF file

And there is also more than 2 items in the Array. Any ideas?

This question is related to php tcpdf

The answer is


Add the function ob_end_clean(); before call the Output function. It worked for me within a custom Wordpress function!

ob_end_clean();
$pdf->Output($pdf_name, 'I');

use ob_end_clean();

$pdf->Output($file, 'I'); to open pdf. It works for me


Just use ob_start(); at the top of the page.


Use ob_start(); at the beginning of your code.


This problem means you have headers. Deletes tags

?>

at the end of your code and make sure not to have whitespace at the beginning.


I had this but unlike the OP I couldn't see any output before the TCPDF error message.

Turns out there was a UTF8 BOM (byte-order-mark) at the very start of my script, before the <?php tag so before I had any chance to call ob_start(). And there was also a UTF8 BOM before the TCPDF error message.


I had the same error but finally I solved it by suppressing PHP errors Just put this code error_reporting(0); at the top of your print page

    <?php 
    error_reporting(0); //hide php errors
    if( ! defined('BASEPATH')) exit('No direct script access allowed');
    require_once dirname(__FILE__) . '/tohtml/tcpdf/tcpdf.php';
    .... //continue

I had this weird error and the culprit is a white space on the beginning of the PHP open tag

even without the ob_flush and ob_end_clean

Just make sure there are no extra white spaces on or after any <?php ?> block


I just want to add that I was getting this error, and nothing would fix it until I changed the Output destination parameter from F to FI. In other words, I have to output to both file and inline.

Output('doc.pdf', 'I')

to

Output('doc.pdf', 'FI')

I have no idea why this made the difference, but it fixed the error for me...


For those who are still facing this issue try adding:

libxml_use_internal_errors(true);

before the loadHtml call and add

libxml_use_internal_errors(false);

after the call.

This solved it for me.


The tcpdf file that causes the "data has already been output" is in the tcpdf folder called tcpdf.php. You can modify it:

add the line ob_end_clean(); as below (3rd last line):

public function Output($name='doc.pdf', $dest='I') {
    //LOTS OF CODE HERE....}
    switch($dest) {
        case 'I': {
        // Send PDF to the standard output
        if (ob_get_contents()) {
        $this->Error('Some data has already been output, can\'t send PDF file');}
        //some code here....}
            case 'D': {         // download PDF as file
        if (ob_get_contents()) {
    $this->Error('Some data has already been output, can\'t send PDF file');}
            break;}
        case 'F':
        case 'FI':
        case 'FD': {
            // save PDF to a local file
                 //LOTS OF CODE HERE.....       break;}
        case 'E': {
            // return PDF as base64 mime email attachment)
        case 'S': {
            // returns PDF as a string
            return $this->getBuffer();
        }
        default: {
            $this->Error('Incorrect output destination: '.$dest);
        }
    }
           ob_end_clean(); //add this line here 
    return '';
}

Now lets look at your code.
I see you have $rs and $sql mixed up. These are 2 different things working together.

$conn=odbc_connect('northwind','****','*****');
if (!$conn) {
   exit("Connection Failed: " . $conn);
 }

$sql="SELECT * FROM products"; //is products your table name?
$rs=odbc_exec($conn,$sql);
if (!$rs) {
  exit("Error in SQL");
}

while (odbc_fetch_row($rs)) {
  $prodname=odbc_result($rs,"Product Name"); //but preferably never use spaces for table names.
 $prodid=odbc_result($rs,"ProdID");  //prodID is assumed attribute
  echo "$prodname";
  echo "$prodid";
}
odbc_close($conn);

now you can use the $prodname and output it to the TCPDF output.  

and I assume your are connecting to a MS access database.


The error of "Some data has already been output, can't send PDF file" refers to the output buffer of PHP.

so you need to clean any content of the output buffer before sending output.

ob_end_clean(); // Clean any content of the output buffer

then

$pdf->Output('example_001.pdf', 'I'); // Send the PDF !

This problem is when apache/php show errors.

This data(html) destroy pdf output.

You must off display errors in php.ini.


for my case Footer method was having malformed html code (missing td) causing error on osx.

public function Footer() {
$this->SetY(-40);
$html = <<<EOD
<table>
<tr>
 Test Data
</tr>
</table>
EOD;
$this->writeHTML($html);
}

Add the function ob_end_clean() before call the Output function.