ingress-nginx config use custom variables - kubernetes

I have a nginx conf like below
map $http_upgrade $connection_upgrade {
default upgrade;
'' close;
}
server {
listen 80 default_server;
access_log off;
return 200 'Hello, World! - nginx\n';
}
server {
listen 80;
server_name ~^(dev-)?(?<app>[^.]+)\.mysite\.com$;
access_log off;
location / {
resolver 127.0.0.11;
proxy_set_header Host $host;
proxy_pass http://${app}-web;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
}
}
I expected that redirecting
dev-blog.mysite.com into service blog-web
dev-market.mysite.com into service market-web
and so on
Is there any way to implement this in k8s ingress-nginx?

No, you would make a separate Ingress object for each (or one huge one, but that's less common). Usually this is semi-automated through either Helm charts or custom controllers.

Related

Nginx returns blank page while serving Flutter DevTools with reverse proxy. (Ubuntu)

When I access https://my.server.com, it returns blank page.
When I access http://myserver_external_ip:9100, it returns DevTools as expected.
I checked "my.server.com" by using Chrome DevTools, there was no error log.
server {
server_name my.server.com; # my domain
location / {
proxy_pass http://localhost:9100;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "Upgrade";
proxy_set_header Host $host;
}
listen 443 ssl;
}
server {
if ($host = my.server.com) {
return 301 https://$host$request_uri;
} # managed by Certbot
listen 80 ;
listen [::]:80 ;
server_name my.server.com; # my domain
return 404;
}
I think both urls return same pages.

NGINX not respecting server_name regex

I have this nginx config.. i want it to accept all domains that have the word competitions in it and end with .com.au.. I have tested with a domain name that should NOT be accepted but it reaches the application.. is the server_name being ignore because I'm using a proxy?
server {
listen 80 default_server;
server_name ~^(.+)competitions?(.+)\.com\.au;
access_log /var/log/nginx/$host.access.log;
error_log /var/log/nginx/error.log;
if ($host !~* ^www){
rewrite ^/(.*)$ https://www.$host/$1 permanent;
}
location / {
proxy_no_cache 1;
proxy_set_header Host $host;
proxy_pass http://127.0.0.1:8888;
try_files $uri $uri/ #proxy;
}
location #proxy {
proxy_set_header Host $host;
proxy_pass http://127.0.0.1:8888;
proxy_intercept_errors on;
recursive_error_pages on;
error_page 404 = #rewrite_proxy;
}
location #rewrite_proxy {
rewrite /(.*) /index.cfm?path=$1;
proxy_set_header Host $host;
proxy_pass http://127.0.0.1:8888;
}
}
You'd have to remove the default_server from there, because this is a catch-all directive.And you still could setup another one server with the default_server directive, if required.
See How nginx processes a request for a more detailed explanation:
If its value does not match any server name, or the request does not contain this header field at all, then nginx will route the request to the default server for this port.

Artifactory docker registry docker image

I am playing around with the 4.13 version of artifactory using the pro-registry docker image
I created a virtual docker repo and a local docker repo as suggested in the doc and changed the nginx conf as follows
log into the running container
sudo docker exec -i -t containerID# /bin/bash
vi /etc/nginx/conf.d/default.conf
ssl_certificate /etc/nginx/ssl/demo.pem;
ssl_certificate_key /etc/nginx/ssl/demo.key;
ssl_session_cache shared:SSL:1m;
ssl_prefer_server_ciphers on;
server {
listen 80;
listen 443 ssl;
client_max_body_size 2048M;
location / {
proxy_set_header Host $host;
proxy_pass http://localhost:8081/artifactory/;
proxy_read_timeout 90;
}
access_log /var/log/nginx/access.log upstreamlog;
location /basic_status {
stub_status on;
allow all;
}
}
## Sub domain config for docker repository
server {
listen 443 ssl;
listen 80 ;
server_name my-docker-virtual.art.local art.local;
if ($http_x_forwarded_proto = '') {
set $http_x_forwarded_proto $scheme;
}
## Application specific logs
access_log /var/log/nginx/docker-access.log;
error_log /var/log/nginx/docker-error.log;
rewrite ^/(v1|v2)/(.*) /artifactory/api/docker/my-docker-virtual/$1/$2;
client_max_body_size 0;
chunked_transfer_encoding on;
location /artifactory/ {
proxy_read_timeout 900;
proxy_pass_header Server;
proxy_cookie_path ~*^/.* /;
proxy_pass http://artifactory_lb/artifactory/
proxy_set_header X-Artifactory-Override-Base-Url $http_x_forwarded_proto://$host:$server_port/artifactory;
proxy_set_header X-Forwarded-Port $server_port;
proxy_set_header X-Forwarded-Proto $http_x_forwarded_proto;
proxy_set_header Host $http_host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
}
This works great I can do the following
docker login my-docker-virtual.art.local
user
pass
email
docker push my-docker-virtual.art.local/busybox
docker pull busybox
However when I change the nginx o the following
ssl_certificate /etc/nginx/ssl/demo.pem;
ssl_certificate_key /etc/nginx/ssl/demo.key;
ssl_session_cache shared:SSL:1m;
ssl_prefer_server_ciphers on;
server {
listen 80;
listen 443 ssl;
client_max_body_size 2048M;
location / {
proxy_set_header Host $host;
proxy_pass http://localhost:8081/artifactory/;
proxy_read_timeout 90;
}
access_log /var/log/nginx/access.log upstreamlog;
location /basic_status {
stub_status on;
allow all;
}
}
## Sub domain config for docker repository
server {
listen 443 ssl;
listen 80 ;
server_name my-docker-virtual.art.local art.local;
if ($http_x_forwarded_proto = '') {
set $http_x_forwarded_proto $scheme;
}
## Application specific logs
access_log /var/log/nginx/docker-access.log;
error_log /var/log/nginx/docker-error.log;
rewrite ^/(v1|v2)/(.*) /artifactory/api/docker/wrong-docker-virtual/$1/$2;
client_max_body_size 0;
chunked_transfer_encoding on;
location /artifactory/ {
proxy_read_timeout 900;
proxy_pass_header Server;
proxy_cookie_path ~*^/.* /;
proxy_pass http://localhost:8081/artifactory/
proxy_set_header X-Artifactory-Override-Base-Url $http_x_forwarded_proto://$host:$server_port/artifactory;
proxy_set_header X-Forwarded-Port $server_port;
proxy_set_header X-Forwarded-Proto $http_x_forwarded_proto;
proxy_set_header Host $http_host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
}
after this I reload the config
Everything still works which it should not, the redirect should fail. Shouldnt it?
Note that I am using the self signed cert that comes with the docker image
So I had to do a service nginx restart in order to see these changes reflected

How to change request_uri in nginx proxy_pass?

I am running a django application through gunicorn via unix socket and I have my nginx configuration which looks like this :
Current NGINX config File :
upstream django_app_server {
server unix:/django/run/gunicorn.sock fail_timeout=0;
}
server{
listen 80;
server_name demo.mysite.com;
location / {
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_redirect off;
if (!-f $request_filename) {
proxy_pass http://django_app_server;
break;
}
}
}
so my django is running on a unix socket here , lets say if it was running on localhost then it has a url which looks like :
http://127.0.0.1:8000/demo/app1
http://127.0.0.1:8000/demo/notifications
Main goal
so what i want to do is , when someone visit http://demo.mysite.com/app1 they can access via proxy pass the url : http://127.0.0.1:8000/demo/app1
It would have been really easy if i would be running django on localhost tcp port and i could have easy done this and it would have worked for me :
server{
listen 80;
server_name demo.mysite.com;
location / {
proxy_pass http://127.0.0.1:8000/demo/;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
}
How do i achieve this with my current nginx configurtion ?
One approach is to use rewrite ... break, for example:
location / {
try_files $uri #proxy;
}
location #proxy {
rewrite ^ /demo$uri break;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_redirect off;
proxy_pass http://django_app_server;
}
See this document for details.

Nginx https reverse proxy infinite loop

this is my site-available nginx configuration for flask application
server {
listen 80;
server_name _;
access_log /var/log/nginx/nginx_access.log;
error_log /var/log/nginx/nginx_error.log;
rewrite ^ https://$http_host$request_uri? permanent;
}
server {
listen 443;
server_name _;
access_log /var/log/nginx/nginx_access.log;
error_log /var/log/nginx/nginx_error.log;
ssl on;
ssl_certificate /etc/nginx/ssl/<redacted>.pem;
ssl_certificate_key /etc/nginx/ssl/<redacted>.key;
ssl_session_timeout 5m;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_ciphers "HIGH:!aNULL:!MD5 or HIGH:!aNULL:!MD5:!3DES";
ssl_prefer_server_ciphers on;
location / {
proxy_pass http://127.0.0.1:5000;
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
I have gone through the questions
Nginx configuration leads to endless redirect loop
and nginx redirect loop with ssl. I seem to have the configuration specified in them already.
EDIT
Flask application is running via gunicorn/supervisord
Supervisor config.conf
[program:config]
command=/usr/local/bin/gunicorn run:app --config /etc/gunicorn/gunicorn.conf --preload
directory=/srv/<application>
autostart=true
autorestart=true
startretries=10
stderr_logfile = /var/log/supervisord/<application>-stderr.log
stdout_logfile = /var/log/supervisord/<application>-stdout.log
user=root
Gunicorn gunicorn.conf
bind = '0.0.0.0:5000'
backlog = 2048
workers = 3
worker_class = 'sync'
worker_connections = 1000
timeout = 30
keepalive = 2
accesslog='/var/log/gunicorn/gunicorn_access.log'
errorlog='/var/log/gunicorn/gunicorn_error.log'
pidfile = '/tmp/gunicorn.pid'
loglevel = 'debug'
Flask Application
run.py
from app import app
from app import views
if __name__ == '__main__':
app.run(host='0.0.0.0', debug=True)
view.py
from app import app, session
from flask import render_template, json, jsonify
import datetime
#app.route("/hello/")
def render_templates():
return render_template("display.html")
(... other code ..)
NB: I have an ELB in front of the flask application. 80 and 443 ports are open.
Input: https://example.com/hello/ Output: Redirected Loop
Any help will be appreciated.Thanks in advance.
I did figure out the issue.
The nginx configuration should have been
server {
listen 80;
server_name _;
access_log /var/log/nginx/nginx_access.log;
error_log /var/log/nginx/nginx_error.log;
location / {
proxy_pass http://127.0.0.1:5000;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
}
As ELB does an unloading of HTTPS encryption to HTTP request , my previous configuration was redirecting all my HTTP requests into HTTPS.