Server Blocks in nginx - 502 Error - nginx

I have 2 subdomains I want to catch and forward from one server running nginx: foo.acme.com, bar.acme.com
In my nginx.conf file I have set up 2 server blocks:
server {
listen 80;
server_name foo.acme.com;
location / {
proxy_pass http://<my_ip_server_1>:80;
}
}
server {
listen 80;
server_name bar.acme.com;
location / {
proxy_pass http://<my_ip_server_2>:80;
}
}
My 2 subdomains point to the same IP (the one with nginx running on it).
I'm getting 502 Bad Gateway errors on both servers in this configuration.

The 502 code means 502 Bad Gateway, The server was acting as a gateway or proxy and received an invalid response from the upstream server.
It usually means the backend servers are not reachable, which could be a problem with them, not with your front-end configuration.
On the machine running Nginx, you should test that you can rest the backend servers. Using w3m or another HTTP client on that machine, check these URLs. Do they load what you expect?
http://<my_ip_server_1>:80
http://<my_ip_server_2>:80
If not, you may have some updates to make sure that your Nginx server can reach the backend servers.
I should add, you may need send the Host: header to get the backend servers to serve the expected content, if they each host multiple virtual domains. I like to use GET and HEAD tools from the libwww-perl distribution:
GET -H 'Host: bar.acme.com' http://http://<my_ip_server_1>:80
It's important to run the test from the machine hosting Nginx, as running it from your desktop could produce a different result.

Related

Basic proxy_pass from nginx from one local ip to another local ip

I am a new user of nginx and I am following a video guide from Linode on youtube (How to Set Up an NGINX Reverse Proxy).
I have a working nginx and apache server both on port 80. I know that because when I type the ip address of both in firefox, it directs me to nginx/apache welcome page.
The youtube video configuration template is as follow (where the server_name is the linode ip) :
server {
listen 80;
listen [..]:80;
server_name 172.105.104.226;
location / {
proxy_pass http://localhost:3000/;
}
On my Proxmox machine, the nginx server is on a VM at 192.168.1.241 and the apache server on another VM at 192.168.1.243.
Looking at nginx documentation we find that this :
location /some/path/ {
proxy_pass http://www.example.com/link/;
}
should proxy all the traffic received on the nginx listening port and redirect it to the address specified by proxy pass.
With all these information, my configuration file is like this :
server {
listen 80;
listen [::]:80;
server_name 192.168.1.241;
location / {
proxy_pass http://192.168.1.243;
}
}
My understanding is that this configuration file should listen at the address 192.168.1.241 on port 80 (nginx server) and redirect it to the specified address 192.168.1.243 (apache server)/
If i understand correctly, Location / should take the request as is received on the nginx server and redirect it to the apache server.
However, when I enter 192.168.1.241 in my browser, it doesn't show the apache welcome message but shows the nginx welcome message. That means that the proxy isn't working.
My nginx understanding is extremely limited as I am just starting to learn, but to me it seems like this should work but doesn't.
Thank you for your help
It turns out that the configuration is correct.
The problem was that the webpage was cached. By forcing a full refresh, 192.168.1.241 redirected to 192.168.1.243 successfully.

How to let the backend api handle https certificate?

I'm new to nginx.
I have a machine, behind my router, that runs a server and handles correctly 80 and 443 request with Https.
Problem is that I want to host a second website on another device but I have only one IP address. I bought a raspberry pi zero to use it as a reverse proxy behind my router. I install nginx and want to redirect all the request to my other machines. Both the RPI 0 and the old machine have local IP.
To redirect requests from my router to RPI 0 and then to my old machine, I used proxy_pass. On port 80 everything works fine, but on port 443 I get a certificate error on my browser.
Is it possible to let the whole request go on the old machine and let the old machine handles the https certificate like before ? Or is it mandatory to have the certificate processed by nginx ?
Diagram of the old but functional installation
Current installation with certificate error
My configuration:
upstream backend_a {
server 192.168.0.20:80;
}
upstream backend_a_s {
server 192.168.0.20:443;
}
server {
listen 80;
server_name mydomain;
location / {
include proxy_params;
proxy_pass http://backend_a;
}
}
server {
listen 443 ssl;
server_name mydomain;
location / {
include proxy_params;
proxy_pass https://backend_a_s;
}
}
I found a solution. I need to use port forwarding. To do this in nginx, I need to use stream keyword.
stream {
server {
listen 443;
proxy_pass 192.168.0.20:443;
}
}
The stream keyword need to be at the same level as http, so I needed to edit /etc/nginx/nginx.conf source. Other solution is to manually compile a version of nginx, with the parameter --with-stream source.

Nginx Reverse Proxy upstream not working

I'm having trouble figuring out load balancing on Nginx. I'm using:
- Ubuntu 16.04 and
- Nginx 1.10.0.
In short, when I pass my ip address directly into "proxy_pass", the proxy works:
server {
location / {
proxy_pass http://01.02.03.04;
}
}
When I visit my proxy computer, I can see the content from the proxy ip...
but when I use an upstream directive, it doesn't:
upstream backend {
server 01.02.03.04;
}
server {
location / {
proxy_pass http://backend;
}
}
When I visit my proxy computer, I am greeted with the default Nginx server page and not the content from the upstream ip address.
Any further assistance would be appreciated. I've done a ton of research but can't figure out why "upstream" is not working. I don't get any errors. It just doesn't proxy.
Okay, looks like I found the answer...
two things about the backend servers, at least for the above scenario when using IP addressses:
a port must be specified
the port cannot be :80 (according to #karliwsn the port can be 80 it's just that the upstream servers cannot listen to the same port as the reverse proxy. I haven't tested it yet but it's good to note).
backend server block(s) should be configured as following:
server {
# for your reverse_proxy, *do not* listen to port 80
listen 8080;
listen [::]:8080;
server_name 01.02.03.04;
# your other statements below
...
}
and your reverse proxy server block should be configured like below:
upstream backend {
server 01.02.03.04:8080;
}
server {
location / {
proxy_pass http://backend;
}
}
It looks as if a backend server is listening to :80, the reverse proxy server doesn't render it's content. I guess that makes sense, since the server is in fact using default port 80 for the general public.
Thanks #karliwson for nudging me to reconsider the port.
The following example works:
Only thing to mention is that, if the server IP is used as the "server_name", then the IP should be used to access the site, means in the browser you need to type the URL as http://yyy.yyy.yyy.yyy or (http://yyy.yyy.yyy.yyy:80), if you use the domain name as the "server_name", then access the proxy server using the domain name (e.g. http://www.yourdomain.com)
upstream backend {
server xxx.xxx.xxx.xxx:8080;
}
server {
listen 80;
server_name yyy.yyy.yyy.yyy;
location / {
proxy_pass http://backend;
}
}

502 bad gateway on backend servers (nginx upstream module)

Hi have an 502 bad gateway problem when upstream server connects to NGINX backend servers (nodes).
if I use NGINX on backend servers then I got 502 bad gateway, if I use apache web server then no errors. doesn't matter if I use IPs instead of domains example server 192.101.876.76:8081
nginx.conf
http {
upstream appserver {
server backend1.example.com; # with NGINX web server gives an 502 bad gateway when connected, with apache works fine
server backend2.example.com; # with NGINX web server gives an 502 bad gateway when connected, with apache works fine
}
}
server {
listen 80;
server_name example.com;
location / {
proxy_pass http://appserver;
}
}
**If I use Apache web server on backend1.example.com and backend2.example.com then it works. But I would like to use nginx because its more reliable and faster than apache.
Why it don't work with NGINX backend server?

Proxy/gateway for HTTP binding

I have following infrastructure and want to provide an online web chat (on server 1) using our internal xmpp server (server 2), which is running an Openfire server.
wan <----> server 1 <----> server 2
Server 1 can only reach server 2 over a HTTP proxy. So I need a possibility to get a HTTP binding or something else on server 1, which provides the bindings for a web chat like JWChat or Co.
I think a simple redirect to the HTTP binding on server 2 would be good, but I don't know how.
Perhaps there is another possibility, thanks for any advices.
EDIT:
The nginx configuration is now like the following:
server {
listen 8000;
server_name server1 localhost;
location ~ ^/http-bind {
proxy_pass http://server2:8085;
}
location / {
proxy_pass http://proxy:3128;
}
}
But the following commands doesn't work correctly:
-bash-4.1# wget http://localhost:8000
--2012-02-06 10:57:14-- http://localhost:8000/
Resolving localhost... 127.0.0.1
Connecting to localhost|127.0.0.1|:8000... connected.
HTTP request sent, awaiting response... 400 Bad Request
2012-02-06 10:57:14 ERROR 400: Bad Request.
-bash-4.1# wget http://localhost:8000/http-bind
--2012-02-06 10:57:21-- http://localhost:8000/http-bind
Resolving localhost... 127.0.0.1
Connecting to localhost|127.0.0.1|:8000... connected.
HTTP request sent, awaiting response... 502 Bad Gateway
2012-02-06 10:57:21 ERROR 502: Bad Gateway.
What is wrong?
Typically server 1 will be running:
A proxy
A webserver running your chat app.
Let's assume nginx as a proxy running on port 80, and your choice of a webserver running on port 8080. Also assume that your web client will bind to /http-bind. Your nginx config will then contain:
server {
listen 80;
server_name server1;
location ~ ^/http-bind {
proxy_pass http://server2:5280;
}
location / {
proxy_pass http://localhost:8080/;
}
}
Adapt accordingly for some other proxy.

Resources