Commit 384e88d2 authored by Ziirish's avatar Ziirish

fix: werkzeug >= 0.15.0 compatibility (fix #303)

parent ec6e305f
......@@ -7,6 +7,7 @@ Current
- **BREAKING**: the *single* and *version* options within the ``[Global]`` section have been removed in favor of a new unified *backend* option
- **BREAKING**: a change introduced by `#284 <https://git.ziirish.me/ziirish/burp-ui/issues/284>`_ may return wrong timestamps for backups made with burp-server <= 2.1.10 if your current burp-server is >= 2.1.10
- **BREAKING**: the authentication backends section have been renamed with the ``:AUTH`` suffix
- **BREAKING**: the ``prefix`` option has been moved from the ``[Global]`` configuration section to the ``[Production]`` one
- Add: new `audit logging <https://git.ziirish.me/ziirish/burp-ui/issues/260>`_ system
- Add: new ``bui-monitor`` processes pool + ``async`` backend to parallelize some requests `#278 <https://git.ziirish.me/ziirish/burp-ui/issues/278>`_
- Add: new `listen` and `listen_status` options in burp-2.2.10 `#279 <https://git.ziirish.me/ziirish/burp-ui/issues/279>`_
......
......@@ -10,6 +10,7 @@ jQuery/Bootstrap
.. moduleauthor:: Ziirish <hi+burpui@ziirish.me>
"""
import os
import json
import time
import logging
......@@ -148,9 +149,14 @@ def create_app(conf=None, verbose=0, logfile=None, **kwargs):
# Manage reverse_proxy special tricks & improvements
if reverse_proxy: # pragma: no cover
from werkzeug.contrib.fixers import ProxyFix
from werkzeug.middleware.proxy_fix import ProxyFix
app.wsgi_app = ProxyFix(app.wsgi_app)
kwargs = {}
if app.config['NUM_PROXIES'] > 0:
kwargs = app.config['PROXY_FIX_ARGS'].format(num_proxies=app.config['NUM_PROXIES'])
kwargs = json.loads(kwargs)
logger.debug(f"Using {kwargs} as ProxyFix parameters")
app = ProxyFix(app, **kwargs)
if app.storage and app.storage.lower() == 'redis':
try:
......@@ -373,10 +379,10 @@ def create_app(conf=None, verbose=0, logfile=None, **kwargs):
g.date_format = session.get('dateFormat', 'llll')
# make sure to store secure cookie if required
if app.config['BUI_SCOOKIE']:
criteria = [
criteria = (
request.is_secure,
request.headers.get('X-Forwarded-Proto', 'http') == 'https'
]
)
app.config['SESSION_COOKIE_SECURE'] = \
app.config['REMEMBER_COOKIE_SECURE'] = any(criteria)
if '_extra' in request.args:
......
......@@ -11,6 +11,7 @@ import os
import re
import sys
import logging # noqa
import warnings
from ..tools.logging import logger
from ..misc.auth.handler import UserAuthHandler
......@@ -25,8 +26,8 @@ from flask import Flask
BUI_DEFAULTS = {
'Global': {
'port': 5000,
'bind': '::',
'port': 0,
'bind': '',
'ssl': False,
'sslcert': '',
'sslkey': '',
......@@ -64,6 +65,8 @@ BUI_DEFAULTS = {
'database': '',
'limiter': False,
'ratio': '60/minute',
'num_proxies': 0,
'proxy_fix_args': "{'x_for': {num_proxies}, 'x_host': {num_proxies}, 'x_prefix': {num_proxies}}",
},
'WebSocket': {
'enabled': True,
......@@ -137,40 +140,41 @@ class BUIServer(Flask):
self.conf.parse(conf, True, BUI_DEFAULTS)
self.conf.default_section('Global')
self.config['BUI_PORT'] = self.conf.safe_get(
'port',
'integer'
)
self.demo = self.config['BUI_DEMO'] = self.conf.safe_get(
'demo',
'boolean'
)
self.config['BUI_BIND'] = self.conf.safe_get('bind')
self.config['BUI_PORT'] = self.conf.safe_get('port', 'integer')
if self.config['BUI_BIND'] or self.config['BUI_PORT']:
warnings.warn(
"The 'bind' and 'port' configuration options are now deprecated and "
"have no effect on burp-ui anymore unless you use the 'burp-ui-legacy' "
"command.\n"
"Please use the '-h' and '-p' command line flags instead.",
UserWarning
)
self.demo = self.config['BUI_DEMO'] = self.conf.safe_get('demo', 'boolean')
self.config['BUI_DSN'] = self.conf.safe_get('dsn')
self.config['BUI_PIWIK_URL'] = self.conf.safe_get('piwik_url')
self.config['BUI_PIWIK_SCRIPT'] = self.conf.safe_get('piwik_script')
self.config['BUI_PIWIK_ID'] = self.conf.safe_get('piwik_id', 'integer')
self.config['BUI_BIND'] = self.conf.safe_get('bind')
self.config['BACKEND'] = self.conf.safe_get('backend')
# FIXME: this sucks, we need to test the burp2 backend as well!
if unittest:
self.config['BACKEND'] = 'burp1'
self.config['BUI_SSL'] = self.conf.safe_get(
'ssl',
'boolean'
)
self.config['STANDALONE'] = self.config['BACKEND'] != 'multi'
self.config['BUI_SSLCERT'] = self.conf.safe_get(
'sslcert'
)
self.config['BUI_SSLKEY'] = self.conf.safe_get(
'sslkey'
)
prefix = self.config['BUI_PREFIX'] = self.conf.safe_get(
'prefix'
)
if prefix and not prefix.startswith('/'):
if prefix.lower() != 'none':
self.logger.warning("'prefix' must start with a '/'!")
self.config['BUI_PREFIX'] = ''
self.config['BUI_SSL'] = self.conf.safe_get('ssl', 'boolean')
self.config['BUI_SSLCERT'] = self.conf.safe_get('sslcert')
self.config['BUI_SSLKEY'] = self.conf.safe_get('sslkey')
if self.config['BUI_SSL'] or self.config['BUI_SSLCERT'] or \
self.config['BUI_SSLKEY']:
warnings.warn(
"The 'ssl', 'sslcert' and 'sslkey' configuration options are deprecated "
"as of v0.4.0. It means they have no effect on burp-ui anymore. "
"If you really need them, consider using the 'burp-ui-legacy' command "
"instead.",
UserWarning
)
# TODO: remove in 0.8.0
old_prefix = self.conf.safe_get('prefix')
self.plugins = self.config['BUI_PLUGINS'] = self.conf.safe_get(
'plugins',
......@@ -274,6 +278,33 @@ class BUIServer(Flask):
else:
self.config['WITH_CELERY'] = self.use_celery and \
self.use_celery.lower() != 'none'
self.config['NUM_PROXIES'] = self.conf.safe_get(
'num_proxies',
'integer',
section='Production'
)
self.config['PROXY_FIX_ARGS'] = self.conf.safe_get(
'proxy_fix_args',
section='Production'
)
prefix = self.conf.safe_get(
'prefix',
section='Production'
)
if not prefix and old_prefix:
# TODO: remove in a later version
prefix = old_prefix
warnings.warn(
"The 'prefix' option has been moved from the '[Global]' section to the "
"'[Production]' section",
UserWarning
)
if prefix and not prefix.startswith('/'):
if prefix.lower() != 'none':
self.logger.warning("'prefix' must start with a '/'!")
self.config['BUI_PREFIX'] = ''
elif prefix:
self.config['BUI_PREFIX'] = prefix
# WebSocket options
self.ws_enabled = self.config['WS_ENABLED'] = self.conf.safe_get(
......
......@@ -55,12 +55,6 @@ The `burpui.cfg`_ configuration file contains a ``[Global]`` section as follow:
# list the misc/audit directory to see the available backends
# default is no audit log
audit = basic
# You can change the prefix if you are behind a reverse-proxy under a custom
# root path. For example: /burpui
# You can also configure your reverse-proxy to announce the prefix through the
# 'X-Script-Name' header. In this case, the bellow prefix will be ignored in
# favour of the one announced by your reverse-proxy
prefix = none
# list of paths to look for external plugins
plugins = none
......@@ -78,8 +72,6 @@ Each option is commented, but here is a more detailed documentation:
- *auth*: What `Authentication`_ backend to use.
- *acl*: What `ACL`_ module to use.
- *audit*: What `Audit`_ module to use.
- *prefix*: You can host `Burp-UI`_ behind a sub-root path. See the `gunicorn
<gunicorn.html#sub-root-path>`__ page for details.
- *plugins*: Specify a list of paths to look for external plugins. See the
`Plugins <plugins.html>`_ page for details on how to write plugins.
......@@ -161,6 +153,30 @@ follow:
# limiter ratio
# see https://flask-limiter.readthedocs.io/en/stable/#ratelimit-string
ratio = 60/minute
# you can change the prefix if you are behind a reverse-proxy under a custom
# root path. For example: /burpui
# You can also configure your reverse-proxy to announce the prefix through the
# 'X-Script-Name' header. In this case, the bellow prefix will be ignored in
# favour of the one announced by your reverse-proxy
prefix = none
# ProxyFix
# number of reverse-proxy to trust in order to retrieve some HTTP headers
# All the details can be found here:
# https://werkzeug.palletsprojects.com/en/0.15.x/middleware/proxy_fix/#module-werkzeug.middleware.proxy_fix
num_proxies = 0
# alternatively, you can specify your own ProxyFix args.
# The default is: "{'x_for': {num_proxies}, 'x_host': {num_proxies}, 'x_prefix': {num_proxies}}"
# if num_proxies > 0, else it defaults to ProxyFix defaults
proxy_fix_args = "{'x_for': {num_proxies}, 'x_host': {num_proxies}, 'x_prefix': {num_proxies}}"
- *prefix*: You can host `Burp-UI`_ behind a sub-root path. See the `gunicorn
<gunicorn.html#sub-root-path>`__ page for details.
- *num_proxies*: This is useful only if you host `Burp-UI`_ behind a
`reverse-proxy <gunicorn.html#reverse-proxy>`__.
- *proxy_fix_args*: Same as above. Please refer to `Werkzeug's documentation
<https://werkzeug.palletsprojects.com/en/0.15.x/middleware/proxy_fix/#module-werkzeug.middleware.proxy_fix>`_
for details.
WebSocket
......
......@@ -257,10 +257,10 @@ Sub-root path
You can host `Burp-UI`_ behind a sub-root path. For instance ``/burpui``.
To accomplish this, you can either setup your reverse-proxy to announce the
desired *prefix*, or you can use the ``prefix`` option in your `Burp-UI`_
configuration file (see `usage <advanced_usage.html>`_ for details).
configuration file (see `usage <advanced_usage.html#production>`_ for details).
If you want to configure this reverse-proxy side, you need to announce the HTTP
Header ``X-Script-Name``.
Header ``X-Script-Name``. Alternatively, you can use the ``X_Forwarded_Prefix``.
Here is a sample configuration for Nginx:
......@@ -280,6 +280,7 @@ Here is a sample configuration for Nginx:
proxy_set_header Host $http_host;
proxy_set_header X-Forwarded-For $remote_addr;
# Our service is hosted behind the "/burpui" prefix
# Alternatively you can use the "X_FORWARDED_PREFIX" instead
proxy_set_header X-Script-Name /burpui;
proxy_read_timeout 300;
......
......@@ -36,6 +36,9 @@ v0.7.0
and the burp-client used by burp-ui must be able to reach the burp-server).
A new timeout has been added though in order for ``bui-agent`` to wait for the
burp-server to be ready.
- **Breaking** - the ``prefix`` option has been moved from the ``[Global]``
configuration section to the ``[Production]`` one for consistency with the new
*Production* options introduced.
v0.6.0
------
......
......@@ -14,3 +14,4 @@ pyOpenSSL==19.0.0
configobj==5.0.6
async_generator
Click==7.0
werkzeug>=0.15.0
......@@ -24,12 +24,6 @@ acl = basic
# list the misc/audit directory to see the available backends
# default is no audit log
audit = basic
# you can change the prefix if you are behind a reverse-proxy under a custom
# root path. For example: /burpui
# You can also configure your reverse-proxy to announce the prefix through the
# 'X-Script-Name' header. In this case, the bellow prefix will be ignored in
# favour of the one announced by your reverse-proxy
prefix = none
# list of paths to look for external plugins
plugins = none
......@@ -88,6 +82,21 @@ limiter = false
# limiter ratio
# see https://flask-limiter.readthedocs.io/en/stable/#ratelimit-string
ratio = 60/minute
# you can change the prefix if you are behind a reverse-proxy under a custom
# root path. For example: /burpui
# You can also configure your reverse-proxy to announce the prefix through the
# 'X-Script-Name' header. In this case, the bellow prefix will be ignored in
# favour of the one announced by your reverse-proxy
prefix = none
# ProxyFix
# number of reverse-proxy to trust in order to retrieve some HTTP headers
# All the details can be found here:
# https://werkzeug.palletsprojects.com/en/0.15.x/middleware/proxy_fix/#module-werkzeug.middleware.proxy_fix
num_proxies = 0
# alternatively, you can specify your own ProxyFix args.
# The default is: "{'x_for': {num_proxies}, 'x_host': {num_proxies}, 'x_prefix': {num_proxies}}"
# if num_proxies > 0, else it defaults to ProxyFix defaults
proxy_fix_args = "{'x_for': {num_proxies}, 'x_host': {num_proxies}, 'x_prefix': {num_proxies}}"
[WebSocket]
## This section contains WebSocket server specific options.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment