
As part of a web project running under Docker with Nginx, I ran into an issue with a VueJS project.
Table of contents
Real-world use case
Your page refreshes return a 404 error on a VueJS SPA behind Nginx: here's the configuration that fixes this behavior.
As part of a web project running under Docker with Nginx, I ran into an issue with a VueJS project. The absolute path isn't known by the Nginx server due to normal VueJS behavior. A 404 error appears when refreshing a URI.
Configuring Nginx with VueJS
When using an Nginx web server with VueJS, you may have run into the 404 error. As a reminder, Nginx is a web server and VueJS is a JavaScript framework. Once our web application is finished with VueJS, it needs to be transpiled and minified with webpack. At the end of this, we get a ready-to-use "dist" folder that the Nginx server will host and serve. However, we quickly notice a 404 error appearing when accessing our various URIs (e.g., https://kassianoff.fr/**blog/**).
Our environment
In my case, I'm using the latest version of Nginx, 1.21.6, dated January 25, 2022. The server is published as a micro-service with a default configuration. The dist folder is placed in the web server's default location. I access my production server fine, but as soon as I refresh the page on a URI, I get a 404 web error.
VueJS
During the development phase in VueJS, a router using "hash" mode by default is used, which poses no problem in the local (or online) environment, since it uses a hash character (#) before the URL passed internally. Since this part of the URL is never sent to the server, it doesn't require any special handling.
In production (behind a reverse proxy), the home page is accessible normally with no issues. However, when you refresh the page, a 404 error will appear, and the resource being accessed can't be found on the server, because the routing address defined by the Vue router is treated as the URL address, yet that address path doesn't exist, hence the 404 issue.
Nginx
Looking at my Nginx server's default configuration, there's no real "menu/index" resource under the /dist root directory in the Nginx configuration. These access resources are rendered in JS. The server's initial Nginx configuration is as follows (assuming the domain name is: kassianoff.fr):
server
{
listen 80;
server_name kassianoff.fr;
index index.php index.html index.htm default.php default.htm default.html;
root /var/www/kassianoff/dist;
}
The Vue router jump parameter therefore needs to be added to the server's Nginx configuration. The first page here is index.html. The correct configuration is as follows:
server
{
listen 80;
server_name kassianoff.fr;
index index.php index.html index.htm default.php default.htm default.html;
root /var/www/kassianoff/dist;
#Vue router configuration
location / {
try_files $uri $uri/ @router;
index index.html;
}
location @router {
rewrite ^.*$ /index.html last;
}
}
After restarting the Nginx server, the problem is gone. You'll notice the configuration is simple, since I don't use Nginx directly facing the web but behind a reverse proxy that handles TLS as well as routing with specific middlewares. If you run into any issue, feel free to share your feedback on the topic.

