serving two websites with nginx - http

I want to run a simple nginx page that serves two pages. One from folder ~/A and one from ~/B
Each folder runs a copy of Python's SimpleHTTPServer in ports 1000 and 2000
Each file has a single file called index.html with text Hello World!
server {
listen 80;
index index.html index.htm;
# Make site accessible from http://localhost/
server_name localhost;
location / {
root ~/A;
proxy_pass http://localhost:1000;
}
location /B/ {
root ~/B;
proxy_pass http://localhost:2000;
}
}
Unfortunately curl http://localhost/B/index.html returns a 404.
<head>
<title>Error response</title>
</head>
<body>
<h1>Error response</h1>
<p>Error code 404.
<p>Message: File not found.
<p>Error code explanation: 404 = Nothing matches the given URI.
</body>
What is wrong with my nginx conf file? Why can't it route properly?

I think you want use alias ~/B instead of root ~/B because your location /B/ will try ~/B/B. See alias and root documentations.

you can open the nginx debug log and s.
i think this url will matches 'location \' and goto A.

Related

Nginx reverse proxy return 502

I'm very new to nginx and server game and i'm trying to setup a reverse proxy. Basically what i need is when i enter my server ip it should open a particular website (Ex: https://example.com).
So for example if i enter my ip (Ex: 45.10.127.942) it should open the website example.com , but the url should remain as http://45.10.127.942.
I tried to set my server configuration as follows but it returns a 502 error.
server {
listen 80;
location / {
proxy_pass http://example.com;
}
}
It returns a 502 error. Can you please explain what i need to do?
You can have something like this in your configuration file:
server {
root /var/www/html;
server_name _;
location / {
try_files $uri $uri/ /index.html;
}
}
Place the index.html file in root folder specified.
Then just restart the NGINX and it should work.
What is the problem with your configuration file is you should not proxy_pass.
If you want to open the other website, you should have DNS record pointing to that IP. What actually happens is the thing you are trying to do is known as CLICKJACKING. For more details, search CLICKJACKING on google and you will find a lot of references.

nginx serve index file from subfolders

I would like to serve an index file from a root folder and one from a subfolder from root.
My nginx server conf looks as follows:
server {
listen 80;
server_name localhost;
root /data/;
index index.html index.htm index.txt;
location / {
}
location /a {
alias /data/a/;
}
}
and my directory structure looks as follows:
/data/:
a index.txt
/data/a:
index.txt
If I then do curl localhost, I get the contents of the file /data/index.txt.
But curl /localhost/a gives me a 301.
curl localhost/a/index.txt works.
Why can't I access my index.txt with curl /localhost/a ?
I tried using a root instead of alias in the location /a block and also tried to specify the index.txt for location /a, but no success.
I see similar posts, e.g.
Nginx location configuration (subfolders)
but couldn't yet find the answer.
The index directive works with URIs that end with a /:
So the URI / gives you the contents of /index.txt and /a/ gives you the contents of `/a/index.txt.
If you provide Nginx with a URI of a directory (but without a trailing /), the default behaviour is to redirect to the same URI, but with a trailing /.
This is just how the index directive works. See this document for details.
If you want something other than default behaviour you will have to do it manually using try_files. See this document for details.
For example, to return the contents of an index.txt file by providing the URI of the directory without a trailing /, use:
root /data;
location / {
try_files $uri $uri/index.txt =404;
}
Note that the location /a { ... } block is not necessary in either this example, or the example in your question.

Redirect nginx /index.html to root causing infinite redirects

I want to avoid having the same HTML page accessible on www.example.com and www.example.com/index.html, i.e i want to redirect the index.html to root.
This:
location = /index.html {
return 301 $scheme://www.example.com;
}
is causing me to get ERR_TOO_MANY_REDIRECTS, a redirect loop.
Any ideas what can i change to make it work?
PS this is my entire nginx conf
server {
listen 443 ssl http2 default_server;
listen [::]:443 ssl http2 default_server;
include /etc/nginx/snippets/ssl-example.com.conf;
include /etc/nginx/snippets/ssl-params.conf;
include /etc/nginx/snippets/letsencrypt-challenge.conf;
root /var/www/newsite;
index index.php index.html index.htm;
server_name www.example.com;
location / {
# try_files $uri $uri/ =404;
try_files $uri $uri/ /index.php?q=$uri&$args;
}
location = /index.html {
return 301 $scheme://www.example.com;
}
}
This is not a detailed treatment of the subject but a simplified explanation just to answer your dilemma. The answer is that you need to abandon the attempt to do what you are doing.
Webservers can only serve specific files such as an xyz.html file. They cannot serve folders.
A call to https://www.example.com/abc/index.html is a request for the index.html file in the abc folder of the web root. A call to https://www.example.com/abc on the other hand is a request for the abc folder of the web root, which as mentioned, cannot be served.
As you have noticed however, the second call results in https://www.example.com/abc/index.html being served. This is because webservers are generally set up such that when a call is made to a folder without specifying a specific file to serve, a redirect to the index.html file in that folder is generated and this is served instead. That is, the webserver internally turns the request for https://www.example.com/abc into a request for https://www.example.com/abc/index.html.
This is what the index index.php index.html index.htm; line in your config does. It says "if there is a request for a folder without a file specified, serve the index.php file instead. If there is not such file, serve the index.html. If there is not such file, serve the index.htm file. If this also does not exist, throw a fit"
The problem is that you then go on to instruct your webserver to redirect requests for https://www.example.com/index.html to https://www.example.com which the webserver redirects back to https://www.example.com/index.html which is again redirected back to https://www.example.com in an endless loop until the webserver or your browser finally gives up.
You stated that I want to avoid having the same HTML page accessible on www.example.com and www.example.com/index.html, i.e i want to redirect the index.html to root. The question is why? There is absolutely no benefit in doing this and as you found out, you end up in a redirect loop.
You may be trying some SEO stuff but this does not apply here.

Why nginx not able to serve sites in different locations?

I want to use nginx to host some static html which is located in different path on my pc, below is my configuration:
server {
listen 8080;
server_name localhost;
location /chatserver {
root /Users/xxxx/gitrepo/chatserver/public;
index index.html;
}
location /test {
root /Users/xxxx/test/test_site;
index index.html;
}
The file structure is:
Users
|-xxxx
|-gitrepo
| |-chatserver
| |-public
| |- index.html
|-test
|-test_site
|- index.html
But when I access: http://localhost:8080/chatserver or http://localhost:8080/test, nginx always responds 404 Not Found.
If I access: http://localhost:8080/, nginx will return the default nginx welcome page.
Why is my configuration not working?
I think you should use alias instead of root.
In your example the URL /chatserver/index.html will search the /Users/xxxx/gitrepo/chatserver/public/chatserver/index.html (note the "undesired" chatserver after public!). Check your nginx's logfiles!
See documentation of root and documentation of alias.

When do we need to use http block in nginx config file?

I am reading nginx beginner's tutorial, on the section Serving Static Content they have
http {
server {
}
}
but when I add an http block I get the error
[emerg] "http" directive is not allowed here …
When I remove the http block and change the conf file to this, it works fine:
server {
listen 80 default_server;
listen [::]:80 default_server ipv6only=on;
root /var/example.com/html;
index index.html index.htm;
# make site accessible from http://localhost/
server_name localhost
location / {
try_files $uri $uri/ /index.html;
}
I suspect that I am missing something simple, but why do they use http to serve static files?
Your doing fine. I guess you are editing /etc/nginx/sites-enabled/default (or the linked file at /etc/nginx/sites-available/default.
This is the standard nginx set up. It is configured with /etc/nginx/nginx.conf which contains the http {} statement. This in turn contains an "include /etc/nginx/sites-enabled/*" line to include your file above with server{ } clause in it.
Note that if you are using an editor that creates a backup file, you must modify the include statement to exclude the backup files, or you will get some "interesting" errors! My line is
include /etc/nginx/sites-enabled/*[a-zA-Z]
which will not pick up backup files ending in a tilde. YMMV.

Resources