A downloadable PDF from database - php

I have a database table which stores the document file name and on the local pc i have a folder named as uploads which stores the actual files the user uploads.
The way i upload files are as follows,
$filename = $_FILES['attachment']['name'];
// destination of the file on the server
$destination = 'uploads/' . $filename;
// get the file extension
$extension = pathinfo($filename, PATHINFO_EXTENSION);
// the physical file on a temporary uploads directory on the server
$file = $_FILES['attachment']['tmp_name'];
$size = $_FILES['attachment']['size'];
if (!in_array($extension, ['zip', 'pdf', 'docx'])) {
echo "You file extension must be .zip, .pdf or .docx";
} elseif ($_FILES['attachment']['size'] > 1000000) { // file shouldn't be larger than 1Megabyte
echo "File too large!";
} else {
// move the uploaded (temporary) file to the specified destination
if (move_uploaded_file($file, $destination)) {
$sender_name = $_POST['sender_name'];
$contact = $_POST['contactnumber'];
$sender_mail = $_POST['sender_email'];
$description = $_POST['description'];
$applied = date('Y-m-d');
$jobapply = "INSERT INTO `job_submission`(`NAME`, `CONTACT`, `EMAIL`, `MESSAGE`,
`APPLIED_ON`, `CAREER_ID`,`CV`) VALUES
('$sender_name','$contact','$sender_mail','$description','$applied','$idc','$filename')";
if (mysqli_query($connect, $jobapply)) {
echo "You Application Was Submitted Successfully! We Wish You All The Best";
}
} else {
echo "Failed to upload file.";
}
}
The results of this code is the file name along with the other data are stored in the database and on the other hand the file is also stored in the uploads directory.
Now i want to download the file stored in the folder to the machine by using a button. for which I have written a code as follows,
if (isset($_GET['file_id'])) {
$id = $_GET['file_id'];
// fetch file to download from database
$sql = "SELECT * FROM job_submission WHERE JOB_ID='$id'";
$result = mysqli_query($connect, $sql);
$file = mysqli_fetch_assoc($result);
$filepath = 'uploads/' . $file['CV'];
if (file_exists($filepath)) {
header('Content-Description: File Transfer');
header('Content-Type: application/octet-stream');
header('Content-Disposition: attachment; filename=' . basename($filepath));
header('Expires: 0');
header('Cache-Control: must-revalidate');
header('Pragma: public');
header('Content-Length: ' . filesize('uploads/' . $file['CV']));
readfile('uploads/' . $file['CV']);
exit;
}
}
The above code is called from a button inside a table,
<td>Download </td>
The file gets downloaded but it doesn't open and throws an error saying
Error Failed to load PDF document.

Related

php can't open pdf after downloading

in my project I need to upload pdf file and download it afterwards.
everything works fine , but after i download the pdf file its been currupted and i can't view it.
if i try to open it with Adobe Acrobat Reader i get this error that says the file been currupted and didn't encoded correctly.
can someone help me to resolve this? thanks!
php script for download and upload:
<?php
// connect to the database
require_once 'connectionoop.php';
require_once 'core/init.php';
$query1 = sprintf("SELECT files.id, files.name,files.size ,files.downloads , association.Aname ,projects.Pname,files.project
FROM files
INNER JOIN projects ON files.project = projects.id INNER JOIN association ON projects.Aid = association.id
");
$result1 = $mysqli->query($query1);
$files=array();
foreach ($result1 as $row) {
$files[] = $row;
}
// Uploads files
if (isset($_POST['save'])) { // if save button on the form is clicked
// name of the uploaded file
$filename = $_FILES['myfile']['name'];
$proj = $_POST['Aid'];
// destination of the file on the server
$destination = 'uploads/' . $filename;
// get the file extension
$extension = pathinfo($filename, PATHINFO_EXTENSION);
// the physical file on a temporary uploads directory on the server
$file = $_FILES['myfile']['tmp_name'];
$size = $_FILES['myfile']['size'];
if (!in_array($extension, ['zip', 'pdf', 'docx'])) {
echo "You file extension must be .zip, .pdf or .docx";
} elseif ($_FILES['myfile']['size'] > 1000000) { // file shouldn't be larger than 1Megabyte
echo "File too large!";
} else {
// move the uploaded (temporary) file to the specified destination
if (copy($file, $destination)) {
$query = sprintf("INSERT INTO files (name, size, downloads , project) VALUES ('$filename', $size, 0,$proj)");
//execute query
$result = $mysqli->query($query);
$sql = "INSERT INTO files (name, size, downloads) VALUES ('$filename', $size, 0)";
$pr=new Project($proj);
$pr->update(array(
'hasfile' =>1
));
Redirect::to('downloads.php');
} else {
echo "Failed to upload file.<br>".$destination;
}
}
}
if (isset($_GET['file_id'])) {
$id = $_GET['file_id'];
$query2 = sprintf("SELECT * FROM files WHERE id=$id");
// fetch file to download from database
$result2 = $mysqli->query($query2);
$data = array();
foreach ($result2 as $row) {
$data[] = $row;
}
$filepath = 'uploads/' .$data[0]['name'];
if (file_exists($filepath)) {
header('Content-Description: File Transfer');
header('Content-Type: application/octet-stream');
header('Content-Disposition: attachment; filename=' . basename($filepath));
header('Expires: 0');
header('Cache-Control: must-revalidate');
header('Pragma: public');
header('Content-Length: ' . filesize('uploads/' . $data['name']));
readfile('uploads/' . $data['name']);
// Now update downloads count
$newCount = $data['downloads'] + 1;
$query3 = sprintf("UPDATE files SET downloads=$newCount WHERE id=$id");
// fetch file to download from database
$result3 = $mysqli->query($query3);
exit;
}
}
It should be header("Content-type:application/pdf");

PHP Zip unable to close()

I'm trying to get a couple files from wordpress /uploads folder using php and I get this error:
Warning: ZipArchive::close(): Can't remove file: No such file or directory in /www/public_html/wp-content/plugins/insert-php-code-snippet/shortcode-handler.php(65) : eval()'d code on line 32 (relative to $zip->close(); and bellow "if")
I use a plugin to inject PHP on the page.
I basically have a couple dozens checkboxes that when I press "Generate", it gets the name of the file like 07/2019/blabla (with code I get uploads folder + extension, checkbox only hold the media location + name file).
I checked and it's creating the Zip on /uploads, .pdf files exist but it crashes on the close part and when I download and try to extract I get the archive is either in unknown format or damaged
Any advise please?
if(isset($_POST['files'])) {
$error = ""; //error holder
$upload_dir = wp_upload_dir();
if(isset($_POST['createzip'])){
$post = $_POST;
if(isset($post['files']) and count($post['files']) > 0){
// open zip
$zip_file = $upload_dir['basedir'].'/'.time().".zip";
$zip_name = time().".zip";
$zip = new ZipArchive();
if ($zip->open($zip_file, ZIPARCHIVE::CREATE | ZIPARCHIVE::OVERWRITE) !== TRUE) {
$error .= ("An error occurred creating your ZIP file.<br>");
}
foreach ($post['files'] as $file) {
// generate filename to add to zip
$filepath = $upload_dir['basedir'].'/' . $file . '.pdf';
if (file_exists($filepath)) {
$zip->addFile($filepath) or $error .= ("ERROR: Could not add the file $filename<br>");
} else {
$error .= ("File $filepath doesnt exit.<br>");
}
}
$zip->close();
if ($zip->close() !== true ) {
die($zip->getStatusString()."\n");
}
if(file_exists($zip_file)){
$error .= $zip_file;
ob_end_clean();
// push to download the zip
header('Content-type: application/zip');
header('Content-Disposition: attachment; filename="'.$zip_name.'"');
header("Content-Length: " . filesize($zip_file));
readfile($zip_file);
unlink($zip_file);
}
}
}
}
echo $error;
After $zip->close(); I replaced all code for this:
if(file_exists($zip_file)){
header($_SERVER['SERVER_PROTOCOL'].' 200 OK');
header("Content-Type: application/zip");
header("Content-Transfer-Encoding: Binary");
header("Content-Length: ".filesize($zip_file));
header("Content-Disposition: attachment; filename=\"".basename($zip_file)."\"");
readfile($zip_file);
unlink($zip_file);
exit;
}

How can I show a PDF return from sftp-get from PHPSECLIB

I want to show to the user a PDF or a PNG that is in my SFTP server.
I am doing the connection with phpseclib to get the file.
How can I manipulate the file to show it in the browser?
$key = new RSA();
$key->loadKey(file_get_contents('*******'));
$sftp = new SFTP($fsock);
if (!$sftp->login('*******', $key)) {
exit('Bad credentials!');
}
$path = "******";
$filename = $result[0]->filefinalname ;
$file = $sftp->get($path . $filename);
Send Content-Type and file content
$file = '/path/to/temp/dir/'.uniqid(rand(), true); //temp name
file_put_contents($file,$sftp->get($path . $filename)); // save temp file
if (exif_imagetype($file)) //if this image
header("Content-Type: image/png"); //type file png
else
header("Content-type:application/pdf"); //type file pdf
header('Content-Length: ' . filesize($file)); //send size
readfile($file); //send file
unlink($file); //delete temp file

PDF not downloading when file is called

I have a database that is storing all my pdf files for a website. The table has columns for the library_item_id, filename(name of the file), mime_type, File size, file_item(the Blob) and I have a php file called download.php. This file is supposed to download the correct file from the database when they user clicks the link. But when the file is downloaded and clicked to open I get Adobe saying it cannot open the pdf. Saying its not decoded correctly. Here is my download.php file:
require_once("scripts/connection.php");
if(isset($_GET["id"])){
$fid = $_GET["id"];
}
else{
header("Location: literature.php");
}
$sql= "SELECT filename, mime_type, file_item FROM library_items WHERE library_item_id = ?";
$stmt = $conn->prepare($sql);
$stmt->bind_param('s', $fid);
$stmt->execute();
$stmt->bind_result($filename, $mime, $file_item);
while($stmt->fetch()){
$file_name = $filename;
$mime_type = $mime;
$file = $file_item;
}
header("Content-length: ".strlen($file));
header("Content-type: $mime_type");
header("Content-disposition: download; filename=$file_name");
echo $file;
mysqli_close($conn);
I have tried everything I could think of including add the obj_flush() commands and all that it still gives me the same error. What am I doing wrong on this?
Here is the edit for the code inserting the file into the database.
session_start();
$display = trim($_POST["file-display-name"]);
$company = trim($_POST["companies"]);
$lib_cat = trim($_POST["library-cats"]);
if(empty($display) || empty($company) || empty($lib_cat)){
$_SESSION["errormsg"] = "Required information is missing please fill out all required fields.";
header("Location: ../library.php");
}
else{
$file_name = $_FILES['library-file']['name'];
$tmp_name = $_FILES['library-file']['tmp_name'];
$file_size = $_FILES['library-file']['size'];
$file_type = $_FILES['library-file']['type'];
$fp = fopen($tmp_name, 'r');
$content = fread($fp, filesize($tmp_name));
$content = addslashes($content);
fclose($fp);
if(!get_magic_quotes_gpc()){
$file_name = addslashes($file_name);
}
if(empty($content)){
$_SESSION["errormsg"] = "Required information is missing please fill out all required fields.";
header("Location: ../library.php");
}
else{
require_once("connection.php");
// Insert the logo into the companies photo table
$sql = "INSERT INTO library_items(filename, mime_type, file_size, file_item, display_name, company_id, library_category_id) VALUES(?,?,?,?,?,?,?)";
$stmt = $conn->prepare($sql);
$stmt->bind_param('sssssss', $file_name, $file_type, $file_size, $content, $display, $company, $lib_cat);
if(!$stmt->execute()){
$_SESSION["errormsg"] = "Failed to add library item: ".mysqli_error();
header("Location: ../library.php");
}
}
unset($_SESSION["errormsg"]);
$_SESSION["successmsg"] = "Library Item successfully added into the database.";
header("Location: ../library.php");
}
UPDATE:
I now have the file downloading and attempting to display once the downloaded file is double clicked to open. It is telling me there is an invalid colorSpace. From what I can tell this is a problem when the file is uploaded into the database. From my upload file posted is there anything I am not doing correctly?
You need following changes. In the insert file
Instead of
$content = addslashes($content);
use
$content = base64_encode($content);
So while downloading, decode it.
$file = base64_decode($file_item);
Replace the following code
header("Content-type: '".$mime_type."'");
header("Content-Disposition: inline; filename='".$file_name."'");
header('Content-Transfer-Encoding: binary');
header('Accept-Ranges: bytes');
readfile($file);
with
header("Content-length: ".strlen($file));
header("Content-type: $mime_type");
header("Content-disposition: download; filename=$file_name");
echo $file;
check if size of downloaded file is correct (matches size of file in database). If it is, you should be debugging the part where the file is inserted into database. If not - check if anything gets printed out before sending file to browser - maybe scripts/connection.php prints something like empty line, error message or BOM?
If you can't find it, try turning output buffering on and call ob_clean() before sending file.
Sorry for my english, I hope it's understandable.

Cant upload and store the image to the database by using php

I try to build an upload image system by using php.After testing it,the system echo out"Image is uploaded",but it doesn't shown in database.Here is my code here
upload.php
<?php
//connect database
include('config.php');
//file properties
if(isset($_FILES['image'])){
$file = $_FILES['image']['tmp_name'];
}
if(!isset($file)){
echo "Please select an image";
}
else{
$image = addslashes(file_get_contents($_FILES['image']['tmp_name']));
$image_name =addslashes($_FILES['image']['name']);
$image_size =getimagesize($_FILES['image']['tmp_name']);
if ($image_size == FALSE) {
echo "This is not an image";
}
else{
$insert = "INSERT INTO image(name,picture) VALUES ('$image_name','$image')";
if(!$insert){
echo "Problem uploading";
}
else {
$lastid =mysqli_insert_id($con);
echo "Image Uploaded <p />Your Image :<p /><img src=get.php?id=$lastid>";
}
}
}
?>
get.php
<?php
include ('config.php');
$id = addslashes($_REQUEST['id']);
$image = mysqli_query($con ,"SELECT * FROM image WHERE id=$id");
$image = mysqli_fetch_assoc($image);
$image = $image['picture'];
header("Content-type :image/jpeg");
?>
and I clicking the submit button without choosing any files this 2 line of warning is showing up
Warning: file_get_contents(): Filename cannot be empty in upload.php line 14.
line14 is this $image = addslashes(file_get_contents($_FILES['image']['tmp_name']));
Warning: getimagesize(): Filename cannot be empty in in upload.php line 16.
while line 16 is this $image = addslashes(file_get_contents($_FILES['image']['tmp_name']));
Any idea about this?
You need a function to send your query, otherwise you just filled up a string: this:
$insert = "INSERT INTO image(name,picture) VALUES ('$image_name','$image')";
should be followed by this:
mysqli_query($con, $insert);
The warnings are caused by multiple issues with your code. First you are checking whether the file has been uploaded in the wrong way: this
if(isset($_FILES['image'])){
$file = $_FILES['image']['tmp_name'];
}
Will always set a $file variable, even though no file has been selected into the form, leading therefore to never execute this if statement:
if(!isset($file)){
echo "Please select an image";
}
and to always execute what's in the else block instead, which causes the errors, because the functions you mentioned, which are contained in this else block, are not able to operate on any file.
Therefore simply checking the file upload correctly will solve the issue: one way to do this would be to first remove this, which is unuseful
if(isset($_FILES['image'])){
$file = $_FILES['image']['tmp_name'];
}
and then change this:
if(!isset($file)){
echo "Please select an image";
}
to this:
if(!isset($_FILES['image']['tmp_name'])){
echo "Please select an image";
}
After line 16 you need to echo the image data.
echo $image;
#ken, here is a function that I use to output the image by setting the correct headers:
function output_headers($filetype, $imgsize, $filename, $attachment=false)
{
header("Content-Type: {$filetype}");
header("Pragma: public");
header("Cache-Control: public");
header("Cache-Control: must-revalidate");
$offset = 60 * 60 * 24 * 4 -1;
$ExpStr = "Expires: " . gmdate("D, d M Y H:i:s", time() + $offset) . " GMT";
header($ExpStr);
header("Cache-Control: max-age=$offset");
//header("Content-Type: application/octet-stream");
header('Accept-Ranges: bytes');
header("Content-Length: $imgsize");
#insert the filename we want into the image so it can be saved with something
# more meaningful that showimg.jpg. :-)
# 04/03/06
#attachment causes save as to appear, inline serves imbedded image.
if ($attachment)
header('Content-Disposition: attachment; filename="' . $filename . '"');
else
header('Content-Disposition: inline; filename="' . $filename . '"');
}
This is part of a php file called showimg.php.jpg
This needs to be saved into a separate directory with the following .htaccess file to get php to handle requests for .jpgs:
AddType application/x-httpd-php .jpg
In this way, the webpage refers to the image <img src='/img/showimg.php.jpg?<add your parameters here>
regards
Steve

Categories