Unable to upload user profile images #387

Closed
opened 2026-02-04 19:20:00 +03:00 by OVERLORD · 14 comments
Owner

Originally created by @ghost on GitHub (Jul 28, 2017).

  • BookStack Version: v0.17.1
  • PHP Version: 7.0.21
  • MySQL Version: 5.6.34-79.1 Percona Server
Expected Behavior

We should be able to set the user's avatar to a custom uploaded file.

Actual Behavior

We're currently unable to upload user profile avatars. When we attempt to, we get the following message:

<html>
<head><title>404 Not Found</title></head>
<body bgcolor="white">
<center><h1>404 Not Found</h1></center>
<hr><center>nginx</center>
</body>
</html>
<!-- a padding to disable MSIE and Chrome friendly error page -->
<!-- a padding to disable MSIE and Chrome friendly error page -->
<!-- a padding to disable MSIE and Chrome friendly error page -->
<!-- a padding to disable MSIE and Chrome friendly error page -->
<!-- a padding to disable MSIE and Chrome friendly error page -->
<!-- a padding to disable MSIE and Chrome friendly error page -->

We're using Nginx, if it helps. In the nginx error log, here's what we see:

2017/07/28 15:25:28 [error] 24177#24177: *4113 open() "/home/support/site/documentation/public/images/user/upload" failed (2: No such file or directory), client: ..., server: ..., request: "POST /images/user/upload HTTP/1.1", host: "...", referrer: "https://....com/settings/users/9"

It seems like the request isn't being routed through the index.php file? I have very limited Laravel knowledge, but it does seem like it's attempting to access this as a directory, instead of a route?

Originally created by @ghost on GitHub (Jul 28, 2017). * BookStack Version: v0.17.1 * PHP Version: 7.0.21 * MySQL Version: 5.6.34-79.1 Percona Server ##### Expected Behavior We should be able to set the user's avatar to a custom uploaded file. ##### Actual Behavior We're currently unable to upload user profile avatars. When we attempt to, we get the following message: ``` <html> <head><title>404 Not Found</title></head> <body bgcolor="white"> <center><h1>404 Not Found</h1></center> <hr><center>nginx</center> </body> </html> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> <!-- a padding to disable MSIE and Chrome friendly error page --> ``` We're using Nginx, if it helps. In the nginx error log, here's what we see: ```2017/07/28 15:25:28 [error] 24177#24177: *4113 open() "/home/support/site/documentation/public/images/user/upload" failed (2: No such file or directory), client: ..., server: ..., request: "POST /images/user/upload HTTP/1.1", host: "...", referrer: "https://....com/settings/users/9"``` It seems like the request isn't being routed through the index.php file? I have very limited Laravel knowledge, but it does seem like it's attempting to access this as a directory, instead of a route?
OVERLORD added the 🐕 Support label 2026-02-04 19:20:00 +03:00
Author
Owner

@ssddanbrown commented on GitHub (Jul 28, 2017):

Hi @tylerschade, Are you able to post your nginx config at all? You're correct that the request is not hitting the correct part of the app.

@ssddanbrown commented on GitHub (Jul 28, 2017): Hi @tylerschade, Are you able to post your nginx config at all? You're correct that the request is not hitting the correct part of the app.
Author
Owner

@ghost commented on GitHub (Jul 28, 2017):

Here are the relevant parts of the config:

server {
    listen              ***;
    server_name         ****.****.com;
    root                /home/****/site/****/public/;

    include /etc/nginx/custom.d/server_level/*.conf;

    # Direct download
    location ~* ^/(js|static|skin|media|images)/ { expires 1w; }

    autoindex off;

    location / {
        try_files $uri $uri/ /index.php?$args;
        index index.php index.html;
        access_log off;
    }
    
    location ~* \.(jpeg|jpg|gif|png|css|js|ico|swf)$ {
        try_files $uri $uri/ /get.php;
        expires 1w;
        access_log off;
    }
}

Please let me know if there is more that would be helpful. Thanks so much for your help.

@ghost commented on GitHub (Jul 28, 2017): Here are the relevant parts of the config: ``` server { listen ***; server_name ****.****.com; root /home/****/site/****/public/; include /etc/nginx/custom.d/server_level/*.conf; # Direct download location ~* ^/(js|static|skin|media|images)/ { expires 1w; } autoindex off; location / { try_files $uri $uri/ /index.php?$args; index index.php index.html; access_log off; } location ~* \.(jpeg|jpg|gif|png|css|js|ico|swf)$ { try_files $uri $uri/ /get.php; expires 1w; access_log off; } } ``` Please let me know if there is more that would be helpful. Thanks so much for your help.
Author
Owner

@ghost commented on GitHub (Aug 2, 2017):

Any thoughts on this? I don't mean to be pushy but we have a client who is concerned about this specifically.

@ghost commented on GitHub (Aug 2, 2017): Any thoughts on this? I don't mean to be pushy but we have a client who is concerned about this specifically.
Author
Owner

@ssddanbrown commented on GitHub (Aug 3, 2017):

Hi @tylerschade,
Apologies for my late reply.
Looks like this line is the issue:

    # Direct download
    location ~* ^/(js|static|skin|media|images)/ { expires 1w; }

Remove images from that and I think things should work. This location block is matching the call so the request is not being picked up by the location block below.

@ssddanbrown commented on GitHub (Aug 3, 2017): Hi @tylerschade, Apologies for my late reply. Looks like this line is the issue: ``` # Direct download location ~* ^/(js|static|skin|media|images)/ { expires 1w; } ``` Remove `images` from that and I think things should work. This location block is matching the call so the request is not being picked up by the location block below.
Author
Owner

@ghost commented on GitHub (Aug 4, 2017):

Hey there! No problem, thanks for the help. We have added an override to remove that, but it's still not working - we receive the same error. I'm curious how the cache expiry setting would be causing issues with this?

@ghost commented on GitHub (Aug 4, 2017): Hey there! No problem, thanks for the help. We have added an override to remove that, but it's still not working - we receive the same error. I'm curious how the cache expiry setting would be causing issues with this?
Author
Owner

@ssddanbrown commented on GitHub (Aug 4, 2017):

Can you post your updated config?

From my understanding of Nginx, It's not anything to do with the caching rule, It's the location block the caching rule is in that's the problem.
Nginx will only match one location block. The location block with the expires is being used for this request so the request is never rooted to the index.php entry point of the app. Thus Nginx will just try to serve it as a static file.

This request should go through the second location block, Not the first as it is now.

@ssddanbrown commented on GitHub (Aug 4, 2017): Can you post your updated config? From my understanding of Nginx, It's not anything to do with the caching rule, It's the location block the caching rule is in that's the problem. Nginx will only match one location block. The location block with the expires is being used for this request so the request is never rooted to the `index.php` entry point of the app. Thus Nginx will just try to serve it as a static file. This request should go through the second location block, Not the first as it is now.
Author
Owner

@ghost commented on GitHub (Aug 5, 2017):

Makes sense. Here are the relevant parts:

server {
    listen              ---
    server_name         ---.---.com;
    root                /home/---/site/---/public/;

    include /etc/nginx/custom.d/server_level/*.conf;

    location ~* ^/images/ {}

    # Direct download
    location ~* ^/(js|static|skin|media|images)/ { expires 1w; }
    location /errors/ { }
    location ~* ^/errors/.*\.xml$ { deny all; }
    location ~* ^/errors/.*\.phtml$ { deny all; }
    # Deny
    location ~* /(\.ht|\.svn|\.git) { deny all; }
    location ~* ^/(app|lib|pkginfo|report/config.xml|var)/ { deny all; }

    autoindex off;

    location / {
        try_files $uri $uri/ /index.php?$args;
        index index.php index.html;
        access_log off;
    }

    location ~* \.(jpeg|jpg|gif|png|css|js|ico|swf)$ {
        try_files $uri $uri/ /get.php;
        expires 1w;
        access_log off;
    }
}
@ghost commented on GitHub (Aug 5, 2017): Makes sense. Here are the relevant parts: ``` server { listen --- server_name ---.---.com; root /home/---/site/---/public/; include /etc/nginx/custom.d/server_level/*.conf; location ~* ^/images/ {} # Direct download location ~* ^/(js|static|skin|media|images)/ { expires 1w; } location /errors/ { } location ~* ^/errors/.*\.xml$ { deny all; } location ~* ^/errors/.*\.phtml$ { deny all; } # Deny location ~* /(\.ht|\.svn|\.git) { deny all; } location ~* ^/(app|lib|pkginfo|report/config.xml|var)/ { deny all; } autoindex off; location / { try_files $uri $uri/ /index.php?$args; index index.php index.html; access_log off; } location ~* \.(jpeg|jpg|gif|png|css|js|ico|swf)$ { try_files $uri $uri/ /get.php; expires 1w; access_log off; } } ```
Author
Owner

@nvnvnvnvn commented on GitHub (Aug 8, 2017):

Hello @ssddanbrown , I know you have lots going on but was wondering if you have ideas on this or know of anyone we can contact who would be more familiar with BookStack that we could hire to help? We can pay you as well if you can work on it. This is a new install for us and we'd really like to be able to make a few more changes and start using it. I'm just not wanting to mess with anything until we get it sorted out.
Thanks so much!

Dan Hill
MachMotion

@nvnvnvnvn commented on GitHub (Aug 8, 2017): Hello @ssddanbrown , I know you have lots going on but was wondering if you have ideas on this or know of anyone we can contact who would be more familiar with BookStack that we could hire to help? We can pay you as well if you can work on it. This is a new install for us and we'd really like to be able to make a few more changes and start using it. I'm just not wanting to mess with anything until we get it sorted out. Thanks so much! Dan Hill MachMotion
Author
Owner

@ssddanbrown commented on GitHub (Aug 9, 2017):

@tylerschade Yeah, Your override won't help there.

Remove the following line:

location ~* ^/images/ {}

And remove just |images from the following line:

location ~* ^/(js|static|skin|media|images)/ { expires 1w; }
@ssddanbrown commented on GitHub (Aug 9, 2017): @tylerschade Yeah, Your override won't help there. Remove the following line: ``` location ~* ^/images/ {} ``` And remove just `|images` from the following line: ``` location ~* ^/(js|static|skin|media|images)/ { expires 1w; } ```
Author
Owner

@ssddanbrown commented on GitHub (Aug 9, 2017):

Hi @nvnvnvnvn, I'm happy to offer support when I can here on GitHub and there's a few others that do help when possible. Personally, I'm not looking to provide paid support services right now.

My previous comment should resolve this issue.

@ssddanbrown commented on GitHub (Aug 9, 2017): Hi @nvnvnvnvn, I'm happy to offer support when I can here on GitHub and there's a few others that do help when possible. Personally, I'm not looking to provide paid support services right now. My previous comment should resolve this issue.
Author
Owner

@nvnvnvnvn commented on GitHub (Aug 10, 2017):

@ssddanbrown wow, thanks so much. @tylerschade made the changes and it is working. Really appreciate it!

@nvnvnvnvn commented on GitHub (Aug 10, 2017): @ssddanbrown wow, thanks so much. @tylerschade made the changes and it is working. Really appreciate it!
Author
Owner

@ghost commented on GitHub (Aug 11, 2017):

Thanks, @ssddanbrown. We appreciate your help.

@ghost commented on GitHub (Aug 11, 2017): Thanks, @ssddanbrown. We appreciate your help.
Author
Owner

@JosephMaxwell commented on GitHub (Aug 11, 2017):

@ssddanbrown: for future reference, what was going on was the hosting provider has a standard nginx configuration. They provide a location to inject configuration, so here is what we figured out:

location  ~*/images {
        try_files $uri $uri/ /index.php?$args;
        break;
}

Essentially, duplicating the location / configuration, we are pointing the images path there.

@JosephMaxwell commented on GitHub (Aug 11, 2017): @ssddanbrown: for future reference, what was going on was the hosting provider has a standard nginx configuration. They provide a location to inject configuration, so here is what we figured out: ``` location ~*/images { try_files $uri $uri/ /index.php?$args; break; } ``` Essentially, duplicating the `location /` configuration, we are pointing the images path there.
Author
Owner

@ssddanbrown commented on GitHub (Aug 12, 2017):

@JosephMaxwell Ah, Okay, makes sense.

Glad you managed to get things working.

@ssddanbrown commented on GitHub (Aug 12, 2017): @JosephMaxwell Ah, Okay, makes sense. Glad you managed to get things working.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: starred/BookStack#387