Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

rhys's avatar
Level 5

Image upload production docker

Hi

I have recently deployed a basic website using docker.

For production I have decided to turn off volumes to improve speed but I think it has caused a knock on affect to an image uploader.(I think this is the cause)

On development I have a vue.js image uploader that saves files to public/images this works great. However when deployed to production I'm getting message: "Can't write image data to path (/var/www/html/public/thumbnail/1634312431download.jpg)",…}

I've ssh' into the server and this is where I'm a bit confused.

My code is located in /site when I cd into this /site/src/public/images I do not see any files being saved down which makes sense as I'm seeing the above issue. When I use docker-compose exec php /bin/sh and then navigate to public/images I can see the files in this location.

If I'm no longer using volumes how do save images to my server? What is the best practice in this situation? should I be storing images on a third party server like azure or amazon ?

Sorry if this is a dumb question but I would like to implement best practice.

0 likes
4 replies
rhys's avatar
Level 5

@jlrdw

I will take a look at this. All the images belong to articles, any one will be able to view articles once an admin approves the article but only authenticated users will be able to create them.

rhys's avatar
Level 5

I'm not sure my issue is to do with volumes. Tried without https still no change. I've listed some of my code below. Does anything look odd?

I've kept the image controller outside the Auth middleware while I'm trying to get this to work.

Local -

nginx       | 2021/10/18 15:15:09 [warn] 3131: *2 a client request body is buffered to a temporary file /var/cache/nginx/client_temp/0000000001, client: 172.20.0.1, server: localhost, request: "POST /api/image HTTP/1.1", host: "127.0.0.1", referrer: "http://127.0.0.1/article/create"

nginx       | 172.20.0.1 - - [18/Oct/2021:15:15:11 +0000] "POST /api/image HTTP/1.1" 200 35 "http://127.0.0.1/article/create" "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.81 Safari/537.36" "-"

php         | 172.20.0.2 -  18/Oct/2021:15:15:09 +0000 "POST /index.php" 200

Production

        nginx       | 2021/10/18 15:20:48 [warn] 3131: *1 a client request body is buffered to a temporary file /var/cache/nginx/client_temp/0000000002, client: 86.3.140.138, server: pactest.tk, request: "POST /api/image HTTP/1.1", host: "pactest.tk", referrer: "https://pactest.tk/article/create"

nginx       | 86.3.140.138 - - [18/Oct/2021:15:20:48 +0000] "POST /api/image HTTP/1.1" 500 11196 "https://pactest.tk/article/create" "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.81 Safari/537.36" "-"

php         | 172.22.0.7 -  18/Oct/2021:15:20:48 +0000 "POST /index.php" 500

routes/api

Route::middleware('auth:api')->get('/user', function (Request $request) {

    return $request->user();
});

Route::post('image', 'ImageController@store');

image controller

class ImageController extends Controller
{
    public function store(Request $request)
    {
        if($request->file('file'))
        {
            $originalImage= $request->file('file');
            $name = time().$originalImage->getClientOriginalName();
            $img = ImageIntervention::make($originalImage);
            $img->orientate();
            $thumbnailPath = public_path().'/thumbnail/';
            $originalPath = public_path().'/images/';
//            var_dump($img);
            $img->save($originalPath.$name);
            $thumbnailImage = ImageIntervention::make($originalPath.$name)->fit(145, 145,null,'top');
            $thumbnailImage->orientate();
            $thumbnailImage->save($thumbnailPath.$name);
//            var_dump($img);
//            var_dump($thumbnailImage);
        }
        return response()->json($name, 200);
    }
}
rhys's avatar
Level 5

Ok,

I have solved this issue and its embarrassing but a learning experience on how production is different from local development.

So the underlying issue was hidden by a few factors.

Initial issue Image upload was receive 500 with no notification.

I started to explore my vue component to ensure no timeouts were applied, here is where I noticed some changes I made to the code were not reflecting in my production despite pushing to production. I also noticed that throttling was on in browser dev tools which was causing the upload to be very slow adding to the confusion of some files failing on local.

I ran docker-compose run --rm npm run watch This showed some asset issues to do with lower case and upper case which is not shown on windows.

I resolved these and with watcher still running started to push changes to production on my vue component. With the front end compiled successful I was now getting an error that I could not save the thumbnail version of the image.

This was due to the directory being added to the git ignore and subsequently deleted. DOH.

Bringing the directory back has restored all functionality.

Please or to participate in this conversation.