My problem here is even though it gets saved "successfully" the file is not actually saved. (I'm running this on the Cloud9IDE)
My folder exports is set to be readable and writable via chmod 777 -R ./.
Can someone explain to me why the hello.txt file is not being created, and what I can do to solve this problem?
JQuery:
$("[data-action=save-file]").on("click", function(e) {
var filename = "hello.txt"
var content = "Hello world!"
$.ajax({
type: "GET",
url: "submit.php",
data: {
"filename": filename,
"content": content,
},
cache: false,
success: function(msg) {
console.log(msg)
},
error: function(XMLHttpRequest, textStatus, errorThrown) {
console.log("Some error occurred")
}
})
})
PHP:
<?php
$filename = $_GET["filename"];
$fp = fopen("anon/".$filename, "wb");
if (!$fp) {
echo getcwd();
exit;
} else {
$outputstring = $_GET["outputstring"];
fwrite($fp, $outputstring);
}
$fclose($fp);
?>
I've also tried...
<?php
$filename = $_GET["filename"];
$outputstring = $_GET["outputstring"];
file_put_contents($filename, $outputstring, FILE_APPEND | LOCK_EX);
?>
If this is the actual code that is posted, then the arguments being sent by ajax are "content" and "filename", while php is expecting "outputstring" and "filename", so, on the php end, there is no "outputstring" and the program doesn't check for "content" in $_GET.
$filename = $_GET["filename"];
$outputstring = $_GET["content"];
file_put_contents($filename, $outputstring, FILE_APPEND | LOCK_EX);
Also there is a max length to too url parameters for GET (Max size of URL parameters in _GET), so if file content is ever an actual file this may be truncated. Try using type: "POST" instead.
maybe you should start debugging server side:
first of all, when using file_put_contents, check if it returns false (use operator ===). In this case folder anon/ doesn't exists.
second: check for writability of that folder with is_writable.
if (!isset($_GET[...], $_GET[...])) die("missing vars...");
if (!is_writable($filenamewithpath)) die("dir not writable");
if (file_put_contents(...) === false) die("dir doesn't exists");
if directory not writable, try using chmod($path, 0777). could be that your main directory is 0777 but not the sub-directories.
by the way, as others pointed out, your ajax call is sending "content", not "outputstring" as parameter. you should rename the data object key.
try also to use absolute path (using for example __DIR__ . "/anon/". $filename);
The code in php $fp.close() is error. It should be fclose($fp).
wb is not any mode in php. use w+ instead of wb
and you need to check folder is exist or not
$path = "anon";
if (!file_exists($path) && is_dir($path))
{
if (!mkdir($path, 0777, TRUE))
{
return false;
}
}
Related
I want to upload images to a server using ajax and php.
On client-side i hava the following code:
var reader = new FileReader();
reader.readAsDataURL(file, 'UTF-8');
reader.onload = function (event) {
var result = event.target.result;
$.ajax({
type: "POST",
url: "url",
data: {
data: result,
name: file.name,
mimeType: file.type
}
});
};
On server-side my code looks like the following:
$path = 'somehow/'
$fp = fopen( $path . $_POST['name'], 'w');
$data = explode( ',', $_POST['data'] );
fwrite($fp, base64_decode( $data[ 1 ] ));
fclose($fp);
chmod($path . $_POST['name'], 7777);
list($width, $height) = getimagesize($path . $_POST['name']);
Now the method "getimagesize" always runs into an error "getimagesize(): Read error!"
Does anybody know, why this happens? When i look into the filesystem on the server the file 'FILENAME.JPG' exists ...
You can use $result = #getimagesize($file) to suppress the error.
So, when the $result is empty, means there is an error occurred.
There are two possible reasons for this error : either the url path is incommplete/incorrect or the picture file is corrupt and cannot be opened. A file may be corrupted, for example, if the image is not fully/correctly loaded onto the server.
I'm trying to save data into a file using fwrite, the problem is that it is creating a second file with the same file name, and the data is saved to the second file and not the original.
It works under Windows localhost, Apache 2.4.10, PHP 5.6 (no second file), but not on live server running Linux and PHP 5.4.42.
edit.php
$(document).ready(function() {
var pageName = "<?php echo $pageName; ?> ";
$('#save').click(function(e) {
e.preventDefault();
var content = $('#content').html();
$.ajax({
type: 'POST',
url: 'includes/readInput.php',
data: {
content: content,
pageName: pageName,
}
}).done(
function(data){
}
);
});
});
readInput.php.
// Receive post variable s from "admin/ edit.php"
$content = $_POST['content'];
$pageName = $_POST['pageName'];
$dirPath= "../content/";
file_put_contents($dirPath.$pageName,$content);
If you open the file where the data will be stored with the "a" from append flag this will result to write at the end of the file content:
$file = fopen($filename, 'a');
fwrite($file, 'new content');
Then you file will be stored with old content and "new content" the the end.
I am adding a file upload function to my php page. The code seems correct to me and it even adds the file to the server with the correct name, but with no contents. i.e. there is an empty .jpg file when loading an image.
Can any of you more experienced php developers see what I am doing wrong to produce empty files.
calling script:
<script>
$(document).ready(function(){
$("#mediaFileInput").on("change", function(e){
console
if (e.target.value) {
var formData = new FormData(e.target.form);
$.ajax({
url: 'media.php', //Server script to process data
type: 'POST',
success: function(data){
location.reload();
},
// Form data
data: formData,
//Options to tell jQuery not to process data or worry about content-type.
cache: false,
contentType: false,
processData: false
});
}
});
});
</script>
media.php
<?php
require('config/config.php');
$file_uploaded;
$mime_type;
// Handle multipart file uploads
if (isset ( $_FILES ['file'] )) {
$file_uploaded = fopen($_FILES['file']['name'], "r");
$mime_type = $_FILES['file']['type'];
} else if ($_SERVER["REQUEST_METHOD"] == "POST") {
/* PUT data comes in on the stdin stream */
$file_uploaded = fopen("php://input", "r");
/* Open a file for writing */
$mime_type = $_SERVER["CONTENT_TYPE"];
}
$file_name = $_FILES['file']['name'];
$new_path = "media/" . $file_name;
$media_url = "/" . $new_path;
$fp = fopen($new_path, "w");
/* Read the data 1 KB at a time
and write to the file */
while ($data = fread($file_uploaded, 1024)) {
fwrite($fp, $data);
}
/* Close the streams */
fclose($fp);
fclose($file_uploaded);
chmod($new_path, 0755);
// insert into database.
$stmt = $db_conn->prepare("INSERT INTO MEDIA (type, url) VALUES(?, ?)");
$stmt->bind_param('ss',
$mime_type,
$media_url);
$stmt->execute();
$media_id = $db_conn->insert_id;
$stmt->close();
echo json_encode(array("id" => $media_id, "type" => $mime_type, "url" => $media_url));
?>
You should not be using fopen("php://input", "r"); because according to the docs for it:
php://input is not available with enctype="multipart/form-data".
When you're uploading a file, of course, you have to use enctype="multipart/form-data". So instead, use move_uploaded_file.
Also, fopen($_FILES['file']['name'], "r"); in your other branch doesn't make sense, since that's just trying to open a filename with no particular path. Use move_uploaded_file.
I'm trying to scan the files in a directory using a php request. This is my code right now:
$.ajax({
type: "POST",
url: "scandir.php",
data: { dirname: "./test" },
success: function( data ) {
console.log( data );
}
error: function() {
console.log( "error" );
}
});
scandir.php:
<?php
$dirname = $_POST[ "dirname" ];
$files = scandir( $dirname ) or die("Unable to scan directory " . $dirname );
foreach ( $files as $filename ) {
echo $filename . "\n";
}
?>
Problem is, the request always returns successfully, even if the directory "dirname" doesn't exist (it returns the text of the php directory-not-found messages). How do I make it return with an error when the directory is not found?
if(!empty($_POST["dirname"])) {
$dirname = $_POST["dirname"];
if(!is_dir($dirname)) {
header('HTTP/1.0 404 Not Found');
exit;
}
foreach(scandir($dirname) as $filename) {
echo $filename . "\n";
}
}
As you can see here, the error entry is only for http errors like timeout or 404 not found. If you want to check if the php script failed internally, you either can set a header using php's method header or you check in the success function whether the php script returned an error. Hope that helps.
I encoded a canvas-image to base64 which gives me this:
data:image/jpeg;base64,/9j/4AAQSkZJRgABAQAAAQABAAD/2wBDAAICAgICAQICAgICAgIDAwYEAwMDAwcFBQQGCAcICAgHCAgJCg0LCQkMCggICw8LDA0ODg4OCQsQEQ8OEQ0ODg7/2wBDAQICAgMDAwYEBAYOCQgJDg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg7/wAARCAAKAAoDASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD5a/Z7/Zw8EfF/9mT4h6Z4u0GTwt8WNP1iSya7vZp0uNKYJBsItyANjt5o2uGkDBsHhMfDsOn2zWcTQ39tJCUBR5HVGYY4JUEgH2BIHrXunw71vWdI/aa+POraTq+p6Xqr+H/Edy15aXTxTNMt4m2QupDbxubDZyMn1r4yRE8pflXoO1fleQYDEzzHGxnXbjeEop6qPNFtpXb00Wm3zP1vNM2pUMLh5RpK75k3fV8rVm7LzP/Z
which seems like a valid base64-image (decoded it with an online-decoder).
I send this with other (form-) variables with jquery ajax like this:
$.ajax({
type: "POST",
url: "index.php?action=saveNewPost",
data: {text: text, img: encodeURIComponent(base64img)},
contentType: "application/x-www-form-urlencoded;charset=UTF-8",
success: function(){
//...
}
});
on the server this goes to this line:
saveImage(utf8_decode($_POST['img']));
which calls:
function saveImage($base64img){
define('UPLOAD_DIR', '../uploads/');
$base64img = str_replace('data:image/jpeg;base64,', '', $base64img);
$data = base64_decode($base64img);
$file = UPLOAD_DIR . uniqid() . '.jpg';
file_put_contents($file, $data);
}
However, the file isn't saved. What could be wrong?
Lets try to create file test.php in same folder with single function and call, check output errors in browser or /var/log/httpd/error_log
<?php
function saveImage($base64img){
define('UPLOAD_DIR', '../uploads/');
$base64img = str_replace('data:image/jpeg;base64,', '', $base64img);
$data = base64_decode($base64img);
$file = UPLOAD_DIR . '123123123.jpg';
file_put_contents($file, $data);
}
saveImage('data:image/jpeg;base64,/9j/4AAQSkZJRgABAQAAAQABAAD/2wBDAAICAgICAQICAgICAgIDAwYEAwMDAwcFBQQGCAcICAgHCAgJCg0LCQkMCggICw8LDA0ODg4OCQsQEQ8OEQ0ODg7/2wBDAQICAgMDAwYEBAYOCQgJDg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg7/wAARCAAKAAoDASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD5a/Z7/Zw8EfF/9mT4h6Z4u0GTwt8WNP1iSya7vZp0uNKYJBsItyANjt5o2uGkDBsHhMfDsOn2zWcTQ39tJCUBR5HVGYY4JUEgH2BIHrXunw71vWdI/aa+POraTq+p6Xqr+H/Edy15aXTxTNMt4m2QupDbxubDZyMn1r4yRE8pflXoO1fleQYDEzzHGxnXbjeEop6qPNFtpXb00Wm3zP1vNM2pUMLh5RpK75k3fV8rVm7LzP/Z');
That mean that troubles in part AJAX => php script. Now, we try to compare what we recieve from ajax and original string, just change your function to this and look at test.txt:
function saveImage($base64img){
define('UPLOAD_DIR', '../uploads/');
$file = UPLOAD_DIR . 'test.txt';
file_put_contents($file, 'ORIG:'.'data:image/jpeg;base64,/9j/4AAQSkZJRgABAQAAAQABAAD/2wBDAAICAgICAQICAgICAgIDAwYEAwMDAwcFBQQGCAcICAgHCAgJCg0LCQkMCggICw8LDA0ODg4OCQsQEQ8OEQ0ODg7/2wBDAQICAgMDAwYEBAYOCQgJDg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg4ODg7/wAARCAAKAAoDASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD5a/Z7/Zw8EfF/9mT4h6Z4u0GTwt8WNP1iSya7vZp0uNKYJBsItyANjt5o2uGkDBsHhMfDsOn2zWcTQ39tJCUBR5HVGYY4JUEgH2BIHrXunw71vWdI/aa+POraTq+p6Xqr+H/Edy15aXTxTNMt4m2QupDbxubDZyMn1r4yRE8pflXoO1fleQYDEzzHGxnXbjeEop6qPNFtpXb00Wm3zP1vNM2pUMLh5RpK75k3fV8rVm7LzP/Z'."\n".'AJAX:'.$base64img);
}
It works - seems when a file is included in php using
include('file.php');
the relative path is from the parent and not from the included file :(
That was the whole problem... Thanks to all
You write encodeURIComponent (JS) and then utf8_decode (PHP). Just use urldecode (PHP) and it will work fine! :)