PHP file not copying correctly => file empty - php

I'm currently trying to copy a file from location A to B in PHP. The file get's copied but it has 0 Bytes. I'm so confused why this file is empty after this process. This is my code:
if ( ! file_exists( $file_dir . $file_category ) ) {
if ( ! mkdir( $file_dir . $file_category, 0777, true ) && ! is_dir( $file_dir . $file_category ) ) {
throw new \RuntimeException( sprintf( 'Directory "%s" was not created', $file_dir . $file_category ) );
}
$data = '<html><body bgcolor="#FFFFFF"></body></html>';
$file = fopen( $file_dir . $file_category . '/index.html', 'wb' );
fwrite( $file, $data );
fclose( $file );
$data = 'deny from all';
$file = fopen( $file_dir . $file_category . '/.htaccess', 'wb' );
fwrite( $file, $data );
fclose( $file );
}
copy( $output_dir . $filename, $file_dir . $file_category . '/' . $filename . '.pdf' );
Any help would be awesome.

is it just me or do you have switched the source and the destination file in your copy line:
copy( $output_dir . $filename, $file_dir . $file_category . '/' . $filename . '.pdf' );
PHP docs says that the parameters is like this:
copy ( string $source , string $dest [, resource $context ] ) : bool
but you first parameter uses "$output_dir" (might just be your variable name)
If this is not the case it would be helpful to know where you get "$filename" from since you are not validating it anywhere in your code, only "$file_category". Are you sure that your source file actually exists and has content?

Related

WordPress plugin development : How to upload a file to the default "uploads" directory?

I'm trying to upload files to the default "wp-content/uploads" directory. Have tried almost all the available tags, still not working.
Few of the codes I tried:
$filename = $_FILES["uploadfile"]["name"];
$tempname = $_FILES["uploadfile"]["tmp_name"];
$folder= 'wp_upload_dir()'. $filename; //This code is uploading the file to the "wp-admin" directory
if(move_uploaded_file($tempname, $folder)){$response}
$uploaddir = 'uploads/'; $uploadfile = $uploaddir . $filename;`
if(move_uploaded_file($tempname, $uploadfile))
`
I've coded to save the image in uploads folder for one of my website. please check if this code helps
//taking image in $name_icon
$name_icon = $_POST['myfile'];
// WordPress environment
require( dirname(__FILE__) . '/../../../wp-load.php' );
$wordpress_upload_dir = wp_upload_dir();
$i = 1; // number of tries when the file with the same name is already exists
$profilepicture = $_FILES['myfile'];
$new_file_path = $wordpress_upload_dir['path'] . '/' . $profilepicture['name'];
$new_file_mime = mime_content_type( $profilepicture['tmp_name'] );
if( empty( $profilepicture ) )
die();
if( $profilepicture['error'] )
die( $profilepicture['error'] );
if( $profilepicture['size'] > wp_max_upload_size() )
die( 'It is too large than expected.' );
if( !in_array( $new_file_mime, get_allowed_mime_types() ) )
die( 'WordPress doesn\'t allow this type of uploads.' );
while( file_exists( $new_file_path ) ) {
$i++;
$new_file_path = $wordpress_upload_dir['path'] . '/' . $i . '_' . $profilepicture['name'];
}
// looks like everything is OK
if( move_uploaded_file( $profilepicture['tmp_name'], $new_file_path ) ) {
$upload_id = wp_insert_attachment( array(
'guid' => $new_file_path,
'post_mime_type' => $new_file_mime,
'post_title' => preg_replace( '/\.[^.]+$/', '', $profilepicture['name'] ),
'post_content' => '',
'post_status' => 'inherit'
), $new_file_path );
// wp_generate_attachment_metadata() won't work if you do not include this file
require_once( ABSPATH . 'wp-admin/includes/image.php' );
// Generate and save the attachment metas into the database
wp_update_attachment_metadata( $upload_id, wp_generate_attachment_metadata( $upload_id, $new_file_path ) );
Tested & works

Getting error "Specified file failed upload test" when adding file from Base64 decode

I have searched everywhere online and cannot find a solution.
I am attempting to use wp_handle_upload() but I am getting "Specified file failed upload test", only when I try to upload a file that I created from base64_decode();
I am pretty sure this is not a permissions or a server issue. Here are some more notes:
everything works fine when uploading files on WordPress to the media library
my code even works when I get the files directly from $_FILES. It stopped working when I started having to create my own $file array.
I have another live version of this on a completely different server and the problem is the same
I have tried 'image/png' and 'image/jpg' for the file type.
I was using the uploads directory for the tmp_name but that didnt make a difference
The temporary file is succesfully uploading
More Info: I added the line print_r( is_uploaded_file( $file['tmp_name'] ));die; to line 822 in /wp-admin/includes/file.php. I believe its because this is coming back as false that error is being thrown.
$upload_dir = wp_upload_dir();
$upload_path = get_stylesheet_directory().'/tmp-images/';
$img = $_POST['main_image_0'];
$img = str_replace('data:image/png;base64,', '', $img);
$img = str_replace(' ', '+', $img);
$decoded = base64_decode($img) ;
$filename = $_POST['file_name'];
$hashed_filename = md5( $filename . microtime() ) . '_' . $filename;
// #new
if (!is_dir($upload_path)) {
// dir doesn't exist, make it
mkdir('upload/promotions/' . $month);
}
$image_upload = file_put_contents( $upload_path . $hashed_filename, $decoded );
//HANDLE UPLOADED FILE
if( !function_exists( 'wp_handle_sideload' ) ) {
require_once( ABSPATH . 'wp-admin/includes/file.php' );
}
// Without that I'm getting a debug error!?
if( !function_exists( 'wp_get_current_user' ) ) {
require_once( ABSPATH . 'wp-includes/pluggable.php' );
}
// #new
$file = array();
$file['error'] = 0;
$file['tmp_name'] = $upload_path . $hashed_filename;
$file['name'] = $filename;
$file['type'] = 'image/jpeg';
$file['size'] = filesize( $upload_path . $hashed_filename );
require_once( ABSPATH . 'wp-admin/includes/admin.php' );
require_once( ABSPATH . 'wp-admin/includes/file.php' );
$file_return = wp_handle_upload( $file, array('test_form' => false ) );
print_r($file);print_r($file_return);die;
This returns
Array
(
[error] => 0
[tmp_name] => /var/www/example/wp-content/themes/mytheme/tmp-images/eea84bdc7b9b79a10898425c79f62fc2_20130202_173509.jpg
[name] => 20130202_173509.jpg
[type] => image/jpeg
[size] => 273444
)
Array
(
[error] => Specified file failed upload test.
)
I found the cause of this. It was due to the function using is_uploaded_file which is specifically designed to handle HTTP POST requests. So everything was working the way it should be. I just did not realise wp_handle_upload() was only for this purpose. I had used base64 and converted this before calling the function which meant it was no longer processing a file from a post request.
To solve my issue I instead used wp_upload_bits (ref).

Why is this php mkdir / uniqid not working?

I have this piece of code that should create a random directory and move uploads there:
$uploadPath = dirname( __FILE__ ) . DIRECTORY_SEPARATOR . mkdir( 'assets/post/email_uploads/{uniqid(attachment_)}', 0777 ) . DIRECTORY_SEPARATOR . $_FILES[ 'file' ][ 'name' ];
The path assets/post/email_uploads/ already exists so the random folder should go inside email_uploads. The issue I'm facing is what to place between the DIRECTORY_SEPARATORs and have everything work.
When I try mkdir( 'assets/post/email_uploads/{uniqid(attachment_)}', 0777 ) OR
mkdir( 'assets/post/email_uploads/'.uniqid(attachment_), 0777 ) - The folder is not created and the upload is placed at the root.
When I try
$attchmentPath = 'assets/post/email_uploads/';
$uploadPath = dirname( __FILE__ ) . DIRECTORY_SEPARATOR . $attchmentPath.mkdir( uniqid(attachment_), 0777 ) . DIRECTORY_SEPARATOR . $_FILES[ 'file' ][ 'name' ];
OR
$attchmentPath = 'assets/post/email_uploads/';
$randomDir = mkdir( uniqid(attachment_), 0777 );
$newPath = $attchmentPath.$randomDir;
$uploadPath = dirname( __FILE__ ) . DIRECTORY_SEPARATOR . $newPath . DIRECTORY_SEPARATOR . $_FILES[ 'file' ][ 'name' ];
The folder is created at the root instead of the desired path and the file is not uploaded at all.
Perhaps like this? The content of uniqid should be quoted (unless it is a constant ) and the function call to uniqid needs to be escaped from the single quoted string
$dir=mkdir( __DIR__ . '/assets/post/email_uploads/'.uniqid('attachment_'), 0777 );
$name=$_FILES['file']['name'];
$uploadPath = $dir . DIRECTORY_SEPARATOR . $name;
You could try a recursive function to ensure that the directory path exists
function createpath( $path=NULL, $perm=0644 ) {
if( !file_exists( $path ) ) {
createpath( dirname( $path ) );
mkdir( $path, $perm, TRUE );
clearstatcache();
}
return $path;
}
$targetpath=__DIR__ . '/assets/post/email_uploads/'.uniqid( 'attachment_' );
$path=createpath( $targetpath );
echo $path;
I solved this by simply adding a parameter - TRUE in mkdir I had left out. So the functional code is - mkdir($path, 0777, TRUE) where $path is the path to the directory to be created.

PHP: Copy entire contents of a directory

Sorry for new post! I'm not yet trusted to comment on others posts.
I'm having trouble copying folders and this is where I started:
Copy entire contents of a directory
Function
function recurse_copy($src,$dst) {
$dir = opendir($src);
#mkdir($dst);
while(false !== ( $file = readdir($dir)) ) {
if (( $file != '.' ) && ( $file != '..' )) {
if ( is_dir($src . '/' . $file) ) {
recurse_copy($src . '/' . $file,$dst . '/' . $file);
}
else {
copy($src . '/' . $file,$dst . '/' . $file);
}
}
}
closedir($dir);
}
My input
$src = "http://$_SERVER[HTTP_HOST]/_template/function/";
$dst = "http://$_SERVER[HTTP_HOST]/city/department/function/";
recurse_copy($src, $dst);
I've also tried this
$src = "$_SERVER[DOCUMENT_ROOT]/_template/function/"; // And so on...
The function is executed but nothing is being copied.
Any ideas on what might be wrong?
SOLVED
Working solution
Along with
$src = "$_SERVER[DOCUMENT_ROOT]/_template/function/";
$dst = "$_SERVER[DOCUMENT_ROOT]/city/department/function/";
recurse_copy($src, $dst);
It's not tested but I think the issue might be that the target directory is not necessarily being created before attempting to copy files to it. The piece of code that creates the target directory would require a folder path rather than a full filepath - hence using dirname( $dst )
if( !defined('DS') ) define( 'DS', DIRECTORY_SEPARATOR );
function recurse_copy( $src, $dst ) {
$dir = opendir( $src );
#mkdir( dirname( $dst ) );
while( false !== ( $file = readdir( $dir ) ) ) {
if( $file != '.' && $file != '..' ) {
if( is_dir( $src . DS . $file ) ) {
recurse_copy( $src . DS . $file, $dst . DS . $file );
} else {
copy( $src . DS . $file, $dst . DS . $file );
}
}
}
closedir( $dir );
}
Use local paths
$src= "_template/function/";
$dst= "city/department/function/";
recurse_copy($src, $dst);
copy works locally on your server. You're trying to copy using HTTP scheme, it's not working that way.

PHP script doesn't end

So I got my script doing this:
I got a list of filenames (images), I loop through the array and load the images from Amazon S3 to my local storage. We are talking about 35k pictures which takes more than 3 hours.
After I downloaded all the images I want to make a redirect via header Location. But the script won't execute that. It's like it's stopping after the loop.
When I have a very small list of images to load it will work with no issues.
The apache error log doesn't show any errors. There is no php process running on the server after that. But the request is still running in the browser.
Ini settings are as followed:
ini_set( 'max_execution_time', 60 * 30 );
ini_set( 'memory_limit', '4096M' );
Foreach loop lookes like this:
foreach( $arrImages as $file ) {
$strPath = $strBasePath . DIRECTORY_SEPARATOR . $file['name'];
// check directory
$pos = strrpos( $strPath, DIRECTORY_SEPARATOR );
$dir = substr( $strPath, 0, $pos );
if( !is_dir( $dir ) ) {
exec( "mkdir -p " . $dir );
exec( "chmod -R 777 " . $strBasePath . DIRECTORY_SEPARATOR );
}
// check if file or path
if( !is_dir( $strPath ) ) {
// build filename
$lastSeparatorPos = strrpos( $strPath, DIRECTORY_SEPARATOR );
$filename = explode( '.', substr( $strPath, $lastSeparatorPos + 1, strlen( $strPath ) - 1 ) );
$clearedFilename = explode( '_', $filename[0] );
if( !in_array( $clearedFilename[0], $arrOrdernumbers ) && strpos( $dir, 'groups' ) == false && strpos( $dir, 'background' ) == false ) {
$intCountNotImported++;
}
else {
$handle = fopen( $strPath, 'wb' );
if( $handle == false ) {
\ImportLogger::log( $strPath . ' - Bild konnte nicht uebertragen werden' );
}
else {
// get File/Folder
$objImage = \S3::getObject( C_S3_BUCKET, $file['name'] );
fwrite( $handle, $objImage->body );
$intAmount++;
// Log every 100 Files
if( $intAmount % 100 == 0 ) {
\ImportLogger::log( $intAmount . ' Bilder uebertragen' );
}
}
fclose( $strPath );
}
}
}
\Debugger::sendEmail( 'xx#xxxx.de', 'Fetchimages', $intAmount . ' - Images loaded' ); // This E-Mail I still get
// Redirect is not happening
$strUrl = '/string/configurator2/compressimages';
header( 'Location: ' . $strUrl );
exit;
Any ideas what could cause this?
Thanks for your help!

Categories