Merge "django2: adopt New-style middleware"

This commit is contained in:
Zuul 2018-03-09 16:49:28 +00:00 committed by Gerrit Code Review
commit ab7e989d40
12 changed files with 101 additions and 35 deletions

View File

@ -43,6 +43,15 @@ class HorizonMiddleware(object):
logout_reason = None logout_reason = None
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
self.process_request(request)
response = self.get_response(request)
response = self.process_response(request, response)
return response
def process_request(self, request): def process_request(self, request):
"""Adds data necessary for Horizon to function to the request.""" """Adds data necessary for Horizon to function to the request."""

View File

@ -52,10 +52,12 @@ class OperationLogMiddleware(object):
# In order to allow to access from mock in test cases. # In order to allow to access from mock in test cases.
return self._logger return self._logger
def __init__(self): def __init__(self, get_response):
if not getattr(settings, "OPERATION_LOG_ENABLED", False): if not getattr(settings, "OPERATION_LOG_ENABLED", False):
raise MiddlewareNotUsed raise MiddlewareNotUsed
self.get_response = get_response
# set configurations # set configurations
_log_option = getattr(settings, "OPERATION_LOG_OPTIONS", {}) _log_option = getattr(settings, "OPERATION_LOG_OPTIONS", {})
_available_methods = ['POST', 'GET', 'PUT', 'DELETE'] _available_methods = ['POST', 'GET', 'PUT', 'DELETE']
@ -77,6 +79,11 @@ class OperationLogMiddleware(object):
ignored_urls = _log_option.get("ignore_urls", _default_ignored_urls) ignored_urls = _log_option.get("ignore_urls", _default_ignored_urls)
self._ignored_urls = [re.compile(url) for url in ignored_urls] self._ignored_urls = [re.compile(url) for url in ignored_urls]
def __call__(self, request):
response = self.get_response(request)
response = self.process_response(request, response)
return response
def process_response(self, request, response): def process_response(self, request, response):
"""Log user operation.""" """Log user operation."""
log_format = self._get_log_format(request) log_format = self._get_log_format(request)

View File

@ -141,8 +141,12 @@ class TestCase(django_test.TestCase):
self._setup_factory() self._setup_factory()
self._setup_user() self._setup_user()
self._setup_request() self._setup_request()
middleware.HorizonMiddleware().process_request(self.request) # A dummy get_response function (which is not callable) is passed
AuthenticationMiddleware().process_request(self.request) # because middlewares below are used only to populate request attrs.
middleware.HorizonMiddleware('dummy_get_response') \
.process_request(self.request)
AuthenticationMiddleware('dummy_get_response') \
.process_request(self.request)
os.environ["HORIZON_TEST_RUN"] = "True" os.environ["HORIZON_TEST_RUN"] = "True"
def _setup_test_data(self): def _setup_test_data(self):

View File

@ -62,7 +62,7 @@ INSTALLED_APPS = (
'openstack_auth' 'openstack_auth'
) )
MIDDLEWARE_CLASSES = ( MIDDLEWARE = (
'django.middleware.common.CommonMiddleware', 'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware', 'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware', 'django.contrib.sessions.middleware.SessionMiddleware',

View File

@ -13,9 +13,11 @@
# License for the specific language governing permissions and limitations # License for the specific language governing permissions and limitations
# under the License. # under the License.
import django import mock
from django.conf import settings from django.conf import settings
from django.http import HttpResponseRedirect from django.http import HttpResponseRedirect
from django import test as django_test
from django.utils import timezone from django.utils import timezone
from horizon import exceptions from horizon import exceptions
@ -23,32 +25,32 @@ from horizon import middleware
from horizon.test import helpers as test from horizon.test import helpers as test
class MiddlewareTests(test.TestCase): class MiddlewareTests(django_test.TestCase):
def setUp(self): def setUp(self):
self._timezone_backup = timezone.get_current_timezone_name() self._timezone_backup = timezone.get_current_timezone_name()
return super(MiddlewareTests, self).setUp() self.factory = test.RequestFactoryWithMessages()
self.get_response = mock.Mock()
super(MiddlewareTests, self).setUp()
def tearDown(self): def tearDown(self):
timezone.activate(self._timezone_backup) timezone.activate(self._timezone_backup)
return super(MiddlewareTests, self).tearDown() super(MiddlewareTests, self).tearDown()
def test_redirect_login_fail_to_login(self): def test_redirect_login_fail_to_login(self):
url = settings.LOGIN_URL url = settings.LOGIN_URL
request = self.factory.post(url) request = self.factory.post(url)
self.get_response.return_value = request
mw = middleware.HorizonMiddleware() mw = middleware.HorizonMiddleware(self.get_response)
resp = mw.process_exception(request, exceptions.NotAuthenticated()) resp = mw.process_exception(request, exceptions.NotAuthenticated())
resp.client = self.client resp.client = self.client
if django.VERSION >= (1, 9):
self.assertRedirects(resp, settings.TESTSERVER + url) self.assertRedirects(resp, settings.TESTSERVER + url)
else:
self.assertRedirects(resp, url)
def test_process_response_redirect_on_ajax_request(self): def test_process_response_redirect_on_ajax_request(self):
url = settings.LOGIN_URL url = settings.LOGIN_URL
mw = middleware.HorizonMiddleware() mw = middleware.HorizonMiddleware(self.get_response)
request = self.factory.post(url, request = self.factory.post(url,
HTTP_X_REQUESTED_WITH='XMLHttpRequest') HTTP_X_REQUESTED_WITH='XMLHttpRequest')
@ -65,7 +67,7 @@ class MiddlewareTests(test.TestCase):
def test_timezone_awareness(self): def test_timezone_awareness(self):
url = settings.LOGIN_REDIRECT_URL url = settings.LOGIN_REDIRECT_URL
mw = middleware.HorizonMiddleware() mw = middleware.HorizonMiddleware(self.get_response)
request = self.factory.get(url) request = self.factory.get(url)
request.session['django_timezone'] = 'America/Chicago' request.session['django_timezone'] = 'America/Chicago'

View File

@ -12,25 +12,34 @@
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the # WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations # License for the specific language governing permissions and limitations
# under the License. # under the License.
import mock
from mock import patch from mock import patch
from django.conf import settings from django.conf import settings
from django.core.exceptions import MiddlewareNotUsed from django.core.exceptions import MiddlewareNotUsed
from django.http import HttpResponseRedirect from django.http import HttpResponseRedirect
from django import test as django_test
from django.test.utils import override_settings from django.test.utils import override_settings
from horizon import middleware from horizon import middleware
from horizon.test import helpers as test from horizon.test import helpers as test
class OperationLogMiddlewareTest(test.TestCase): class OperationLogMiddlewareTest(django_test.TestCase):
http_host = u'test_host' http_host = u'test_host'
http_referer = u'/dashboard/test_http_referer' http_referer = u'/dashboard/test_http_referer'
def setUp(self):
super(OperationLogMiddlewareTest, self).setUp()
self.factory = test.RequestFactoryWithMessages()
def test_middleware_not_used(self): def test_middleware_not_used(self):
get_response = mock.Mock()
with self.assertRaises(MiddlewareNotUsed): with self.assertRaises(MiddlewareNotUsed):
middleware.OperationLogMiddleware() middleware.OperationLogMiddleware(get_response)
self.assertFalse(get_response.called)
def _test_ready_for_post(self): def _test_ready_for_post(self):
url = settings.LOGIN_URL url = settings.LOGIN_URL
@ -63,11 +72,13 @@ class OperationLogMiddlewareTest(test.TestCase):
@patch(('horizon.middleware.operation_log.OperationLogMiddleware.' @patch(('horizon.middleware.operation_log.OperationLogMiddleware.'
'OPERATION_LOG')) 'OPERATION_LOG'))
def test_process_response_for_post(self, mock_logger): def test_process_response_for_post(self, mock_logger):
olm = middleware.OperationLogMiddleware()
request, response = self._test_ready_for_post() request, response = self._test_ready_for_post()
get_response = mock.Mock(return_value=response)
olm = middleware.OperationLogMiddleware(get_response)
resp = olm.process_response(request, response) resp = olm(request)
get_response.assert_called_once_with(request)
self.assertTrue(mock_logger.info.called) self.assertTrue(mock_logger.info.called)
self.assertEqual(302, resp.status_code) self.assertEqual(302, resp.status_code)
log_args = mock_logger.info.call_args[0] log_args = mock_logger.info.call_args[0]
@ -86,11 +97,13 @@ class OperationLogMiddlewareTest(test.TestCase):
@patch(('horizon.middleware.operation_log.OperationLogMiddleware.' @patch(('horizon.middleware.operation_log.OperationLogMiddleware.'
'OPERATION_LOG')) 'OPERATION_LOG'))
def test_process_response_for_get(self, mock_logger): def test_process_response_for_get(self, mock_logger):
olm = middleware.OperationLogMiddleware()
request, response = self._test_ready_for_get() request, response = self._test_ready_for_get()
get_response = mock.Mock(return_value=response)
olm = middleware.OperationLogMiddleware(get_response)
resp = olm.process_response(request, response) resp = olm(request)
get_response.assert_called_once_with(request)
self.assertTrue(mock_logger.info.called) self.assertTrue(mock_logger.info.called)
self.assertEqual(302, resp.status_code) self.assertEqual(302, resp.status_code)
log_args = mock_logger.info.call_args[0] log_args = mock_logger.info.call_args[0]
@ -106,11 +119,13 @@ class OperationLogMiddlewareTest(test.TestCase):
'OPERATION_LOG')) 'OPERATION_LOG'))
def test_process_response_for_get_no_target(self, mock_logger): def test_process_response_for_get_no_target(self, mock_logger):
"""In default setting, Get method is not logged""" """In default setting, Get method is not logged"""
olm = middleware.OperationLogMiddleware()
request, response = self._test_ready_for_get() request, response = self._test_ready_for_get()
get_response = mock.Mock(return_value=response)
olm = middleware.OperationLogMiddleware(get_response)
resp = olm.process_response(request, response) resp = olm(request)
get_response.assert_called_once_with(request)
self.assertEqual(0, mock_logger.info.call_count) self.assertEqual(0, mock_logger.info.call_count)
self.assertEqual(302, resp.status_code) self.assertEqual(302, resp.status_code)
@ -118,12 +133,14 @@ class OperationLogMiddlewareTest(test.TestCase):
@patch(('horizon.middleware.operation_log.OperationLogMiddleware.' @patch(('horizon.middleware.operation_log.OperationLogMiddleware.'
'OPERATION_LOG')) 'OPERATION_LOG'))
def test_process_exception(self, mock_logger): def test_process_exception(self, mock_logger):
olm = middleware.OperationLogMiddleware()
request, response = self._test_ready_for_post() request, response = self._test_ready_for_post()
get_response = mock.Mock(return_value=response)
olm = middleware.OperationLogMiddleware(get_response)
exception = Exception("Unexpected error occurred.") exception = Exception("Unexpected error occurred.")
olm.process_exception(request, exception) olm.process_exception(request, exception)
self.assertFalse(get_response.called)
log_args = mock_logger.info.call_args[0] log_args = mock_logger.info.call_args[0]
logging_str = log_args[0] % log_args[1] logging_str = log_args[0] % log_args[1]
self.assertTrue(mock_logger.info.called) self.assertTrue(mock_logger.info.called)
@ -140,7 +157,8 @@ class OperationLogMiddlewareTest(test.TestCase):
@patch(('horizon.middleware.operation_log.OperationLogMiddleware.' @patch(('horizon.middleware.operation_log.OperationLogMiddleware.'
'OPERATION_LOG')) 'OPERATION_LOG'))
def test_get_log_format(self, mock_logger): def test_get_log_format(self, mock_logger):
olm = middleware.OperationLogMiddleware() get_response = mock.Mock()
olm = middleware.OperationLogMiddleware(get_response)
request, _ = self._test_ready_for_get() request, _ = self._test_ready_for_get()
self.assertEqual(olm._default_format, olm._get_log_format(request)) self.assertEqual(olm._default_format, olm._get_log_format(request))
@ -149,7 +167,8 @@ class OperationLogMiddlewareTest(test.TestCase):
@patch(('horizon.middleware.operation_log.OperationLogMiddleware.' @patch(('horizon.middleware.operation_log.OperationLogMiddleware.'
'OPERATION_LOG')) 'OPERATION_LOG'))
def test_get_log_format_no_user(self, mock_logger): def test_get_log_format_no_user(self, mock_logger):
olm = middleware.OperationLogMiddleware() get_response = mock.Mock()
olm = middleware.OperationLogMiddleware(get_response)
request, _ = self._test_ready_for_get() request, _ = self._test_ready_for_get()
delattr(request, "user") delattr(request, "user")
@ -159,7 +178,8 @@ class OperationLogMiddlewareTest(test.TestCase):
@patch(('horizon.middleware.operation_log.OperationLogMiddleware.' @patch(('horizon.middleware.operation_log.OperationLogMiddleware.'
'OPERATION_LOG')) 'OPERATION_LOG'))
def test_get_log_format_unknown_method(self, mock_logger): def test_get_log_format_unknown_method(self, mock_logger):
olm = middleware.OperationLogMiddleware() get_response = mock.Mock()
olm = middleware.OperationLogMiddleware(get_response)
request, _ = self._test_ready_for_get() request, _ = self._test_ready_for_get()
request.method = "FAKE" request.method = "FAKE"
@ -169,7 +189,8 @@ class OperationLogMiddlewareTest(test.TestCase):
@patch(('horizon.middleware.operation_log.OperationLogMiddleware.' @patch(('horizon.middleware.operation_log.OperationLogMiddleware.'
'OPERATION_LOG')) 'OPERATION_LOG'))
def test_get_log_format_ignored_url(self, mock_logger): def test_get_log_format_ignored_url(self, mock_logger):
olm = middleware.OperationLogMiddleware() get_response = mock.Mock()
olm = middleware.OperationLogMiddleware(get_response)
request, _ = self._test_ready_for_get("/api/policy") request, _ = self._test_ready_for_get("/api/policy")
self.assertIsNone(olm._get_log_format(request)) self.assertIsNone(olm._get_log_format(request))

View File

@ -335,7 +335,7 @@ class TabExceptionTests(test.TestCase):
TabWithTableView.tab_group_class.tabs.append(RedirectExceptionTab) TabWithTableView.tab_group_class.tabs.append(RedirectExceptionTab)
view = TabWithTableView.as_view() view = TabWithTableView.as_view()
req = self.factory.get("/") req = self.factory.get("/")
mw = middleware.HorizonMiddleware() mw = middleware.HorizonMiddleware('dummy_get_response')
try: try:
resp = view(req) resp = view(req)
except Exception as e: except Exception as e:

View File

@ -34,7 +34,8 @@ class MessageTests(test.TestCase):
messages.error(req, string) messages.error(req, string)
self.assertItemsEqual(req.horizon['async_messages'], [expected]) self.assertItemsEqual(req.horizon['async_messages'], [expected])
res = http.HttpResponse() res = http.HttpResponse()
res = middleware.HorizonMiddleware().process_response(req, res) res = middleware.HorizonMiddleware('dummy_get_response') \
.process_response(req, res)
self.assertEqual(json.dumps([expected]), self.assertEqual(json.dumps([expected]),
res['X-Horizon-Messages']) res['X-Horizon-Messages'])
@ -48,6 +49,7 @@ class MessageTests(test.TestCase):
messages.error(req, string) messages.error(req, string)
self.assertItemsEqual(req.horizon['async_messages'], [expected]) self.assertItemsEqual(req.horizon['async_messages'], [expected])
res = http.HttpResponse() res = http.HttpResponse()
res = middleware.HorizonMiddleware().process_response(req, res) res = middleware.HorizonMiddleware('dummy_get_response') \
.process_response(req, res)
self.assertEqual(json.dumps([expected]), self.assertEqual(json.dumps([expected]),
res['X-Horizon-Messages']) res['X-Horizon-Messages'])

View File

@ -99,6 +99,15 @@ class ThemeMiddleware(object):
the Cookie's theme value for use later in the Django chain. the Cookie's theme value for use later in the Django chain.
""" """
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
self.process_request(request)
response = self.get_response(request)
response = self.process_response(request, response)
return response
def process_request(self, request): def process_request(self, request):
# Determine which theme the user has configured and store in local # Determine which theme the user has configured and store in local

View File

@ -27,7 +27,7 @@ INSTALLED_APPS = [
'openstack_auth.tests' 'openstack_auth.tests'
] ]
MIDDLEWARE_CLASSES = [ MIDDLEWARE = [
'django.middleware.common.CommonMiddleware', 'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware', 'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware', 'django.contrib.sessions.middleware.SessionMiddleware',

View File

@ -39,10 +39,16 @@ class ProfilerClientMiddleware(object):
('HTTP_X_TRACE_HMAC', 'X-Trace-HMAC') ('HTTP_X_TRACE_HMAC', 'X-Trace-HMAC')
] ]
def __init__(self): def __init__(self, get_response):
if not PROFILER_ENABLED: if not PROFILER_ENABLED:
raise exceptions.MiddlewareNotUsed() raise exceptions.MiddlewareNotUsed()
super(ProfilerClientMiddleware, self).__init__() super(ProfilerClientMiddleware, self).__init__()
self.get_response = get_response
def __call__(self, request):
self.process_request(request)
response = self.get_response(request)
return response
def is_async_profiling(self, request): def is_async_profiling(self, request):
return self.profiler_headers[0][0] in request.META return self.profiler_headers[0][0] in request.META
@ -62,14 +68,20 @@ class ProfilerClientMiddleware(object):
class ProfilerMiddleware(object): class ProfilerMiddleware(object):
def __init__(self): def __init__(self, get_response):
self.name = PROFILER_CONF.get('facility_name', 'horizon') self.name = PROFILER_CONF.get('facility_name', 'horizon')
self.hmac_keys = PROFILER_CONF.get('keys', []) self.hmac_keys = PROFILER_CONF.get('keys', [])
self.get_response = get_response
if PROFILER_ENABLED: if PROFILER_ENABLED:
api.init_notifier(PROFILER_CONF.get('notifier_connection_string')) api.init_notifier(PROFILER_CONF.get('notifier_connection_string'))
else: else:
raise exceptions.MiddlewareNotUsed() raise exceptions.MiddlewareNotUsed()
def __call__(self, request):
response = self.get_response(request)
response = self.process_response(request, response)
return response
@staticmethod @staticmethod
def is_authenticated(request): def is_authenticated(request):
return hasattr(request, "user") and request.user.is_authenticated return hasattr(request, "user") and request.user.is_authenticated

View File

@ -107,7 +107,7 @@ OPENSTACK_IMAGE_BACKEND = {
] ]
} }
MIDDLEWARE_CLASSES = ( MIDDLEWARE = (
'django.middleware.common.CommonMiddleware', 'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware', 'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware', 'django.contrib.sessions.middleware.SessionMiddleware',