3

I have a problem when I create a new directory with PHP when uploading a file.

The directory is created, but if another instance of the same script runs at the same time the directory exist check doesn't work correctly (gives PHP warning).

Someone told me it's a race condition but I still have this issue after adding some random sleep time.

usleep(mt_rand(1, 50));

if(!is_dir($dir)){
  mkdir($dir);    
}

usleep(mt_rand(1, 50));

can anyone help?

Does anybody know a safe way to upload a file in multiple parts, with 3-4 parts being uploaded at the same time? Currently I'm moving the uploaded parts in a temporary directory (is_dir fails on the temporary dir if more parts arrive at the same time), then when the number of files from that dir equal the number of parts the parts get combined. But it fails many times, sometimes is_dir gives warning, sometimes the parts get combined twice...

J. Doe
  • 51
  • 3
  • Can you explain what you mean by "dosen't work correctly" ? – Dan O'Boyle May 13 '16 at 14:49
  • Use a locking mechanism and a file somewhere that you can check if it is checked out. http://www.htmlite.com/php043.php if the file is locked then don't make the directory. – Roger May 13 '16 at 14:53
  • 1
    can you write the warning? – Gumma Mocciaro May 13 '16 at 14:53
  • The warning is mkdir(): File exists – J. Doe May 13 '16 at 15:03
  • Neoaptt actually I'm using flock on the files, and that doesn't work either. 1 out of 10 times the lock check fails and my files get combined twice.. I don't know what to do anymore, so many issues when working with concurrent file uploads in PHP........ glob doesn't work, is_dir doesn't work, flock doesn't work.. – J. Doe May 13 '16 at 16:35
  • Can you define *if another instance of the same script runs at the same time*, as for these things to run exactly concurrently with two browsers running the same script independantly is extremely unlikely and shouldn't be causing your issues. could you clarify what this phrase actually means? – Martin May 13 '16 at 17:30
  • The upload javascript splits the file in multiple parts and sends 4 ajax requests to php, so the php receives 4 parts simultaneously. when all parts are received the php should combine them to reproduce the file on the server – J. Doe May 13 '16 at 18:39
  • @J.Doe I have updated my answer to reflect this comment. – Martin May 14 '16 at 04:32

2 Answers2

0

mkdir() returns true on success, and false on failure (dir already exists). So you can just use it as a part of your conditional check.

if (!is_dir($dir) && mkdir($dir)) {
    // good to go
}
mister martin
  • 6,197
  • 4
  • 30
  • 63
  • i think it's the same as my code, except you have mkdir in the if block so it looks like mkdir will always be executed, won't that give me warnings every time? – J. Doe May 13 '16 at 15:07
  • @J.Doe it's not the same, no. The conditional in my example will not generate a warning, because it's asking a question (was the directory created?). Yours is not asking the question, therefore it is issuing a warning telling you that it cannot make the directory. – mister martin May 13 '16 at 15:41
0

You want to use clearstatcache() at the top of the page testing for the directory, so that the system cache of current directory structure is fresh. read more here

The upload javascript splits the file in multiple parts and sends 4 ajax requests to php, so the php receives 4 parts simultaneously. when all parts are received the php should combine them to reproduce the file on the server

So why split them up, send the Ajax as a single request and then allow PHP to handle each blob file part in its own scripting. This will sidestep the problem. PHP - with the correct setting up - can comfortably handle large files in chunk blocks.

Community
  • 1
  • 1
Martin
  • 22,212
  • 11
  • 70
  • 132