If I try to delete wave slash from URL, /index answers 404 Not Found - nginx

I'm working on a docker Nginx server on local, this is my conf.d/default.conf configuration:
server {
listen 80;
listen [::]:80;
server_name localhost;
return 301 https://$host$request_uri;
}
server {
listen 443 ssl;
server_name localhost;
ssl_certificate /etc/ssl/certs/localhost.pem;
ssl_certificate_key /etc/ssl/private/localhost.key;
root /usr/share/nginx/html;
index index.html index.htm;
location / {
try_files $uri $uri/ /index.html;
}
location ~ ^/~(.+?)(/.*)?$ {
alias /home/$1/public_html$2;
index index.html index.htm;
autoindex on;
}
}
This configuration works perfectly, but for last "location" block, which works as an "userDir" directive, I have to type an URL like this: https://localhost/~user1/
In order to remove that trailing slash, I tried:
location ~ ^/(.+?)(/.*)?$ {
alias /home/$1/public_html$2;
index index.html index.htm;
autoindex on;
}
This solution works fine and answers with the index.html content in "/home/user1/public_html" by using the URL https:/localhost/user1 which is how I want it to work, but then, root content (https:/localhost/) becomes 404 Not Found.
Hope I did explain it well and someone has a solution! Thank you in advance!!

Related

Can't serve two static websites with Nginx

I have two React build folders and I want to access them like this :
https://example.com/ -> /var/www/web_client/
https://example.com/videochat/ -> /var/www/videochat/
Here is my nginx configuration file :
server {
listen 80 default_server;
listen [::]:80 default_server;
server_name example.com;
location / {
root /var/www/web_client;
try_files $uri /index.html;
}
location /videochat/ {
root /var/www/videochat;
try_files $uri /index.html;
}
listen [::]:443 ssl ipv6only=on;
listen 443 ssl;
ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;
include /etc/letsencrypt/options-ssl-nginx.conf;
ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem;
}
The location block / works perfectly but /videochat/ redirects me to the 404 page of /var/www/web_client and not the index.html of /var/www/videochat.
How can I fix this error and get nginx to serve both static websites on the same server ?
I tried to reverse the two like this to make sure the error is coming from nginx:
location / {
root /var/www/videochat;
try_files $uri /index.html;
}
location /web_client/ {
root /var/www/web_client;
try_files $uri /index.html;
}
Now it's the other way around, the location block / redirects me to the index.html of /var/www/videochat as expected but /web_client/ redirects me to /var/www/videochat and not the index.html of /var/www/web_client.
I think you can try having /videochat location block first and then then the / location block.
Because location /, will be the block that gets used for both / as well /videochat.
Only if we specify '=' in the location match, it will be a exact match, if not requested URI will be matched against the beginning of the mentioned URI in the location block.
For many location blocks it will be better to use regex.
You can refer to article like this for more info:
https://www.digitalocean.com/community/tutorials/nginx-location-directive

I can't change path server name on nginx

I can't change path server name on nginx for example.com to example.com/home1 at (root /var/www/html/public ). please you recommend how to config ? Thank you.
server {
listen 80;
listen 443 ssl;
server_name example.com;
return 301 http://example.com/home1;
root /var/www/html/public;
index index.php index.html index.htm;
location / {
try_files $uri $uri /index.php?$args;
}
/home1 should be in the location selector instead. Remove the equals before /home1 if you want it to match anything with /home1 instead.
server {
listen 80;
listen 443 ssl;
server_name example.com;
root /var/www/html/public;
index index.php index.html index.htm;
location = /home1 {
try_files $uri $uri /index.php?$args;
}
}

Nginx redirection from any subfolder to root index.html

Anything put as a subfolder, it will read the domain.com/index.html
Similar to this but in Nginx
Redirect URL non existent subfolder to root
server {
listen 80;
listen [::]:80;
server_name example.com;
root /apt/website/path;
index index.html;
location / {
try_files $uri $uri/ /index.html;
}
}

Nginx is serving the default content instead of my content

I have a nginx version: nginx/1.10.3 (Ubuntu) running on Ubuntu 16.04.2 LTS.
I use nginx to serve static files, bundles generated by webpack, but that's irrelenvant.
What I want to achieve is this:
On example.com I want to serve /home/bundles/main/index.html. I can do this.
On projects.example.com/project_1 I want to serve /home/bundles/project_1/index.html.
On projects.example.com/project_2 I want to serve /home/bundles/project_2/index.html.
The last two, I can't do. When I go to projects.example.com/project_1 or projects.example.com/project_2 I am served the default nginx page.
To make things more confusing /etc/nginx/sites-enabled/default is entirely commented out.
Additionally, if in the location block of projects.example.com I replace, for example, project_1 with /, I will be served that specific project, but then I will have no way of serving the other.
Bellow, I will show you my nginx configuration
server {
listen 80;
server_name example.com;
location / {
root /home/bundles/main;
try_files $uri /index.html;
}
if ($scheme != "https") {
return 301 https://$host$request_uri;
}
}
server {
listen 443 ssl;
server_name example.com;
location / {
root /home/bundles/main;
try_files $uri /index.html;
}
ssl_certificate ...
ssl_certificate_key ...
}
server {
listen 80;
server_name projects.example.com;
location /project_1 {
root /home/bundles/project_1;
try_files $uri /index.html;
}
location /project_2 {
root /home/bundles/project_2;
try_files $uri /index.html;
}
if ($scheme != "https") {
return 301 https://$host$request_uri;
}
}
server {
listen 443 ssl;
server_name projects.example.com;
location /project_1 {
root /home/bundles/project_1;
try_files $uri /index.html;
}
location /project_2 {
root /home/bundles/project_2;
try_files $uri /index.html;
}
ssl_certificate ...
ssl_certificate_key ...
}
Thank you for your help!
EDIT
My Answer
The solution I found was to change the root with alias.
server {
listen 80;
server_name example.com;
location / {
root /home/bundles/main;
try_files $uri /index.html;
}
if ($scheme != "https") {
return 301 https://$host$request_uri;
}
}
server {
listen 443 ssl;
server_name example.com;
location / {
root /home/bundles/main;
try_files $uri /index.html;
}
ssl_certificate ...
ssl_certificate_key ...
}
server {
listen 80;
server_name projects.example.com;
location /project_1 {
alias /home/bundles/project_1;
index index.html;
}
location /project_2 {
alias /home/bundles/project_2;
index index.html;
}
if ($scheme != "https") {
return 301 https://$host$request_uri;
}
}
server {
listen 443 ssl;
server_name projects.example.com;
location /project_1 {
alias /home/bundles/project_1;
index index.html;
}
location /project_2 {
alias /home/bundles/project_2;
index index.html;
}
ssl_certificate ...
ssl_certificate_key ...
}
The solution is based on these two answers. The first answer showing how to solve the problem and the second answer providing a explanation as to why alias works and root does not.
To quote #treecoder
In case of the root directive, full path is appended to the root including the location part, whereas in case of the alias directive, only the portion of the path NOT including the location part is appended to the alias.
In my particular case, this would translate like this;
With root, the path nginx would try to access would be /home/bundles/project_1/project_1.
With alias it accesses the correct path, /home/bundles/project_1.
Going back one level, for example, saying:
root /home/bundles/ is not really a option either. That is because my projects are not actually called project_1 and project_2. The actual structure is more similar to this.
In /bundles I have the directories project_a and project_b. I want to route project_1 to the project_a directory and project_2 to the project_b directory.
That is why I used alias.
I hope this helps.
You have:
location /project_1 {
root /home/bundles/project_1;
try_files $uri /index.html;
}
So the root is only defined for URIs that begin with /project_1. For any other URI, the default root will be used.
If you present the URI /project_1/ (with a trailing /), assuming that the default index directive is in force, nginx should return your /project_1/index.html content.
However, the URI /project_1 is not found - so /index.html is returned instead. The URI /index.html does not begin with /project_1, so the default root is used.
If you want the URI /project_1 to work as expected, and the default action to go to the project's index.html file, change the try_files directive.
location /project_1 {
root /home/bundles/project_1;
try_files $uri $uri/ /project_1/index.html;
}
See this document for more.
As both projects share a common root, you could simplify as follows:
server {
listen 80;
server_name projects.example.com;
root /home/bundles
index index.html;
location /project_1 {
try_files $uri $uri/ /project_1/index.html;
}
location /project_2 {
try_files $uri $uri/ /project_2/index.html;
}
location / {
deny all;
}
}
I added the index directive to avoid relying on the default value (which is the same), and a location block to deny access to areas outside of the projects.
I had the same problem...and it turned out, for me, that the default site that was "overtaking" my desired secondary site and serving the default files...well it allowed IP6 requests, and my new site didn't.
Here's an example of my access.log:
::1 - - [05/Sep/2020:15:05:16 -0600] "GET / HTTP/1.1" 200 40 "-" "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/85.0.4183.83 Safari/537.36"
Notice the ::1 bit? That's an IP6 request that I guess my browser was defaulting to. So I just made sure to enable local IP6 requests for the site in question in my site config file by changing:
listen 80;
server_name example.local;
to:
listen 80;
listen [::]:80;
server_name example.local;
That was it.

Nginx configuration causing too many redirects

I have a conf file with example.com as the root. In the example.com directory, there is an html, css, img, and js folder. I understand this deviates from the traditional html directory as root. I have tried many different configurations (using regex based on filetypes, variables, etc.) but I always get too many redirect errors. Can anyone help on a good conf file for this type of directory structure? Here is my conf file currently.
server {
listen 80 default_server;
listen [::]:80 default_server;
# return 301 https://$server_name$request_uri;
listen 443 ssl http2 default_server;
listen [::]:443 ssl http2 default_server;
include snippets/ssl-example.com.conf;
include snippets/ssl-params.conf;
server_name www.example.com example.com;
root /var/www/www.example.com/;
index index.php index.html;
client_max_body_size 100m;
error_page 404 = error.html?error=404;
location ~ /.well-known {
allow all;
}
location / {
location ~* \.(html|php)$ {
root html/;
}
location ~* \.css$ {
root css/;
}
location ~* \.js$ {
root js/;
}
location ~* \.(png|jpeg|gif)$ {
root img/;
}
try_files $uri =404;
}
}
Thanks in advance for any help!
Here is the configuration I ended up using:
server {
listen 80 default_server;
listen [::]:80 default_server;
# return 301 https://$server_name$request_uri;
listen 443 ssl http2 default_server;
listen [::]:443 ssl http2 default_server;
include snippets/ssl-example.com.conf;
include snippets/ssl-params.conf;
server_name www.example.com example.com;
root /var/www/www.example.com/;
index index.php index.html;
client_max_body_size 100m;
error_page 404 = /html/error.html?error=404;
location ~ /.well-known {
allow all;
}
location = / {
try_files /html/index.html =404;
}
location / {
location ~* \.(html|php)$ {
try_files $uri /html/$uri =404;
}
location ~* \.css$ {
try_files $uri /css/$uri =404;
}
location ~* \.js$ {
try_files $uri /js/$uri =404;
}
location ~* \.(png|jpeg|gif)$ {
try_files $uri /img/$uri =404;
}
try_files $uri =404;
}
}
My problem was that all of my redirects were using relative pathing (such as try_files html/$uri) instead of absolute pathing from the site root (/html/$uri). This lead to redirects like /html/html/html/...
I thought that if I used an absolute path, it would be absolute to the root of the server, and not the site.
My only issue now is that my parameter on my error page redirect (?error=404) doesn't work with absolute pathing, but that not a huge deal.

Resources