summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJenkins <jenkins@review.openstack.org>2016-05-06 18:20:50 +0000
committerGerrit Code Review <review@openstack.org>2016-05-06 18:20:50 +0000
commitced6c32e0a331dbd32f73642d3a7d8dea7c3256f (patch)
tree325b765f157bb8f095db2dea375f1c310f7d8af6
parent86c0309ecea4db489b2eff0e15d259d8ebe58e82 (diff)
parent38dfe3d907c35dad82514005f9075c0fb1f57a2e (diff)
downloadhorizon-stable/kilo.tar.gz
Merge "Logout user if he has no valid tokens" into stable/kilokilo-eol2015.1.4stable/kilo
-rw-r--r--horizon/exceptions.py7
-rw-r--r--horizon/middleware.py6
-rw-r--r--openstack_dashboard/dashboards/project/instances/tests.py13
-rw-r--r--openstack_dashboard/dashboards/project/overview/tests.py62
4 files changed, 65 insertions, 23 deletions
diff --git a/horizon/exceptions.py b/horizon/exceptions.py
index f6ec76505..ea2c8017c 100644
--- a/horizon/exceptions.py
+++ b/horizon/exceptions.py
@@ -203,6 +203,7 @@ class HandledException(HorizonException):
UNAUTHORIZED = tuple(HORIZON_CONFIG['exceptions']['unauthorized'])
+UNAUTHORIZED += (NotAuthorized,)
NOT_FOUND = tuple(HORIZON_CONFIG['exceptions']['not_found'])
RECOVERABLE = (AlreadyExists, Conflict, NotAvailable, ServiceCatalogException)
RECOVERABLE += tuple(HORIZON_CONFIG['exceptions']['recoverable'])
@@ -281,7 +282,8 @@ def handle_recoverable(request, message, redirect, ignore, escalate, handled,
HANDLE_EXC_METHODS = [
- {'exc': UNAUTHORIZED, 'handler': handle_unauthorized, 'set_wrap': False},
+ {'exc': UNAUTHORIZED, 'handler': handle_unauthorized,
+ 'set_wrap': False, 'escalate': True},
{'exc': NOT_FOUND, 'handler': handle_notfound, 'set_wrap': True},
{'exc': RECOVERABLE, 'handler': handle_recoverable, 'set_wrap': True},
]
@@ -351,7 +353,8 @@ def handle(request, message=None, redirect=None, ignore=False,
if exc_handler['set_wrap']:
wrap = True
handler = exc_handler['handler']
- ret = handler(request, message, redirect, ignore, escalate,
+ ret = handler(request, message, redirect, ignore,
+ exc_handler.get('escalate', escalate),
handled, force_silence, force_log,
log_method, log_entry, log_level)
if ret:
diff --git a/horizon/middleware.py b/horizon/middleware.py
index 885489e5c..d39f4da26 100644
--- a/horizon/middleware.py
+++ b/horizon/middleware.py
@@ -158,6 +158,12 @@ class HorizonMiddleware(object):
login_url = request.build_absolute_uri(auth_url)
response = redirect_to_login(next_url, login_url=login_url,
redirect_field_name=field_name)
+ if isinstance(exception, exceptions.NotAuthorized):
+ logout_reason = _("Unauthorized. Please try logging in again.")
+ utils.add_logout_reason(request, response, logout_reason)
+ # delete messages, created in get_data() method
+ # since we are going to redirect user to the login page
+ response.delete_cookie('messages')
if request.is_ajax():
response_401 = http.HttpResponse(status=401)
diff --git a/openstack_dashboard/dashboards/project/instances/tests.py b/openstack_dashboard/dashboards/project/instances/tests.py
index 478a7c09c..5d520c2f1 100644
--- a/openstack_dashboard/dashboards/project/instances/tests.py
+++ b/openstack_dashboard/dashboards/project/instances/tests.py
@@ -17,9 +17,11 @@
# under the License.
import json
+import logging
import sys
from django.conf import settings
+from django.contrib.auth import REDIRECT_FIELD_NAME # noqa
from django.core.urlresolvers import reverse
from django.forms import widgets
from django import http
@@ -886,9 +888,18 @@ class InstanceTests(helpers.TestCase):
url = reverse('horizon:project:instances:detail',
args=[server.id])
+
+ # Avoid the log message in the test
+ # when unauthorized exception will be logged
+ logging.disable(logging.ERROR)
res = self.client.get(url)
+ logging.disable(logging.NOTSET)
- self.assertRedirectsNoFollow(res, INDEX_URL)
+ self.assertEqual(302, res.status_code)
+ self.assertEqual(('Location', settings.TESTSERVER +
+ settings.LOGIN_URL + '?' +
+ REDIRECT_FIELD_NAME + '=' + url),
+ res._headers.get('location', None),)
def test_instance_details_flavor_not_found(self):
server = self.servers.first()
diff --git a/openstack_dashboard/dashboards/project/overview/tests.py b/openstack_dashboard/dashboards/project/overview/tests.py
index d8db37321..8d91bea16 100644
--- a/openstack_dashboard/dashboards/project/overview/tests.py
+++ b/openstack_dashboard/dashboards/project/overview/tests.py
@@ -17,7 +17,10 @@
# under the License.
import datetime
+import logging
+from django.conf import settings
+from django.contrib.auth import REDIRECT_FIELD_NAME # noqa
from django.core.urlresolvers import reverse
from django import http
from django.utils import timezone
@@ -34,7 +37,8 @@ INDEX_URL = reverse('horizon:project:overview:index')
class UsageViewTests(test.TestCase):
- def _stub_nova_api_calls(self, nova_stu_enabled=True):
+ def _stub_nova_api_calls(self, nova_stu_enabled=True,
+ stu_exception=False):
self.mox.StubOutWithMock(api.nova, 'usage_get')
self.mox.StubOutWithMock(api.nova, 'tenant_absolute_limits')
self.mox.StubOutWithMock(api.nova, 'extension_supported')
@@ -42,6 +46,9 @@ class UsageViewTests(test.TestCase):
'SimpleTenantUsage', IsA(http.HttpRequest)) \
.AndReturn(nova_stu_enabled)
+ if nova_stu_enabled and stu_exception:
+ self._nova_stu_enabled(stu_exception)
+
def _stub_cinder_api_calls(self):
self.mox.StubOutWithMock(api.cinder, 'tenant_absolute_limits')
api.cinder.tenant_absolute_limits(IsA(http.HttpRequest)) \
@@ -64,6 +71,20 @@ class UsageViewTests(test.TestCase):
api.network.security_group_list(IsA(http.HttpRequest)) \
.AndReturn(self.q_secgroups.list())
+ def _nova_stu_enabled(self, exception=False):
+ now = timezone.now()
+ start = datetime.datetime(now.year, now.month, 1, 0, 0, 0, 0)
+ end = datetime.datetime(now.year, now.month, now.day, 23, 59, 59, 0)
+
+ if exception:
+ api.nova.usage_get(IsA(http.HttpRequest), self.tenant.id,
+ start, end) \
+ .AndRaise(exception)
+ else:
+ api.nova.usage_get(IsA(http.HttpRequest), self.tenant.id,
+ start, end) \
+ .AndReturn(api.nova.NovaUsage(self.usages.first()))
+
def test_usage(self):
self._test_usage(nova_stu_enabled=True)
@@ -150,32 +171,33 @@ class UsageViewTests(test.TestCase):
self.assertNotContains(res, 'form-inline')
self.assertEqual(usages.limits['maxTotalFloatingIps'], 10)
- def test_unauthorized(self):
- exc = self.exceptions.nova_unauthorized
- now = timezone.now()
- self._stub_nova_api_calls()
+ @test.create_stubs({api.nova: ('usage_get',
+ 'extension_supported')})
+ def _stub_nova_api_calls_unauthorized(self, exception):
api.nova.extension_supported(
'SimpleTenantUsage', IsA(http.HttpRequest)) \
.AndReturn(True)
- api.nova.usage_get(IsA(http.HttpRequest), self.tenant.id,
- datetime.datetime(now.year,
- now.month,
- 1, 0, 0, 0, 0),
- datetime.datetime(now.year,
- now.month,
- now.day, 23, 59, 59, 0)) \
- .AndRaise(exc)
- api.nova.tenant_absolute_limits(IsA(http.HttpRequest))\
- .AndReturn(self.limits['absolute'])
- self._stub_neutron_api_calls()
- self._stub_cinder_api_calls()
+ self._nova_stu_enabled(exception)
+
+ def test_unauthorized(self):
+ self._stub_nova_api_calls_unauthorized(
+ self.exceptions.nova_unauthorized)
self.mox.ReplayAll()
url = reverse('horizon:project:overview:index')
+
+ # Avoid the log message in the test
+ # when unauthorized exception will be logged
+ logging.disable(logging.ERROR)
res = self.client.get(url)
- self.assertTemplateUsed(res, 'project/overview/usage.html')
- self.assertMessageCount(res, error=1)
- self.assertContains(res, 'Unauthorized:')
+ logging.disable(logging.NOTSET)
+
+ self.assertEqual(302, res.status_code)
+ self.assertEqual((
+ 'Location', settings.TESTSERVER +
+ settings.LOGIN_URL + '?' +
+ REDIRECT_FIELD_NAME + '=' + url),
+ res._headers.get('location', None),)
def test_usage_csv(self):
self._test_usage_csv(nova_stu_enabled=True)