Unable to upload pdf file: Php - javascript

The issue I'm facing is, I get the following error while trying to upload some pdfs your upload file is not PDF file. However, this error doesn't show up for all pdfs, it's only for some pdf files I get this error.
<?php
$error = $_FILES['fileToUpload']['error'];
//get upload file type
$type = $_FILES['fileToUpload']['type'];
$action = "upload";
//get file name
$picname = $_FILES['fileToUpload']['name'];
$nameArray = explode(".", $picname);
if {
//check files
//filetoUpload code
}
?>
The issue is that, in the url: '../controller/uploadFile.php' even if the file is PDF, $type = $_FILES['fileToUpload']['type']; will return empty and then it will go into the condition else if($type !="application/pdf" ) and pop up the alert your upload file is not PDF file.. Like I said, this issue is with most of the pdf file. However, some pdf files manage to get uploaded without any issue and if a pdf file gets uploaded, then $type will be application/pdf.
Your input will be highly appriciated.
---UPDATE---
The issue is with $_FILES, it's not fetching the pdf file details for some reason
The issue has been resolved. I checked '$error= $_FILES['fileToUpload']['error']; and the value was returning 1
Value: 1; The uploaded file exceeds the upload_max_filesize directive in php.ini.```

You could better check the extension, this also prevents malicious users to upload exe or zip files when they provide the header Content-Type: application/pdf. Also not all browsers/api libraries specify a Content-Type.
If your filename does not contain a path, check it with a regex so people cannot upload files to directories they shouldn't (ex ../../cache/exe). use for example
preg_match("/^[a-zA-Z0-9_+\\- ]+\\.pdf$/", $filename) to check if it is a pdf.
Do never do unlink('files/' . $filename); when $filename could be anything submitted by the user. Delete ../index.php could destroy your server.

Related

Creating PHP backend for file upload using filepond

I am creating a form on a website, where files (images and pdfs) need to be uploaded too. Until now, I have used a simple input type="file" element, coupled to a PHP file on the backend (snippet follows):
$allowed = array('jpg', 'jpeg', 'pdf', 'png');
if(isset($_FILES['uploadctl']) && $_FILES['uploadctl']['error'] == 0){
$extension = pathinfo($_FILES['uploadctl']['name'], PATHINFO_EXTENSION);
if(!in_array(strtolower($extension), $allowed)){
echo '{"status":"not_allowed"}';
exit;
}
// create folder to upload files to
$id = session_id();
$user_folder = 'user_data/' . $id;
if( is_dir($user_folder) === false ){
mkdir($user_folder);
}
if(move_uploaded_file($_FILES['uploadctl']['tmp_name'], $user_folder . "/" . $_FILES['uploadctl']['name'])){
echo '{"status":"success"}';
exit;
}
echo '{"status":"error"}';
}
This works well. However, I would like more functionality for the upload form and have looked into filepond. I created the filepond object as per the documentation and copied the boilerplate code to ./file-pond-assets, which I plan to adapt to my needs later:
<input type="file" name="uploadctl" multiple accept=".pdf,.png,.jpg,.jpeg">
<script>
const inputElement = document.querySelector('input[type="file"]');
const pond = FilePond.create( inputElement );
pond.setOptions({
server: './file-pond-assets'
});
</script>
which is showing when displaying the website. When trying to upload a file, the front-end looks fine, as an upload complete message appears. However, I cannot find the uploaded files in the tmp and uploads folder inside ./file-pond-assets. I tried changing permissions of the folders and also checked the console, but cannot find an error message. The config.php file also points to the right folders. What do I miss that makes my files not appear on my server? I would like to keep the upload as a multipart/form-data.
Here is a link to my sample file-pond PHP server implementation repository on gihtub
Repo Link: https://github.com/Onihani/filepond-php-server-example
Live Preview: http://www.ics-courses.co.uk/natbongo/filepond-php-server-example/

filesize is changing during download

i have a pdf file that if downloaded through the viewer it downloads at the correct file size but when i use this code for say download selected the file size of the pdf changes and renders it useless when you open with adobe/nitro/etc.
<?php
#apache_setenv('no-gzip', 1);
#ini_set('zlib.output_compression', 'Off');
if (isset($_GET['url'])) {
$fullPath = $_GET['url'];
if($fullPath) {
#$fsize = filesize($fullPath);
$path_parts = pathinfo($fullPath);
$ext = strtolower($path_parts["extension"]);
switch ($ext) {
case "pdf":
header("Content-Disposition: attachment;
filename=\"".$path_parts["basename"]."\""); // use 'attachment' to force a download
header("Content-type: application/pdf"); // add here more headers for diff. extensions
break;
default;
header("Location: ".$fullPath);
exit;
}
if($fsize) {//checking if file size exist
header("Content-length: $fsize");
}
fopen($fsize, "r");
exit;
}
}
?>
i noticed the file size is 24kb on the server. i go to url and view it then click the download from pdf viewer the file downloads just fine and verified the filesize in my download folder at 24kb. however when i use this code above as my download.php it downloads but comes back as 2kb.
can someone help me figure out why its changing the file size please?
I don't see any code where you are actually sending the file.Make sure you actually send the file. You have used fopen() but you are not using fread() that's why files is getting opened but not getting being read may be that's why it's showing some default output which amounts to 2kb . You can use the much simpler readfile() instead
For that replace this line
fopen($fsize, "r");
with this one
readfile('path/to/' . $path_parts["basename"]);
Just in case you are handling huge files like several MBs then fopen will suite you better as it would be more memory efficient.Also note the b flag in fopen() parameter it refers to binary mode so whenever you are sending a binary file like pdf,images etc you should always use this flag
set_time_limit(0);
$file = #fopen('path/to/' . $path_parts["basename"],"rb");
while(!feof('path/to/' . $path_parts["basename"]))
{
print(#fread('path/to/' . $path_parts["basename"], 1024*2));
ob_flush();
flush();
}
the problem was the / in the url it was starting with. once i added a trim to the url it worked. tbh now that i started looking into this i dont think it really ever work just appeared it did.
$trmfullPath = $_GET['url'];
$fullPath = trim($trmfullPath, "/");
this seemed to fix it. also dont get any errors in my php error log now.

Issue saving file with PHP script

I'm making a PHP script for a JavaScipt site I've made.
The goal is to save the contents of a string as an HTML file when I click a button.
I'm using jQuery to make a Post request.
I'm using an Ubuntu OS with an Apache 2 server. The folder I'm writing to has permissions 777 (for testing only, will repeal this).
A requirement is the PHP must live in another file.
The issue is whenever I make the request, the file saves blank.
A requirement is each filename must be a timestamp. The file has the correct file name, but not contents.
So far, here is my code:
<?php
$fileName = $_GET['fileNameData'];
$htmlImport = $_GET['htmlToSaveData'];
$htmlToSave = (string)$htmlImport;
$myFile = fopen($fileName, "w") or die('You do not have write permissions');
//fwrite($myFile, $htmlToSave);
file_put_contents($myFile, $htmlToSave);
fclose($myFile);
?>
I've tried the frwite function that I've commented out, same effect.
I have tested this in terminal by passing in arguments ($argv[1] and $argv[2]). That works fine.
The JS I've made to run my site looks like:
var newURL = 'saveHTML.php/?fileNameData=' + fileName + '&htmlToSaveData=' + htmlToSave
$.post(newURL)
.done(function(){
alert('Your file saved as ...' + htmlToSave)
})
I've also tried this code, with the same result:
$.post('saveHTML.php/', {
fileNameData : fileName,
htmlToSaveData : htmlToSave
})
Both the fileName and htmlToSave are strings, although htmlToSave is rather long and is actually html text that I've converted to a string.
Does anyone have ideas about what's going on here? I'm not a PHP developer at all.
I'm using a callback so I can be sure I've collected all my html before I pass the string to PHP.
I've read and tested the recommendations on this question here and this has been fruitless.
EDIT Don't be alarmed about the code, I realise it's a security issue but this is a learning project and this will not be in production.
I can see right off the bat that you have
$myFile = fopen($fileName, "w") or die('You do not have write permissions');
//fwrite($myFile, $htmlToSave);
file_put_contents($myFile, $htmlToSave);
fclose($myFile);
file_put_contents takes a file name, not a handle. So you would only need
file_put_contents($fileName, $htmlToSave);
Edit: I also feel like I should point out that you should not allow your users to name your files. They could potentially do some nasty stuff to your machine.

How to download converted HTML file in Codeigniter

I'm working on codebeautify.org site,
in which I want to convert excel to HTML file. I've converted that but I can't download the file.
public function convertHTML(){
$fileName=$this->input->post('fileName');
$file_ext = end(explode('.',$fileName));
if($file_ext!="xlsx"){
$data = new Spreadsheet_Excel_Reader(LOCAL_UPLOAD_PATH.$fileName);
for($s=0; $s<count($data->sheets); $s++) {
echo "<b><u>Sheet Name</u> :- ".$data->boundsheets[$s]['name']."</b><hr>";
echo $data->dump(false,false,$s);
echo "<hr>";
}
$fh = fopen(LOCAL_UPLOAD_PATH.$fileName, 'a');
fclose($fh);
unlink(LOCAL_UPLOAD_PATH.$fileName);
}
else{
$this->convertXLSXtoHTML($fileName);
}
}
Now I want to download it. How can I do it?
If you want to download instead of Show in the browser there are some options, but to be honest, I prefer show the file, because the options are not a very good user experience, and the last one not always is possible:
Option 1: Insert the excel in a .zip
Option 2: The browser (some of them) has an option which ask to the users if they want to show or download the file, the problem with this is that option is not working only in your page.
Option 3: add in the .htacces the next code to force the browser to download some type of files:
<FilesMatch "\.(?i:xlxs)$">
ForceType application/octet-stream
Header set Content-Disposition attachment
</FilesMatch>

Uploadify Success but No Files Uploaded?

I am attempting to implement uploadify on a site.
It says the files are uploaded but when I look in the upload folder nothing is there.
I have read other post similar to this without luck.
I did read this answer to another question:
I had similar problems on a Linux machine. It turned out that the PHP configuration on my server was the cuplrit. PHP was running in SAFE MODE. As I had uploaded the Uploadify scripts via FTP, so script files were stored in the file system with my FTP user details. Since PHP's temp folder was owned by the server root, I had a UID mismatch, i.e. the temporary upload file was attributed to root while the upload script that tried to move it was owned by the FTP user. That fragged it.
To resolve this I changed the ownership of the uploadify php script to root and from there on it worked.
I know little about server side coding as I am more a front end person. How do I change permissions? I am using 1&1 Hosting.
Here is a screenshot of the files on the server in FileZilla:
EDIT
I tried to upload a ZIP file and it said the upload was successful but did not upload. However, I wonder if there is an error with my script because I should not have been allowed to upload a ZIP File because of this line in the PHP Script:
// Validate the file type
$fileTypes = array('jpg','jpeg','gif','png'); // File extensions
Shouldn't the script reject the zip file?
Below is my code I am using in case there is an error with the scripts and not my server:
JS
$(function() {
$('#file_upload').uploadify({
'swf' : 'uploadify.swf',
'uploader' : 'uploadify.php',
'onUploadSuccess' : function(file, data, response) {
alert('The file ' + file.name + ' was successfully uploaded with a response of ' + response + ':' + data);
}
});
});
PHP
<?php
$targetFolder = '/uploads/'; // Relative to the root
$verifyToken = md5('unique_salt' . $_POST['timestamp']);
if (!empty($_FILES) && $_POST['token'] == $verifyToken) {
$tempFile = $_FILES['Filedata']['tmp_name'];
$targetPath = $_SERVER['DOCUMENT_ROOT'] . $targetFolder;
$targetFile = rtrim($targetPath,'/') . '/' . $_FILES['Filedata']['name'];
// Validate the file type
$fileTypes = array('jpg','jpeg','gif','png'); // File extensions
$fileParts = pathinfo($_FILES['Filedata']['name']);
if (in_array($fileParts['extension'],$fileTypes)) {
move_uploaded_file($tempFile,$targetFile);
echo '1';
} else {
echo 'Invalid file type.';
}
}
?>
It looks as though the token verification code is the problem. If you remove that functionality, the upload should go through :)
Can you remove that if() comparison by commenting it out?
if (!empty($_FILES) && $_POST['token'] == $verifyToken) { line changes to:
if (!empty($_FILES) /* && $_POST['token'] == $verifyToken */) {
It seems that the $fileTypes is case sensitive on my Linux PHP install.
'image.jpg' uploads but 'image.JPG' does not.
Change
$fileTypes = array('jpg','jpeg','gif','png');
To
$fileTypes = array('jpg','JPG','jpeg','JPEG','gif','GIF','png','PNG');

Categories