Сохраните PDF, созданный с помощью библиотеки FPDFp php, в поле большого двоичного объекта MySQL. - PullRequest
3 голосов
/ 20 августа 2009

Мне нужно создать файл PDF с библиотекой fpdf и сохранить его в поле BLOB-объекта в моей базе данных MySQL. Проблема заключается в том, что когда я пытаюсь извлечь файл из поля большого двоичного объекта и отправить его в браузер для загрузки, загруженный файл поврежден и не отображается правильно.

Тот же файл PDF отображается правильно, если я немедленно отправляю его в браузер, не сохраняя его в БД, поэтому кажется, что некоторые данные будут повреждены при вставке в БД.

Мой код примерно такой:

$pdf = new MyPDF(); //class that extends FPDF and create te pdf file
$content = $pdf->Output("", "S"); //return the pdf file content as string
$sql = "insert into mytable(myblobfield) values('".addslashes($content)."')";
mysql_query($sql);

для хранения PDF, и вот так:

$sql = "select myblobfield from mytable where id = '1'";
$result = mysql_query($sql);
$rs = mysql_fetch_assoc($result);
$content = stripslashes($rs['myblobfield']);
header('Content-Type: application/pdf');
header("Content-Length: ".strlen(content));
header('Content-Disposition: attachment; filename=myfile.pdf');
print $content;

чтобы отправить его в браузер для скачивания. Что я делаю не так?

Если я изменю свой код на:

$pdf = new MyPDF(); 
$pdf->Output(); //send the pdf to the browser

файл отображается правильно, поэтому я предполагаю, что он правильно сгенерирован, и проблема заключается в сохранении в БД.

Заранее спасибо.

Ответы [ 6 ]

3 голосов
/ 20 августа 2009

На самом деле по соображениям безопасности:

  1. Не используйте addslashes(), но используйте mysql_real_escape_string() вместо

В данном конкретном случае (поскольку это двоичные данные):

  1. Удалить stripslashes()
  2. Заменить addslashes() на mysql_real_escape_string()
2 голосов
/ 20 августа 2009

Вы не должны снимать (обратно) косые черты. Когда вы добавляете их, они используются в качестве escape-символов в запросе и не отображаются в поле.

Попробуйте изменить это

$content = stripslashes($rs['myblobfield']);

в это:

$content = $rs['myblobfield'];
1 голос
/ 13 ноября 2010

Замена

header("Content-Length: ".strlen(content)); 

с

header("Content-Length: ".strlen($content)); 

работал для меня.

1 голос
/ 20 августа 2009

Сравните различия в строках, чтобы помочь отладить проблему.

$pdf = new MyPDF();
echo $pdf->Output("", "S"); //send the pdf string to the browser
exit;

и

$pdf = new MyPDF(); //class that extends FPDF and create te pdf file
$content = $pdf->Output("", "S"); //return the pdf file content as string
$sql = "insert into mytable(myblobfield) values('".addslashes($content)."')";
mysql_query($sql);
$sql = "select myblobfield from mytable where id = '1'";
$result = mysql_query($sql);
$rs = mysql_fetch_assoc($result);
$content = stripslashes($rs['myblobfield']);
echo $content; //send the pdf string to the browser
exit;
0 голосов
/ 17 ноября 2016

Я недавно работал с этой проблемой, и важно дать ответ после предоставленных нами тестовых решений.Затем я решил эту проблему следующим образом. Для сохранения сгенерированного fpdf я использовал этот код .. :

$content = $pdf->Output("", "S"); 
// addslashes is the key to store blob file
$data = addslashes($content); 
$name = "testname.pdf";
$mime = "application/pdf";
$extficheiro = "pdf";
$nomeficheiro = "miarchivo";
$size = strlen($content);
$query = "INSERT INTO filetable(name, mime, size, data, created)
    VALUES ('$name','$mime', '$size', '$data', NOW())";                      
$conn->query($query);

Для чтения (извлечения из базы данных) из моей базы данных было предпочтительнее использовать код pdo:

if(filter_has_var(INPUT_GET, "var") !== false && filter_input(INPUT_GET, 'var', FILTER_VALIDATE_INT) !== false)
{
    $var = filter_input(INPUT_GET, "var", FILTER_SANITIZE_NUMBER_INT);
    try     {
        $dbh = new PDO("mysql:host=our_host;dbname=database", 'username', 'password');
        $dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

        $sql = "SELECT * FROM filetable  WHERE id= ".$var;

        $stmt = $dbh->prepare($sql);
        $stmt->execute(); 
        $stmt->setFetchMode(PDO::FETCH_ASSOC);
        $array = $stmt->fetch();

        /*** set the headers and display the file ***/
        header("Content-Type: ". $array['mime']);
        header("Content-Length: ". $array['size']);/**/
        header("Content-Disposition: inline; filename='". ($array['name'])."'");
        echo $array['data'];
    }
    catch(PDOException $e)
    {
        echo $e->getMessage();
    }
    catch(Exception $e)
    {
        echo $e->getMessage();
    }
}
else
{
    echo '0'; // out of bounds
}

Эти коды работали отлично.Я надеюсь, что этот вклад поможет другим снять головную боль с этой проблемой.С наилучшими пожеланиями.

0 голосов
/ 12 июля 2010

РЕШЕНО!

У меня тоже была та же проблема, и я пробовал вышеупомянутые идеи. Что исправило это для меня, так это то, что моя база данных MySQL хранила PDF как blob вместо mediumblob. Поле большого двоичного объекта ограничено 64 КБ, поэтому оно обрезало оставшуюся часть моего PDF-файла, содержащего ценные данные, включая EOF (отсюда и неприятную ошибку Adobe).

Для подтверждения загрузите файл PDF, который он обслуживает, и посмотрите на размер файла. Если это ровно 64 КБ, вам нужно освободить больше места в БД, установив для поля значение mediumblob.

Спасибо всем за помощь!

Кстати, я последовал совету Тото и вместо него использовал mysql_real_escape_string() вместе с:

  1. Удалить stripslashes()
  2. Заменить addslashes() на mysql_real_escape_string()

С этими изменениями в исходном коде плаката это сработало!

...