Reverse proxy for deploying Apache Superset
use airflow for data pipeline orchestration, for we need not only in-house dashboard but the one that any user can view from public domain, such as Flask app, the easiest way is to use reverse proxy, to mask upstream connections, put in modules conf(suprset.conf).
listening on cloud 18.162.249.250 (localhost) to port 8088.
$pyenv activate superset $ /home/ubuntu/.local/lib/python3.5/site-packages $ vim /home/ubuntu/.local/lib/python3.5/site-packages/superset_config.pyfrom superset.security import SupersetSecurityManager
from flask import redirect, g, flash, request, session
from flask_appbuilder._compat import as_unicode
from flask_appbuilder.security.views import AuthDBView, AuthRemoteUserView
from flask_appbuilder.security.views import expose
from flask_appbuilder.security.manager import BaseSecurityManager
from flask_appbuilder import base
from flask_login import login_user, logout_user
# Uncomment to setup Public role name, no authentication needed
AUTH_ROLE_PUBLIC = 'Public'
# Will allow user self registration
#AUTH_USER_REGISTRATION = False
# The default user self registration role
#AUTH_USER_REGISTRATION_ROLE = "Gamma"
from flask_appbuilder.security.manager import AUTH_DB, AUTH_LDAP, AUTH_REMOTE_USER
from superset.security import SupersetSecurityManager
from flask import redirect, g, flash, request, session
from flask_appbuilder._compat import as_unicode
from flask_appbuilder.security.views import AuthDBView, AuthRemoteUserView
from flask_appbuilder.security.views import expose
from flask_appbuilder.security.manager import BaseSecurityManager
from flask_appbuilder import base
from flask_login import login_user, logout_user
class RemoteUserMiddleware(object):
def __init__(self, app):
self.app = app
def __call__(self, environ, start_response):
user = environ.pop('HTTP_PROXY_REMOTE_USER', None)
environ['REMOTE_USER'] = user
return self.app(environ, start_response)
ADDITIONAL_MIDDLEWARE = [RemoteUserMiddleware, ]
class MiCustomRemoteUserView(AuthRemoteUserView):
# Leave blank
login_template = ''
@expose('/login/')
def login(self):
# headers
username = request.headers.get('HTTP_PROXY_REMOTE_USER')
if g.user is not None and g.user.is_authenticated():
return redirect(self.appbuilder.get_url_for_index)
sm = self.appbuilder.sm
session = sm.get_session
user = session.query(sm.user_model).filter_by(username=username).first()
if user is None and username:
msg = ("User not allowed, {}".format(username))
flash(as_unicode(msg), 'error')
return redirect(self.appbuilder.get_url_for_login)
if username:
user = self.appbuilder.sm.auth_user_remote_user(username)
if user is None:
flash(as_unicode(self.invalid_login_message), 'warning')
else:
login_user(user)
else:
flash(as_unicode(self.invalid_login_message), 'warning')
return redirect(self.appbuilder.get_url_for_index)
class MiCustomSecurityManager(SupersetSecurityManager):
authremoteuserview = MiCustomRemoteUserView
PUBLIC_ROLE_LIKE_GAMMA = True
ROW_LIMIT = 5000
SUPERSET_WORKERS = 4
# You will be serving site on port 8000 from gunicorn which sits in front of flask, and then send to nginx
SUPERSET_WEBSERVER_PORT = 8088
#---------------------------------------------------------
# Flask App Builder configuration
#---------------------------------------------------------
# Your App secret key
#SECRET_KEY = "\2\1thisismyscretkey\1\2\e\y\y\h"
# The SQLAlchemy connection string to your database backend
# Flask-WTF flag for CSRF
CSRF_ENABLED = True
WTF_CSRF_ENABLED = False
ENABLE_PROXY_FIX =True
ENABLE_CORS= True
#your db connection
SQLALCHEMY_DATABASE_URI = "mysql+pymysql://root:[email protected]:3306/binance?charset=utf8"
ACHE_DEFAULT_TIMEOUT = 86400
CACHE_CONFIG = {
'CACHE_TYPE': 'redis',
'CACHE_DEFAULT_TIMEOUT': 86400,
'CACHE_KEY_PREFIX': 'superset_',
'CACHE_REDIS_HOST': 'localhost',
'CACHE_REDIS_PORT': 6379,
'CACHE_REDIS_DB': 1,
'CACHE_REDIS_URL': 'redis://localhost:6379/1'
}$ sudo apt-get update
$ sudo apt-get upgrade$ sudo apt-get install redis-server$ vim /etc/redis/redis.conf maxmemory 128mb
maxmemory-policy allkeys-lru$ sudo systemctl restart redis-server.service
$ sudo systemctl enable redis-server.service $ htop$ redis-cli monitor$ redis-cli
flushall $ pip install gunicorn
$ gunicorn superset:app -b localhost:8000 &$ sudo apt-get install nginx$ sudo vim /etc/nginx/nginx.confuser www-data;
worker_processes auto;
pid /run/nginx.pid;
worker_rlimit_nofile 100480;
events {
worker_connections 20000;
# multi_accept on;
}
http {
# Basic Settings
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65;
types_hash_max_size 2048;
# server_tokens off;
# server_names_hash_bucket_size 64;
# server_name_in_redirect off;
include /etc/nginx/mime.types;
default_type application/octet-stream;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2; # Dropping SSLv3, ref: POODLE
ssl_prefer_server_ciphers on;
# Logging Settings
access_log /var/log/nginx/access.log;
error_log /var/log/nginx/error.log;
##
# Gzip Settings
##
gzip on;
gzip_disable "msie6";
# gzip_vary on;
# gzip_proxied any;
# gzip_comp_level 6;
# gzip_buffers 16 8k;
# gzip_http_version 1.1;
# gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript;
##
# Virtual Host Configs
##
#18.162.249.250
server {
server_name localhost;
listen 8088;
location / {
proxy_pass http://127.0.0.1:8088;
proxy_set_header HTTP_PROXY_REMOTE_USER $1;
proxy_set_header Host $host:8088;
proxy_set_header X-Real-IP $remote_addr;
# proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
}
include /etc/nginx/conf.d/*.conf;
include /etc/nginx/sites-enabled/*;
}$sudo vim /etc/nginx/sites-available/suprset.confserver {
listen 80;
server_name 18.162.249.250;
large_client_header_buffers 4 16k;
location / {
proxy_buffers 16 4k;
proxy_buffer_size 2k;
proxy_pass http://127.0.0.1:8000;
}
}
$ sudo ln -s /etc/nginx/sites-available/superset.conf /etc/nginx/sites-enabled$ sudo nginx -t
$ sudo nginx -s reload nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful$ sudo systemctl status nginx nginx.service - A high performance web server and a reverse proxy server
Loaded: loaded (/lib/systemd/system/nginx.service; enabled; vendor preset: enabled)
Active: active (running) since Wed 2019-11-06 02:48:06 UTC; 6h ago
Process: 7566 ExecStop=/sbin/start-stop-daemon --quiet --stop --retry QUIT/5 --pidfile /run/nginx.pid (code=exited, status=0/SUCCESS)
Process: 7053 ExecReload=/usr/sbin/nginx -g daemon on; master_process on; -s reload (code=exited, status=0/SUCCESS)
Process: 7608 ExecStart=/usr/sbin/nginx -g daemon on; master_process on; (code=exited, status=0/SUCCESS)
Process: 7604 ExecStartPre=/usr/sbin/nginx -t -q -g daemon on; master_process on; (code=exited, status=0/SUCCESS)
Main PID: 7610 (nginx)
Tasks: 17
Memory: 170.2M
CPU: 19.899s
CGroup: /system.slice/nginx.service
├─7610 nginx: master process /usr/sbin/nginx -g daemon on; master_process on
├─7611 nginx: worker process
├─7612 nginx: worker process
├─7613 nginx: worker process
├─7614 nginx: worker process
├─7615 nginx: worker process
├─7616 nginx: worker process
├─7617 nginx: worker process
├─7618 nginx: worker process
├─7619 nginx: worker process
├─7622 nginx: worker process
├─7623 nginx: worker process
├─7624 nginx: worker process
├─7625 nginx: worker process
├─7626 nginx: worker process
├─7627 nginx: worker process
└─7628 nginx: worker process
Nov 06 02:48:06 ip-172-31-9-152 systemd[1]: Starting A high performance web server and a reverse proxy server...
Nov 06 02:48:06 ip-172-31-9-152 systemd[1]: Started A high performance web server and a reverse proxy server.the testing dashboard web page like this can be visited on http://18.162.249.250/superset/dashboard/10/

Reference: