From b7537a8b8155fcf112067eb7d9d12339e280e44f Mon Sep 17 00:00:00 2001 From: Radomir Dopieralski Date: Mon, 28 Oct 2013 11:24:00 +0100 Subject: [PATCH] Use memoized_method decorator in views A lot of horizon's views use the pattern: def get_data(self): if not hasattr(self, "_data"): # Calculate data here. self._data = data return self._data This is copy-pasted all over the codebase. It's better to handle that with a single decorator. In the future, we might even replace it with some better caching approach. Closes-bug: #1248230 Change-Id: Id021fccf9032e5068993ec91a7774a5d0fbf29bb --- horizon/browsers/views.py | 17 +-- horizon/tables/base.py | 4 + horizon/tables/views.py | 2 + horizon/utils/memoized.py | 6 +- .../dashboards/admin/groups/views.py | 51 ++++----- .../dashboards/admin/instances/views.py | 33 +++--- .../dashboards/admin/networks/ports/views.py | 21 ++-- .../dashboards/admin/networks/views.py | 45 ++++---- .../dashboards/admin/projects/views.py | 20 ++-- .../dashboards/admin/roles/views.py | 19 ++-- .../dashboards/admin/users/views.py | 21 ++-- .../security_groups/views.py | 38 +++---- .../dashboards/project/containers/views.py | 49 ++++---- .../project/database_backups/views.py | 2 + .../dashboards/project/databases/views.py | 57 +++++----- .../databases/workflows/create_instance.py | 14 +-- .../dashboards/project/firewalls/views.py | 91 +++++++-------- .../images_and_snapshots/images/views.py | 36 +++--- .../images_and_snapshots/snapshots/views.py | 20 ++-- .../project/images_and_snapshots/views.py | 22 ++-- .../dashboards/project/instances/views.py | 107 +++++++++--------- .../dashboards/project/loadbalancers/views.py | 70 ++++++------ .../project/networks/ports/views.py | 20 ++-- .../project/networks/subnets/tables.py | 22 ++-- .../project/networks/subnets/views.py | 39 ++++--- .../dashboards/project/networks/views.py | 40 ++++--- .../routers/extensions/routerrules/views.py | 19 ++-- .../dashboards/project/routers/ports/views.py | 37 +++--- .../dashboards/project/routers/views.py | 43 ++++--- .../dashboards/project/stacks/views.py | 70 ++++++------ .../dashboards/project/volumes/views.py | 52 ++++----- .../dashboards/router/nexus1000v/views.py | 23 ++-- 32 files changed, 543 insertions(+), 567 deletions(-) diff --git a/horizon/browsers/views.py b/horizon/browsers/views.py index baf1d907af..84daa56957 100644 --- a/horizon/browsers/views.py +++ b/horizon/browsers/views.py @@ -17,6 +17,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon.tables import MultiTableView # noqa +from horizon.utils import memoized class ResourceBrowserView(MultiTableView): @@ -32,15 +33,15 @@ class ResourceBrowserView(MultiTableView): self.navigation_selection = False super(ResourceBrowserView, self).__init__(*args, **kwargs) + @memoized.memoized_method def get_browser(self): - if not hasattr(self, "browser"): - self.browser = self.browser_class(self.request, **self.kwargs) - self.browser.set_tables(self.get_tables()) - if not self.navigation_selection: - ct = self.browser.content_table - item = self.browser.navigable_item_name.lower() - ct._no_data_message = _("Select a %s to browse.") % item - return self.browser + browser = self.browser_class(self.request, **self.kwargs) + browser.set_tables(self.get_tables()) + if not self.navigation_selection: + ct = browser.content_table + item = browser.navigable_item_name.lower() + ct._no_data_message = _("Select a %s to browse.") % item + return browser def get_context_data(self, **kwargs): context = super(ResourceBrowserView, self).get_context_data(**kwargs) diff --git a/horizon/tables/base.py b/horizon/tables/base.py index 4063871ecc..3ccbd467bb 100644 --- a/horizon/tables/base.py +++ b/horizon/tables/base.py @@ -1074,6 +1074,10 @@ class DataTable(object): @property def filtered_data(self): + # This function should be using django.utils.functional.cached_property + # decorator, but unfortunately due to bug in Django + # https://code.djangoproject.com/ticket/19872 it would make it fail + # when being mocked by mox in tests. if not hasattr(self, '_filtered_data'): self._filtered_data = self.data if self._meta.filter and self._meta._filter_action: diff --git a/horizon/tables/views.py b/horizon/tables/views.py index 986cd6aa00..7760245db5 100644 --- a/horizon/tables/views.py +++ b/horizon/tables/views.py @@ -194,6 +194,8 @@ class DataTableView(MultiTableView): return self._tables def get_table(self): + # Note: this method cannot be easily memoized, because get_context_data + # uses its cached value directly. if not self.table_class: raise AttributeError('You must specify a DataTable class for the ' '"table_class" attribute on %s.' diff --git a/horizon/utils/memoized.py b/horizon/utils/memoized.py index f79b4a2c18..0959562051 100644 --- a/horizon/utils/memoized.py +++ b/horizon/utils/memoized.py @@ -98,5 +98,9 @@ def memoized(func): UnhashableKeyWarning, 2) value = func(*args, **kwargs) return value - return wrapped + +# We can use @memoized for methods now too, because it uses weakref and so +# it doesn't keep the instances in memory forever. We might want to separate +# them in the future, however. +memoized_method = memoized diff --git a/openstack_dashboard/dashboards/admin/groups/views.py b/openstack_dashboard/dashboards/admin/groups/views.py index dc821753cf..2062e668d3 100644 --- a/openstack_dashboard/dashboards/admin/groups/views.py +++ b/openstack_dashboard/dashboards/admin/groups/views.py @@ -21,6 +21,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tables +from horizon.utils import memoized from openstack_dashboard import api @@ -58,17 +59,16 @@ class UpdateView(forms.ModalFormView): template_name = constants.GROUPS_UPDATE_VIEW_TEMPLATE success_url = reverse_lazy(constants.GROUPS_INDEX_URL) + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - self._object = api.keystone.group_get(self.request, - self.kwargs['group_id']) - except Exception: - redirect = reverse(constants.GROUPS_INDEX_URL) - exceptions.handle(self.request, - _('Unable to update group.'), - redirect=redirect) - return self._object + try: + return api.keystone.group_get(self.request, + self.kwargs['group_id']) + except Exception: + redirect = reverse(constants.GROUPS_INDEX_URL) + exceptions.handle(self.request, + _('Unable to update group.'), + redirect=redirect) def get_context_data(self, **kwargs): context = super(UpdateView, self).get_context_data(**kwargs) @@ -83,29 +83,24 @@ class UpdateView(forms.ModalFormView): class GroupManageMixin(object): + @memoized.memoized_method def _get_group(self): - if not hasattr(self, "_group"): - group_id = self.kwargs['group_id'] - self._group = api.keystone.group_get(self.request, group_id) - return self._group + group_id = self.kwargs['group_id'] + return api.keystone.group_get(self.request, group_id) + @memoized.memoized_method def _get_group_members(self): - if not hasattr(self, "_group_members"): - group_id = self.kwargs['group_id'] - self._group_members = api.keystone.user_list(self.request, - group=group_id) - return self._group_members + group_id = self.kwargs['group_id'] + return api.keystone.user_list(self.request, group=group_id) + @memoized.memoized_method def _get_group_non_members(self): - if not hasattr(self, "_group_non_members"): - domain_id = self._get_group().domain_id - all_users = api.keystone.user_list(self.request, - domain=domain_id) - group_members = self._get_group_members() - group_member_ids = [user.id for user in group_members] - self._group_non_members = filter( - lambda u: u.id not in group_member_ids, all_users) - return self._group_non_members + domain_id = self._get_group().domain_id + all_users = api.keystone.user_list(self.request, + domain=domain_id) + group_members = self._get_group_members() + group_member_ids = [user.id for user in group_members] + return filter(lambda u: u.id not in group_member_ids, all_users) class ManageMembersView(GroupManageMixin, tables.DataTableView): diff --git a/openstack_dashboard/dashboards/admin/instances/views.py b/openstack_dashboard/dashboards/admin/instances/views.py index 33f8ad6d76..3b3712de2b 100644 --- a/openstack_dashboard/dashboards/admin/instances/views.py +++ b/openstack_dashboard/dashboards/admin/instances/views.py @@ -27,6 +27,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tables +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.dashboards.admin.instances \ @@ -126,26 +127,24 @@ class LiveMigrateView(forms.ModalFormView): context["instance_id"] = self.kwargs['instance_id'] return context + @memoized.memoized_method def get_hosts(self, *args, **kwargs): - if not hasattr(self, "_hosts"): - try: - self._hosts = api.nova.hypervisor_list(self.request) - except Exception: - redirect = reverse("horizon:admin:instances:index") - msg = _('Unable to retrieve hypervisor information.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._hosts + try: + return api.nova.hypervisor_list(self.request) + except Exception: + redirect = reverse("horizon:admin:instances:index") + msg = _('Unable to retrieve hypervisor information.') + exceptions.handle(self.request, msg, redirect=redirect) + @memoized.memoized_method def get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - instance_id = self.kwargs['instance_id'] - try: - self._object = api.nova.server_get(self.request, instance_id) - except Exception: - redirect = reverse("horizon:admin:instances:index") - msg = _('Unable to retrieve instance details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + instance_id = self.kwargs['instance_id'] + try: + return api.nova.server_get(self.request, instance_id) + except Exception: + redirect = reverse("horizon:admin:instances:index") + msg = _('Unable to retrieve instance details.') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): initial = super(LiveMigrateView, self).get_initial() diff --git a/openstack_dashboard/dashboards/admin/networks/ports/views.py b/openstack_dashboard/dashboards/admin/networks/ports/views.py index 0b6d85d439..8407c9b801 100644 --- a/openstack_dashboard/dashboards/admin/networks/ports/views.py +++ b/openstack_dashboard/dashboards/admin/networks/ports/views.py @@ -19,6 +19,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.dashboards.project.networks.ports \ @@ -38,18 +39,16 @@ class CreateView(forms.ModalFormView): return reverse(self.success_url, args=(self.kwargs['network_id'],)) + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - network_id = self.kwargs["network_id"] - self._object = api.neutron.network_get(self.request, - network_id) - except Exception: - redirect = reverse(self.failure_url, - args=(self.kwargs['network_id'],)) - msg = _("Unable to retrieve network.") - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + try: + network_id = self.kwargs["network_id"] + return api.neutron.network_get(self.request, network_id) + except Exception: + redirect = reverse(self.failure_url, + args=(self.kwargs['network_id'],)) + msg = _("Unable to retrieve network.") + exceptions.handle(self.request, msg, redirect=redirect) def get_context_data(self, **kwargs): context = super(CreateView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/admin/networks/views.py b/openstack_dashboard/dashboards/admin/networks/views.py index c31c4f66d0..faab7282fe 100644 --- a/openstack_dashboard/dashboards/admin/networks/views.py +++ b/openstack_dashboard/dashboards/admin/networks/views.py @@ -21,6 +21,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tables +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.dashboards.project.networks import views as user_views @@ -39,18 +40,17 @@ class IndexView(tables.DataTableView): table_class = networks_tables.NetworksTable template_name = 'admin/networks/index.html' + @memoized.memoized_method def _get_tenant_list(self): - if not hasattr(self, "_tenants"): - try: - tenants, has_more = api.keystone.tenant_list(self.request) - except Exception: - tenants = [] - msg = _('Unable to retrieve instance project information.') - exceptions.handle(self.request, msg) + try: + tenants, has_more = api.keystone.tenant_list(self.request) + except Exception: + tenants = [] + msg = _('Unable to retrieve instance project information.') + exceptions.handle(self.request, msg) - tenant_dict = SortedDict([(t.id, t) for t in tenants]) - self._tenants = tenant_dict - return self._tenants + tenant_dict = SortedDict([(t.id, t) for t in tenants]) + return tenant_dict def get_data(self): try: @@ -107,20 +107,19 @@ class DetailView(tables.MultiTableView): p.set_id_as_name_if_empty() return ports + @memoized.memoized_method def _get_data(self): - if not hasattr(self, "_network"): - try: - network_id = self.kwargs['network_id'] - network = api.neutron.network_get(self.request, network_id) - network.set_id_as_name_if_empty(length=0) - except Exception: - redirect = self.failure_url - exceptions.handle(self.request, - _('Unable to retrieve details for ' - 'network "%s".') % network_id, - redirect=redirect) - self._network = network - return self._network + try: + network_id = self.kwargs['network_id'] + network = api.neutron.network_get(self.request, network_id) + network.set_id_as_name_if_empty(length=0) + except Exception: + redirect = self.failure_url + exceptions.handle(self.request, + _('Unable to retrieve details for ' + 'network "%s".') % network_id, + redirect=redirect) + return network def get_context_data(self, **kwargs): context = super(DetailView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/admin/projects/views.py b/openstack_dashboard/dashboards/admin/projects/views.py index 5a45d42a97..714dd9b146 100644 --- a/openstack_dashboard/dashboards/admin/projects/views.py +++ b/openstack_dashboard/dashboards/admin/projects/views.py @@ -23,6 +23,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import tables +from horizon.utils import memoized from horizon import workflows from openstack_dashboard import api @@ -47,18 +48,15 @@ INDEX_URL = "horizon:admin:projects:index" class TenantContextMixin(object): + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - tenant_id = self.kwargs['tenant_id'] - try: - self._object = api.keystone.tenant_get(self.request, - tenant_id, - admin=True) - except Exception: - exceptions.handle(self.request, - _('Unable to retrieve project information.'), - redirect=reverse(INDEX_URL)) - return self._object + tenant_id = self.kwargs['tenant_id'] + try: + return api.keystone.tenant_get(self.request, tenant_id, admin=True) + except Exception: + exceptions.handle(self.request, + _('Unable to retrieve project information.'), + redirect=reverse(INDEX_URL)) def get_context_data(self, **kwargs): context = super(TenantContextMixin, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/admin/roles/views.py b/openstack_dashboard/dashboards/admin/roles/views.py index b0016c5e3f..f882b4ea56 100644 --- a/openstack_dashboard/dashboards/admin/roles/views.py +++ b/openstack_dashboard/dashboards/admin/roles/views.py @@ -21,6 +21,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tables +from horizon.utils import memoized from openstack_dashboard import api @@ -49,17 +50,15 @@ class UpdateView(forms.ModalFormView): template_name = 'admin/roles/update.html' success_url = reverse_lazy('horizon:admin:roles:index') + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - self._object = api.keystone.role_get(self.request, - self.kwargs['role_id']) - except Exception: - redirect = reverse("horizon:admin:roles:index") - exceptions.handle(self.request, - _('Unable to update role.'), - redirect=redirect) - return self._object + try: + return api.keystone.role_get(self.request, self.kwargs['role_id']) + except Exception: + redirect = reverse("horizon:admin:roles:index") + exceptions.handle(self.request, + _('Unable to update role.'), + redirect=redirect) def get_context_data(self, **kwargs): context = super(UpdateView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/admin/users/views.py b/openstack_dashboard/dashboards/admin/users/views.py index 13c3c446b2..d120fa9aed 100644 --- a/openstack_dashboard/dashboards/admin/users/views.py +++ b/openstack_dashboard/dashboards/admin/users/views.py @@ -29,6 +29,7 @@ from django.views.decorators.debug import sensitive_post_parameters # noqa from horizon import exceptions from horizon import forms from horizon import tables +from horizon.utils import memoized from openstack_dashboard import api @@ -64,18 +65,16 @@ class UpdateView(forms.ModalFormView): def dispatch(self, *args, **kwargs): return super(UpdateView, self).dispatch(*args, **kwargs) + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - self._object = api.keystone.user_get(self.request, - self.kwargs['user_id'], - admin=True) - except Exception: - redirect = reverse("horizon:admin:users:index") - exceptions.handle(self.request, - _('Unable to update user.'), - redirect=redirect) - return self._object + try: + return api.keystone.user_get(self.request, self.kwargs['user_id'], + admin=True) + except Exception: + redirect = reverse("horizon:admin:users:index") + exceptions.handle(self.request, + _('Unable to update user.'), + redirect=redirect) def get_context_data(self, **kwargs): context = super(UpdateView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/project/access_and_security/security_groups/views.py b/openstack_dashboard/dashboards/project/access_and_security/security_groups/views.py index a6be1dcff7..c07dbeb312 100644 --- a/openstack_dashboard/dashboards/project/access_and_security/security_groups/views.py +++ b/openstack_dashboard/dashboards/project/access_and_security/security_groups/views.py @@ -28,6 +28,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tables +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.utils import filters @@ -42,17 +43,16 @@ class DetailView(tables.DataTableView): table_class = project_tables.RulesTable template_name = 'project/access_and_security/security_groups/detail.html' + @memoized.memoized_method def _get_data(self): - if not hasattr(self, '_sg'): - sg_id = filters.get_int_or_uuid(self.kwargs['security_group_id']) - try: - self._sg = api.network.security_group_get(self.request, sg_id) - except Exception: - redirect = reverse('horizon:project:access_and_security:index') - exceptions.handle(self.request, - _('Unable to retrieve security group.'), - redirect=redirect) - return self._sg + sg_id = filters.get_int_or_uuid(self.kwargs['security_group_id']) + try: + return api.network.security_group_get(self.request, sg_id) + except Exception: + redirect = reverse('horizon:project:access_and_security:index') + exceptions.handle(self.request, + _('Unable to retrieve security group.'), + redirect=redirect) def get_data(self): return self._get_data().rules @@ -68,17 +68,15 @@ class UpdateView(forms.ModalFormView): template_name = 'project/access_and_security/security_groups/update.html' success_url = reverse_lazy('horizon:project:access_and_security:index') + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - sg_id = filters.get_int_or_uuid(self.kwargs['security_group_id']) - try: - self._object = api.network.security_group_get(self.request, - sg_id) - except Exception: - msg = _('Unable to retrieve security group.') - url = reverse('horizon:project:access_and_security:index') - exceptions.handle(self.request, msg, redirect=url) - return self._object + sg_id = filters.get_int_or_uuid(self.kwargs['security_group_id']) + try: + return api.network.security_group_get(self.request, sg_id) + except Exception: + msg = _('Unable to retrieve security group.') + url = reverse('horizon:project:access_and_security:index') + exceptions.handle(self.request, msg, redirect=url) def get_context_data(self, **kwargs): context = super(UpdateView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/project/containers/views.py b/openstack_dashboard/dashboards/project/containers/views.py index 06af0acb1e..3ad793a716 100644 --- a/openstack_dashboard/dashboards/project/containers/views.py +++ b/openstack_dashboard/dashboards/project/containers/views.py @@ -32,6 +32,7 @@ from django.views import generic from horizon import browsers from horizon import exceptions from horizon import forms +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.api import swift @@ -265,19 +266,18 @@ class CopyView(forms.ModalFormView): class ContainerDetailView(forms.ModalFormMixin, generic.TemplateView): template_name = 'project/containers/container_detail.html' + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - self._object = api.swift.swift_get_container( - self.request, - self.kwargs["container_name"], - with_data=False) - except Exception: - redirect = reverse("horizon:project:containers:index") - exceptions.handle(self.request, - _('Unable to retrieve details.'), - redirect=redirect) - return self._object + try: + return api.swift.swift_get_container( + self.request, + self.kwargs["container_name"], + with_data=False) + except Exception: + redirect = reverse("horizon:project:containers:index") + exceptions.handle(self.request, + _('Unable to retrieve details.'), + redirect=redirect) def get_context_data(self, **kwargs): context = super(ContainerDetailView, self).get_context_data(**kwargs) @@ -288,20 +288,19 @@ class ContainerDetailView(forms.ModalFormMixin, generic.TemplateView): class ObjectDetailView(forms.ModalFormMixin, generic.TemplateView): template_name = 'project/containers/object_detail.html' + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - self._object = api.swift.swift_get_object( - self.request, - self.kwargs["container_name"], - self.kwargs["object_path"], - with_data=False) - except Exception: - redirect = reverse("horizon:project:containers:index") - exceptions.handle(self.request, - _('Unable to retrieve details.'), - redirect=redirect) - return self._object + try: + return api.swift.swift_get_object( + self.request, + self.kwargs["container_name"], + self.kwargs["object_path"], + with_data=False) + except Exception: + redirect = reverse("horizon:project:containers:index") + exceptions.handle(self.request, + _('Unable to retrieve details.'), + redirect=redirect) def get_context_data(self, **kwargs): context = super(ObjectDetailView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/project/database_backups/views.py b/openstack_dashboard/dashboards/project/database_backups/views.py index 0fc66fcb34..0b5acf1533 100644 --- a/openstack_dashboard/dashboards/project/database_backups/views.py +++ b/openstack_dashboard/dashboards/project/database_backups/views.py @@ -38,6 +38,8 @@ class IndexView(horizon_tables.DataTableView): def _get_extra_data(self, backup): """Apply extra info to the backup.""" instance_id = backup.instance_id + # TODO(rdopieralski) It's not clear where this attribute is supposed + # to come from. At first glance it looks like it will always be {}. if not hasattr(self, '_instances'): self._instances = {} instance = self._instances.get(instance_id) diff --git a/openstack_dashboard/dashboards/project/databases/views.py b/openstack_dashboard/dashboards/project/databases/views.py index c2c2f48f87..d1d4fdd9d6 100644 --- a/openstack_dashboard/dashboards/project/databases/views.py +++ b/openstack_dashboard/dashboards/project/databases/views.py @@ -26,6 +26,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import tables as horizon_tables from horizon import tabs as horizon_tabs +from horizon.utils import memoized from horizon import workflows as horizon_workflows from openstack_dashboard import api @@ -44,17 +45,18 @@ class IndexView(horizon_tables.DataTableView): def has_more_data(self, table): return self._more + @memoized.memoized_method + def get_flavors(self): + try: + flavors = api.trove.flavor_list(self.request) + except Exception: + flavors = [] + msg = _('Unable to retrieve database size information.') + exceptions.handle(self.request, msg) + return SortedDict((unicode(flavor.id), flavor) for flavor in flavors) + def _extra_data(self, instance): - if not hasattr(self, '_flavors'): - try: - flavors = api.trove.flavor_list(self.request) - except Exception: - flavors = [] - msg = _('Unable to retrieve database size information.') - exceptions.handle(self.request, msg) - self._flavors = SortedDict([(unicode(flavor.id), flavor) - for flavor in flavors]) - flavor = self._flavors.get(instance.flavor["id"]) + flavor = self.get_flavors().get(instance.flavor["id"]) if flavor is not None: instance.full_flavor = flavor return instance @@ -95,25 +97,24 @@ class DetailView(horizon_tabs.TabbedTableView): context["instance"] = self.get_data() return context + @memoized.memoized_method def get_data(self): - if not hasattr(self, "_instance"): - try: - LOG.info("Obtaining instance for detailed view ") - instance_id = self.kwargs['instance_id'] - instance = api.trove.instance_get(self.request, instance_id) - except Exception: - redirect = reverse('horizon:project:databases:index') - msg = _('Unable to retrieve details ' - 'for database instance: %s') % instance_id - exceptions.handle(self.request, msg, redirect=redirect) - try: - instance.full_flavor = api.trove.flavor_get( - self.request, instance.flavor["id"]) - except Exception: - LOG.error('Unable to retrieve flavor details' - ' for database instance: %s') % instance_id - self._instance = instance - return self._instance + try: + LOG.info("Obtaining instance for detailed view ") + instance_id = self.kwargs['instance_id'] + instance = api.trove.instance_get(self.request, instance_id) + except Exception: + redirect = reverse('horizon:project:databases:index') + msg = _('Unable to retrieve details ' + 'for database instance: %s') % instance_id + exceptions.handle(self.request, msg, redirect=redirect) + try: + instance.full_flavor = api.trove.flavor_get( + self.request, instance.flavor["id"]) + except Exception: + LOG.error('Unable to retrieve flavor details' + ' for database instance: %s') % instance_id + return instance def get_tabs(self, request, *args, **kwargs): instance = self.get_data() diff --git a/openstack_dashboard/dashboards/project/databases/workflows/create_instance.py b/openstack_dashboard/dashboards/project/databases/workflows/create_instance.py index c8d8ba44c9..4af3ec820c 100644 --- a/openstack_dashboard/dashboards/project/databases/workflows/create_instance.py +++ b/openstack_dashboard/dashboards/project/databases/workflows/create_instance.py @@ -20,6 +20,7 @@ from django.conf import settings # noqa from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms +from horizon.utils import memoized from horizon import workflows from openstack_dashboard import api @@ -40,14 +41,13 @@ class SetInstanceDetailsAction(workflows.Action): name = _("Details") help_text_template = ("project/databases/_launch_details_help.html") + @memoized.memoized_method def flavors(self, request): - if not hasattr(self, '_flavors'): - try: - self._flavors = api.trove.flavor_list(request) - except Exception: - LOG.exception("Exception while obtaining flavors list") - self._flavors = [] - return self._flavors + try: + return api.trove.flavor_list(request) + except Exception: + LOG.exception("Exception while obtaining flavors list") + self._flavors = [] def populate_flavor_choices(self, request, context): flavor_list = [(f.id, "%s" % f.name) for f in self.flavors(request)] diff --git a/openstack_dashboard/dashboards/project/firewalls/views.py b/openstack_dashboard/dashboards/project/firewalls/views.py index dfad25bc65..93afa1c80c 100644 --- a/openstack_dashboard/dashboards/project/firewalls/views.py +++ b/openstack_dashboard/dashboards/project/firewalls/views.py @@ -24,6 +24,7 @@ from horizon import exceptions from horizon import forms from horizon import messages from horizon import tabs +from horizon.utils import memoized from horizon import workflows from openstack_dashboard import api @@ -131,17 +132,17 @@ class UpdateRuleView(forms.ModalFormView): context['name'] = obj.name return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - rule_id = self.kwargs['rule_id'] - try: - self._object = api.fwaas.rule_get(self.request, rule_id) - self._object.set_id_as_name_if_empty() - except Exception: - redirect = self.success_url - msg = _('Unable to retrieve rule details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + rule_id = self.kwargs['rule_id'] + try: + rule = api.fwaas.rule_get(self.request, rule_id) + rule.set_id_as_name_if_empty() + return rule + except Exception: + redirect = self.success_url + msg = _('Unable to retrieve rule details.') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): rule = self._get_object() @@ -163,17 +164,17 @@ class UpdatePolicyView(forms.ModalFormView): context['name'] = obj.name return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): policy_id = self.kwargs['policy_id'] try: - self._object = api.fwaas.policy_get(self.request, policy_id) - self._object.set_id_as_name_if_empty() + policy = api.fwaas.policy_get(self.request, policy_id) + policy.set_id_as_name_if_empty() + return policy except Exception: redirect = self.success_url msg = _('Unable to retrieve policy details.') exceptions.handle(self.request, msg, redirect=redirect) - return self._object def get_initial(self): policy = self._get_object() @@ -195,18 +196,18 @@ class UpdateFirewallView(forms.ModalFormView): context['name'] = obj.name return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - firewall_id = self.kwargs['firewall_id'] - try: - self._object = api.fwaas.firewall_get(self.request, - firewall_id) - self._object.set_id_as_name_if_empty() - except Exception: - redirect = self.success_url - msg = _('Unable to retrieve firewall details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + firewall_id = self.kwargs['firewall_id'] + try: + firewall = api.fwaas.firewall_get(self.request, + firewall_id) + firewall.set_id_as_name_if_empty() + return firewall + except Exception: + redirect = self.success_url + msg = _('Unable to retrieve firewall details.') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): firewall = self._get_object() @@ -229,17 +230,17 @@ class InsertRuleToPolicyView(forms.ModalFormView): context['name'] = obj.name return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - policy_id = self.kwargs['policy_id'] - try: - self._object = api.fwaas.policy_get(self.request, policy_id) - self._object.set_id_as_name_if_empty() - except Exception: - redirect = self.success_url - msg = _('Unable to retrieve policy details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + policy_id = self.kwargs['policy_id'] + try: + policy = api.fwaas.policy_get(self.request, policy_id) + policy.set_id_as_name_if_empty() + return policy + except Exception: + redirect = self.success_url + msg = _('Unable to retrieve policy details.') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): policy = self._get_object() @@ -263,17 +264,17 @@ class RemoveRuleFromPolicyView(forms.ModalFormView): context['name'] = obj.name return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - policy_id = self.kwargs['policy_id'] - try: - self._object = api.fwaas.policy_get(self.request, policy_id) - self._object.set_id_as_name_if_empty() - except Exception: - redirect = self.success_url - msg = _('Unable to retrieve policy details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + policy_id = self.kwargs['policy_id'] + try: + policy = api.fwaas.policy_get(self.request, policy_id) + policy.set_id_as_name_if_empty() + return policy + except Exception: + redirect = self.success_url + msg = _('Unable to retrieve policy details.') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): policy = self._get_object() diff --git a/openstack_dashboard/dashboards/project/images_and_snapshots/images/views.py b/openstack_dashboard/dashboards/project/images_and_snapshots/images/views.py index e38bfc513a..334edab44f 100644 --- a/openstack_dashboard/dashboards/project/images_and_snapshots/images/views.py +++ b/openstack_dashboard/dashboards/project/images_and_snapshots/images/views.py @@ -28,6 +28,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tabs +from horizon.utils import memoized from openstack_dashboard import api @@ -49,16 +50,14 @@ class UpdateView(forms.ModalFormView): template_name = 'project/images_and_snapshots/images/update.html' success_url = reverse_lazy("horizon:project:images_and_snapshots:index") + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - self._object = api.glance.image_get(self.request, - self.kwargs['image_id']) - except Exception: - msg = _('Unable to retrieve image.') - url = reverse('horizon:project:images_and_snapshots:index') - exceptions.handle(self.request, msg, redirect=url) - return self._object + try: + return api.glance.image_get(self.request, self.kwargs['image_id']) + except Exception: + msg = _('Unable to retrieve image.') + url = reverse('horizon:project:images_and_snapshots:index') + exceptions.handle(self.request, msg, redirect=url) def get_context_data(self, **kwargs): context = super(UpdateView, self).get_context_data(**kwargs) @@ -88,18 +87,15 @@ class DetailView(tabs.TabView): context["image"] = self.get_data() return context + @memoized.memoized_method def get_data(self): - if not hasattr(self, "_image"): - try: - image_id = self.kwargs['image_id'] - self._image = api.glance.image_get(self.request, image_id) - except Exception: - url = reverse('horizon:project:images_and_snapshots:index') - exceptions.handle(self.request, - _('Unable to retrieve image details.'), - redirect=url) - - return self._image + try: + return api.glance.image_get(self.request, self.kwargs['image_id']) + except Exception: + url = reverse('horizon:project:images_and_snapshots:index') + exceptions.handle(self.request, + _('Unable to retrieve image details.'), + redirect=url) def get_tabs(self, request, *args, **kwargs): image = self.get_data() diff --git a/openstack_dashboard/dashboards/project/images_and_snapshots/snapshots/views.py b/openstack_dashboard/dashboards/project/images_and_snapshots/snapshots/views.py index cd7939c8bf..6813f61064 100644 --- a/openstack_dashboard/dashboards/project/images_and_snapshots/snapshots/views.py +++ b/openstack_dashboard/dashboards/project/images_and_snapshots/snapshots/views.py @@ -27,6 +27,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms +from horizon.utils import memoized from openstack_dashboard import api @@ -39,17 +40,16 @@ class CreateView(forms.ModalFormView): template_name = 'project/images_and_snapshots/snapshots/create.html' success_url = reverse_lazy("horizon:project:images_and_snapshots:index") + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - self._object = api.nova.server_get(self.request, - self.kwargs["instance_id"]) - except Exception: - redirect = reverse('horizon:project:instances:index') - exceptions.handle(self.request, - _("Unable to retrieve instance."), - redirect=redirect) - return self._object + try: + return api.nova.server_get(self.request, + self.kwargs["instance_id"]) + except Exception: + redirect = reverse('horizon:project:instances:index') + exceptions.handle(self.request, + _("Unable to retrieve instance."), + redirect=redirect) def get_initial(self): return {"instance_id": self.kwargs["instance_id"]} diff --git a/openstack_dashboard/dashboards/project/images_and_snapshots/views.py b/openstack_dashboard/dashboards/project/images_and_snapshots/views.py index 819b451289..408cb3fac7 100644 --- a/openstack_dashboard/dashboards/project/images_and_snapshots/views.py +++ b/openstack_dashboard/dashboards/project/images_and_snapshots/views.py @@ -29,6 +29,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import tables from horizon import tabs +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.api import base @@ -95,19 +96,16 @@ class DetailView(tabs.TabView): context["snapshot"] = self.get_data() return context + @memoized.memoized_method def get_data(self): - if not hasattr(self, "_snapshot"): - try: - snapshot_id = self.kwargs['snapshot_id'] - self._snapshot = api.cinder.volume_snapshot_get(self.request, - snapshot_id) - except Exception: - url = reverse('horizon:project:images_and_snapshots:index') - exceptions.handle(self.request, - _('Unable to retrieve snapshot details.'), - redirect=url) - - return self._snapshot + try: + snapshot_id = self.kwargs['snapshot_id'] + return api.cinder.volume_snapshot_get(self.request, snapshot_id) + except Exception: + url = reverse('horizon:project:images_and_snapshots:index') + exceptions.handle(self.request, + _('Unable to retrieve snapshot details.'), + redirect=url) def get_tabs(self, request, *args, **kwargs): snapshot = self.get_data() diff --git a/openstack_dashboard/dashboards/project/instances/views.py b/openstack_dashboard/dashboards/project/instances/views.py index c7556f309f..55050f9e16 100644 --- a/openstack_dashboard/dashboards/project/instances/views.py +++ b/openstack_dashboard/dashboards/project/instances/views.py @@ -32,6 +32,7 @@ from horizon import exceptions from horizon import forms from horizon import tables from horizon import tabs +from horizon.utils import memoized from horizon import workflows from openstack_dashboard import api @@ -172,16 +173,15 @@ class UpdateView(workflows.WorkflowView): context["instance_id"] = self.kwargs['instance_id'] return context + @memoized.memoized_method def get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - instance_id = self.kwargs['instance_id'] - try: - self._object = api.nova.server_get(self.request, instance_id) - except Exception: - redirect = reverse("horizon:project:instances:index") - msg = _('Unable to retrieve instance details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + instance_id = self.kwargs['instance_id'] + try: + return api.nova.server_get(self.request, instance_id) + except Exception: + redirect = reverse("horizon:project:instances:index") + msg = _('Unable to retrieve instance details.') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): initial = super(UpdateView, self).get_initial() @@ -214,27 +214,26 @@ class DetailView(tabs.TabView): context["instance"] = self.get_data() return context + @memoized.memoized_method def get_data(self): - if not hasattr(self, "_instance"): - try: - instance_id = self.kwargs['instance_id'] - instance = api.nova.server_get(self.request, instance_id) - instance.volumes = api.nova.instance_volumes_list(self.request, - instance_id) - # Sort by device name - instance.volumes.sort(key=lambda vol: vol.device) - instance.full_flavor = api.nova.flavor_get( - self.request, instance.flavor["id"]) - instance.security_groups = api.network.server_security_groups( - self.request, instance_id) - except Exception: - redirect = reverse('horizon:project:instances:index') - exceptions.handle(self.request, - _('Unable to retrieve details for ' - 'instance "%s".') % instance_id, - redirect=redirect) - self._instance = instance - return self._instance + try: + instance_id = self.kwargs['instance_id'] + instance = api.nova.server_get(self.request, instance_id) + instance.volumes = api.nova.instance_volumes_list(self.request, + instance_id) + # Sort by device name + instance.volumes.sort(key=lambda vol: vol.device) + instance.full_flavor = api.nova.flavor_get( + self.request, instance.flavor["id"]) + instance.security_groups = api.network.server_security_groups( + self.request, instance_id) + except Exception: + redirect = reverse('horizon:project:instances:index') + exceptions.handle(self.request, + _('Unable to retrieve details for ' + 'instance "%s".') % instance_id, + redirect=redirect) + return instance def get_tabs(self, request, *args, **kwargs): instance = self.get_data() @@ -250,35 +249,33 @@ class ResizeView(workflows.WorkflowView): context["instance_id"] = self.kwargs['instance_id'] return context + @memoized.memoized_method def get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - instance_id = self.kwargs['instance_id'] - try: - self._object = api.nova.server_get(self.request, instance_id) - flavor_id = self._object.flavor['id'] - flavors = self.get_flavors() - if flavor_id in flavors: - self._object.flavor_name = flavors[flavor_id].name - else: - flavor = api.nova.flavor_get(self.request, flavor_id) - self._object.flavor_name = flavor.name - except Exception: - redirect = reverse("horizon:project:instances:index") - msg = _('Unable to retrieve instance details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + instance_id = self.kwargs['instance_id'] + try: + instance = api.nova.server_get(self.request, instance_id) + flavor_id = instance.flavor['id'] + flavors = self.get_flavors() + if flavor_id in flavors: + instance.flavor_name = flavors[flavor_id].name + else: + flavor = api.nova.flavor_get(self.request, flavor_id) + instance.flavor_name = flavor.name + except Exception: + redirect = reverse("horizon:project:instances:index") + msg = _('Unable to retrieve instance details.') + exceptions.handle(self.request, msg, redirect=redirect) + return instance + @memoized.memoized_method def get_flavors(self, *args, **kwargs): - if not hasattr(self, "_flavors"): - try: - flavors = api.nova.flavor_list(self.request) - self._flavors = SortedDict([(str(flavor.id), flavor) - for flavor in flavors]) - except Exception: - redirect = reverse("horizon:project:instances:index") - exceptions.handle(self.request, - _('Unable to retrieve flavors.'), redirect=redirect) - return self._flavors + try: + flavors = api.nova.flavor_list(self.request) + return SortedDict((str(flavor.id), flavor) for flavor in flavors) + except Exception: + redirect = reverse("horizon:project:instances:index") + exceptions.handle(self.request, + _('Unable to retrieve flavors.'), redirect=redirect) def get_initial(self): initial = super(ResizeView, self).get_initial() diff --git a/openstack_dashboard/dashboards/project/loadbalancers/views.py b/openstack_dashboard/dashboards/project/loadbalancers/views.py index d4ef769cea..e25c10611b 100644 --- a/openstack_dashboard/dashboards/project/loadbalancers/views.py +++ b/openstack_dashboard/dashboards/project/loadbalancers/views.py @@ -21,6 +21,7 @@ from horizon import exceptions from horizon import forms from horizon import messages from horizon import tabs +from horizon.utils import memoized from horizon import workflows from openstack_dashboard import api @@ -162,16 +163,15 @@ class UpdatePoolView(forms.ModalFormView): context["pool_id"] = self.kwargs['pool_id'] return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - pool_id = self.kwargs['pool_id'] - try: - self._object = api.lbaas.pool_get(self.request, pool_id) - except Exception as e: - redirect = self.success_url - msg = _('Unable to retrieve pool details. %s') % e - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + pool_id = self.kwargs['pool_id'] + try: + return api.lbaas.pool_get(self.request, pool_id) + except Exception as e: + redirect = self.success_url + msg = _('Unable to retrieve pool details. %s') % e + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): pool = self._get_object() @@ -193,16 +193,15 @@ class UpdateVipView(forms.ModalFormView): context["vip_id"] = self.kwargs['vip_id'] return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - vip_id = self.kwargs['vip_id'] - try: - self._object = api.lbaas.vip_get(self.request, vip_id) - except Exception as e: - redirect = self.success_url - msg = _('Unable to retrieve VIP details. %s') % e - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + vip_id = self.kwargs['vip_id'] + try: + return api.lbaas.vip_get(self.request, vip_id) + except Exception as e: + redirect = self.success_url + msg = _('Unable to retrieve VIP details. %s') % e + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): vip = self._get_object() @@ -238,16 +237,15 @@ class UpdateMemberView(forms.ModalFormView): context["member_id"] = self.kwargs['member_id'] return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - member_id = self.kwargs['member_id'] - try: - self._object = api.lbaas.member_get(self.request, member_id) - except Exception as e: - redirect = self.success_url - msg = _('Unable to retrieve member details. %s') % e - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + member_id = self.kwargs['member_id'] + try: + return api.lbaas.member_get(self.request, member_id) + except Exception as e: + redirect = self.success_url + msg = _('Unable to retrieve member details. %s') % e + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): member = self._get_object() @@ -268,17 +266,15 @@ class UpdateMonitorView(forms.ModalFormView): context["monitor_id"] = self.kwargs['monitor_id'] return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - monitor_id = self.kwargs['monitor_id'] - try: - self._object = api.lbaas.pool_health_monitor_get( - self.request, monitor_id) - except Exception as e: - redirect = self.success_url - msg = _('Unable to retrieve health monitor details. %s') % e - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + monitor_id = self.kwargs['monitor_id'] + try: + return api.lbaas.pool_health_monitor_get(self.request, monitor_id) + except Exception as e: + redirect = self.success_url + msg = _('Unable to retrieve health monitor details. %s') % e + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): monitor = self._get_object() diff --git a/openstack_dashboard/dashboards/project/networks/ports/views.py b/openstack_dashboard/dashboards/project/networks/ports/views.py index bdc23ed2ab..a2b6b0b17f 100644 --- a/openstack_dashboard/dashboards/project/networks/ports/views.py +++ b/openstack_dashboard/dashboards/project/networks/ports/views.py @@ -20,6 +20,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tabs +from horizon.utils import memoized from openstack_dashboard import api @@ -44,17 +45,16 @@ class UpdateView(forms.ModalFormView): return reverse(self.success_url, args=(self.kwargs['network_id'],)) + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - port_id = self.kwargs['port_id'] - try: - self._object = api.neutron.port_get(self.request, port_id) - except Exception: - redirect = reverse("horizon:project:networks:detail", - args=(self.kwargs['network_id'],)) - msg = _('Unable to retrieve port details') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + port_id = self.kwargs['port_id'] + try: + return api.neutron.port_get(self.request, port_id) + except Exception: + redirect = reverse("horizon:project:networks:detail", + args=(self.kwargs['network_id'],)) + msg = _('Unable to retrieve port details') + exceptions.handle(self.request, msg, redirect=redirect) def get_context_data(self, **kwargs): context = super(UpdateView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/project/networks/subnets/tables.py b/openstack_dashboard/dashboards/project/networks/subnets/tables.py index 4db6a953ad..3e89169d81 100644 --- a/openstack_dashboard/dashboards/project/networks/subnets/tables.py +++ b/openstack_dashboard/dashboards/project/networks/subnets/tables.py @@ -22,6 +22,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import tables +from horizon.utils import memoized from openstack_dashboard import api @@ -87,18 +88,17 @@ class SubnetsTable(tables.DataTable): gateway_ip = tables.Column("gateway_ip", verbose_name=_("Gateway IP")) failure_url = reverse_lazy('horizon:project:networks:index') + @memoized.memoized_method def _get_network(self): - if not hasattr(self, "_network"): - try: - network_id = self.kwargs['network_id'] - network = api.neutron.network_get(self.request, network_id) - network.set_id_as_name_if_empty(length=0) - except Exception: - msg = _('Unable to retrieve details for network "%s".') \ - % (network_id) - exceptions.handle(self.request, msg, redirect=self.failure_url) - self._network = network - return self._network + try: + network_id = self.kwargs['network_id'] + network = api.neutron.network_get(self.request, network_id) + network.set_id_as_name_if_empty(length=0) + except Exception: + msg = _('Unable to retrieve details for network "%s".') \ + % (network_id) + exceptions.handle(self.request, msg, redirect=self.failure_url) + return network class Meta: name = "subnets" diff --git a/openstack_dashboard/dashboards/project/networks/subnets/views.py b/openstack_dashboard/dashboards/project/networks/subnets/views.py index 57f9bd4d00..855c2815a7 100644 --- a/openstack_dashboard/dashboards/project/networks/subnets/views.py +++ b/openstack_dashboard/dashboards/project/networks/subnets/views.py @@ -22,6 +22,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import tabs +from horizon.utils import memoized from horizon import workflows from openstack_dashboard import api @@ -35,18 +36,17 @@ from openstack_dashboard.dashboards.project.networks.subnets \ class CreateView(workflows.WorkflowView): workflow_class = project_workflows.CreateSubnet + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - network_id = self.kwargs["network_id"] - self._object = api.neutron.network_get(self.request, - network_id) - self._object.set_id_as_name_if_empty() - except Exception: - redirect = reverse('horizon:project:networks:index') - msg = _("Unable to retrieve network.") - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + try: + network_id = self.kwargs["network_id"] + network = api.neutron.network_get(self.request, network_id) + network.set_id_as_name_if_empty() + return network + except Exception: + redirect = reverse('horizon:project:networks:index') + msg = _("Unable to retrieve network.") + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): network = self.get_object() @@ -57,16 +57,15 @@ class CreateView(workflows.WorkflowView): class UpdateView(workflows.WorkflowView): workflow_class = project_workflows.UpdateSubnet + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - subnet_id = self.kwargs['subnet_id'] - try: - self._object = api.neutron.subnet_get(self.request, subnet_id) - except Exception: - redirect = reverse("horizon:project:networks:index") - msg = _('Unable to retrieve subnet details') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + subnet_id = self.kwargs['subnet_id'] + try: + return api.neutron.subnet_get(self.request, subnet_id) + except Exception: + redirect = reverse("horizon:project:networks:index") + msg = _('Unable to retrieve subnet details') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): initial = super(UpdateView, self).get_initial() diff --git a/openstack_dashboard/dashboards/project/networks/views.py b/openstack_dashboard/dashboards/project/networks/views.py index 179e16658d..bc4ba3da31 100644 --- a/openstack_dashboard/dashboards/project/networks/views.py +++ b/openstack_dashboard/dashboards/project/networks/views.py @@ -23,6 +23,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tables +from horizon.utils import memoized from horizon import workflows from openstack_dashboard import api @@ -75,17 +76,15 @@ class UpdateView(forms.ModalFormView): context["network_id"] = self.kwargs['network_id'] return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - network_id = self.kwargs['network_id'] - try: - self._object = api.neutron.network_get(self.request, - network_id) - except Exception: - redirect = self.success_url - msg = _('Unable to retrieve network details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + network_id = self.kwargs['network_id'] + try: + return api.neutron.network_get(self.request, network_id) + except Exception: + redirect = self.success_url + msg = _('Unable to retrieve network details.') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): network = self._get_object() @@ -125,18 +124,17 @@ class DetailView(tables.MultiTableView): p.set_id_as_name_if_empty() return ports + @memoized.memoized_method def _get_data(self): - if not hasattr(self, "_network"): - try: - network_id = self.kwargs['network_id'] - network = api.neutron.network_get(self.request, network_id) - network.set_id_as_name_if_empty(length=0) - except Exception: - msg = _('Unable to retrieve details for network "%s".') \ - % (network_id) - exceptions.handle(self.request, msg, redirect=self.failure_url) - self._network = network - return self._network + try: + network_id = self.kwargs['network_id'] + network = api.neutron.network_get(self.request, network_id) + network.set_id_as_name_if_empty(length=0) + except Exception: + msg = _('Unable to retrieve details for network "%s".') \ + % (network_id) + exceptions.handle(self.request, msg, redirect=self.failure_url) + return network def get_context_data(self, **kwargs): context = super(DetailView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/project/routers/extensions/routerrules/views.py b/openstack_dashboard/dashboards/project/routers/extensions/routerrules/views.py index 935b150691..0658ae4c31 100644 --- a/openstack_dashboard/dashboards/project/routers/extensions/routerrules/views.py +++ b/openstack_dashboard/dashboards/project/routers/extensions/routerrules/views.py @@ -21,6 +21,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.dashboards.project.routers.extensions.routerrules\ @@ -40,17 +41,15 @@ class AddRouterRuleView(forms.ModalFormView): return reverse(self.success_url, args=(self.kwargs['router_id'],)) + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - router_id = self.kwargs["router_id"] - self._object = api.neutron.router_get(self.request, - router_id) - except Exception: - redirect = reverse(self.failure_url, args=[router_id]) - msg = _("Unable to retrieve router.") - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + try: + router_id = self.kwargs["router_id"] + return api.neutron.router_get(self.request, router_id) + except Exception: + redirect = reverse(self.failure_url, args=[router_id]) + msg = _("Unable to retrieve router.") + exceptions.handle(self.request, msg, redirect=redirect) def get_context_data(self, **kwargs): context = super(AddRouterRuleView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/project/routers/ports/views.py b/openstack_dashboard/dashboards/project/routers/ports/views.py index e6eb8727a2..175ad49b20 100644 --- a/openstack_dashboard/dashboards/project/routers/ports/views.py +++ b/openstack_dashboard/dashboards/project/routers/ports/views.py @@ -20,6 +20,7 @@ from django.utils.translation import ugettext_lazy as _ # noqa from horizon import exceptions from horizon import forms from horizon import tabs +from horizon.utils import memoized from openstack_dashboard import api @@ -39,17 +40,15 @@ class AddInterfaceView(forms.ModalFormView): return reverse(self.success_url, args=(self.kwargs['router_id'],)) + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - router_id = self.kwargs["router_id"] - self._object = api.neutron.router_get(self.request, - router_id) - except Exception: - redirect = reverse(self.failure_url, args=[router_id]) - msg = _("Unable to retrieve router.") - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + try: + router_id = self.kwargs["router_id"] + return api.neutron.router_get(self.request, router_id) + except Exception: + redirect = reverse(self.failure_url, args=[router_id]) + msg = _("Unable to retrieve router.") + exceptions.handle(self.request, msg, redirect=redirect) def get_context_data(self, **kwargs): context = super(AddInterfaceView, self).get_context_data(**kwargs) @@ -71,17 +70,15 @@ class SetGatewayView(forms.ModalFormView): def get_success_url(self): return reverse(self.success_url) + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - try: - router_id = self.kwargs["router_id"] - self._object = api.neutron.router_get(self.request, - router_id) - except Exception: - redirect = reverse(self.failure_url) - msg = _("Unable to set gateway.") - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + try: + router_id = self.kwargs["router_id"] + return api.neutron.router_get(self.request, router_id) + except Exception: + redirect = reverse(self.failure_url) + msg = _("Unable to set gateway.") + exceptions.handle(self.request, msg, redirect=redirect) def get_context_data(self, **kwargs): context = super(SetGatewayView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/project/routers/views.py b/openstack_dashboard/dashboards/project/routers/views.py index 22ac9e3646..b3ebb835f4 100644 --- a/openstack_dashboard/dashboards/project/routers/views.py +++ b/openstack_dashboard/dashboards/project/routers/views.py @@ -27,6 +27,7 @@ from horizon import exceptions from horizon import forms from horizon import tables from horizon import tabs +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.dashboards.project.routers\ import forms as project_forms @@ -90,31 +91,29 @@ class DetailView(tabs.TabbedTableView): template_name = 'project/routers/detail.html' failure_url = reverse_lazy('horizon:project:routers:index') + @memoized.memoized_method def _get_data(self): - if not hasattr(self, "_router"): + try: + router_id = self.kwargs['router_id'] + router = api.neutron.router_get(self.request, router_id) + router.set_id_as_name_if_empty(length=0) + except Exception: + msg = _('Unable to retrieve details for router "%s".') \ + % (router_id) + exceptions.handle(self.request, msg, redirect=self.failure_url) + if router.external_gateway_info: + ext_net_id = router.external_gateway_info['network_id'] try: - router_id = self.kwargs['router_id'] - router = api.neutron.router_get(self.request, router_id) - router.set_id_as_name_if_empty(length=0) + ext_net = api.neutron.network_get(self.request, ext_net_id, + expand_subnet=False) + ext_net.set_id_as_name_if_empty(length=0) + router.external_gateway_info['network'] = ext_net.name except Exception: - msg = _('Unable to retrieve details for router "%s".') \ - % (router_id) - exceptions.handle(self.request, msg, redirect=self.failure_url) - if router.external_gateway_info: - ext_net_id = router.external_gateway_info['network_id'] - try: - ext_net = api.neutron.network_get(self.request, ext_net_id, - expand_subnet=False) - ext_net.set_id_as_name_if_empty(length=0) - router.external_gateway_info['network'] = ext_net.name - except Exception: - msg = _('Unable to retrieve an external network "%s".') \ - % (ext_net_id) - exceptions.handle(self.request, msg) - router.external_gateway_info['network'] = ext_net_id - - self._router = router - return self._router + msg = _('Unable to retrieve an external network "%s".') \ + % (ext_net_id) + exceptions.handle(self.request, msg) + router.external_gateway_info['network'] = ext_net_id + return router def get_context_data(self, **kwargs): context = super(DetailView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/project/stacks/views.py b/openstack_dashboard/dashboards/project/stacks/views.py index 5595cb0a68..b0e006a545 100644 --- a/openstack_dashboard/dashboards/project/stacks/views.py +++ b/openstack_dashboard/dashboards/project/stacks/views.py @@ -19,6 +19,7 @@ from horizon import exceptions from horizon import forms from horizon import tables from horizon import tabs +from horizon.utils import memoized from django.core.urlresolvers import reverse # noqa from django.core.urlresolvers import reverse_lazy # noqa @@ -100,19 +101,18 @@ class DetailView(tabs.TabView): context["stack"] = self.get_data(self.request) return context + @memoized.memoized_method def get_data(self, request, **kwargs): - if not hasattr(self, "_stack"): - stack_id = kwargs['stack_id'] - try: - stack = api.heat.stack_get(request, stack_id) - self._stack = stack - request.session['stack_id'] = stack.id - request.session['stack_name'] = stack.stack_name - except Exception: - msg = _("Unable to retrieve stack.") - redirect = reverse('horizon:project:stacks:index') - exceptions.handle(request, msg, redirect=redirect) - return self._stack + stack_id = kwargs['stack_id'] + try: + stack = api.heat.stack_get(request, stack_id) + request.session['stack_id'] = stack.id + request.session['stack_name'] = stack.stack_name + return stack + except Exception: + msg = _("Unable to retrieve stack.") + redirect = reverse('horizon:project:stacks:index') + exceptions.handle(request, msg, redirect=redirect) def get_tabs(self, request, **kwargs): stack = self.get_data(request, **kwargs) @@ -129,33 +129,31 @@ class ResourceView(tabs.TabView): context["metadata"] = self.get_metadata(self.request, **kwargs) return context + @memoized.memoized_method def get_data(self, request, **kwargs): - if not hasattr(self, "_resource"): - try: - resource = api.heat.resource_get( - request, - kwargs['stack_id'], - kwargs['resource_name']) - self._resource = resource - except Exception: - msg = _("Unable to retrieve resource.") - redirect = reverse('horizon:project:stacks:index') - exceptions.handle(request, msg, redirect=redirect) - return self._resource + try: + resource = api.heat.resource_get( + request, + kwargs['stack_id'], + kwargs['resource_name']) + return resource + except Exception: + msg = _("Unable to retrieve resource.") + redirect = reverse('horizon:project:stacks:index') + exceptions.handle(request, msg, redirect=redirect) + @memoized.memoized_method def get_metadata(self, request, **kwargs): - if not hasattr(self, "_metadata"): - try: - metadata = api.heat.resource_metadata_get( - request, - kwargs['stack_id'], - kwargs['resource_name']) - self._metadata = json.dumps(metadata, indent=2) - except Exception: - msg = _("Unable to retrieve metadata.") - redirect = reverse('horizon:project:stacks:index') - exceptions.handle(request, msg, redirect=redirect) - return self._metadata + try: + metadata = api.heat.resource_metadata_get( + request, + kwargs['stack_id'], + kwargs['resource_name']) + return json.dumps(metadata, indent=2) + except Exception: + msg = _("Unable to retrieve metadata.") + redirect = reverse('horizon:project:stacks:index') + exceptions.handle(request, msg, redirect=redirect) def get_tabs(self, request, **kwargs): resource = self.get_data(request, **kwargs) diff --git a/openstack_dashboard/dashboards/project/volumes/views.py b/openstack_dashboard/dashboards/project/volumes/views.py index a02b4f7a78..89a7584ecb 100644 --- a/openstack_dashboard/dashboards/project/volumes/views.py +++ b/openstack_dashboard/dashboards/project/volumes/views.py @@ -27,6 +27,7 @@ from horizon import exceptions from horizon import forms from horizon import tables from horizon import tabs +from horizon.utils import memoized from openstack_dashboard import api from openstack_dashboard.api import cinder @@ -97,21 +98,20 @@ class DetailView(tabs.TabView): context["volume"] = self.get_data() return context + @memoized.memoized_method def get_data(self): - if not hasattr(self, "_volume"): - try: - volume_id = self.kwargs['volume_id'] - self._volume = cinder.volume_get(self.request, volume_id) - for att in self._volume.attachments: - att['instance'] = api.nova.server_get(self.request, - att['server_id']) - except Exception: - redirect = reverse('horizon:project:volumes:index') - exceptions.handle(self.request, - _('Unable to retrieve volume details.'), - redirect=redirect) - - return self._volume + try: + volume_id = self.kwargs['volume_id'] + volume = cinder.volume_get(self.request, volume_id) + for att in volume.attachments: + att['instance'] = api.nova.server_get(self.request, + att['server_id']) + except Exception: + redirect = reverse('horizon:project:volumes:index') + exceptions.handle(self.request, + _('Unable to retrieve volume details.'), + redirect=redirect) + return volume def get_tabs(self, request, *args, **kwargs): volume = self.get_data() @@ -156,16 +156,15 @@ class EditAttachmentsView(tables.DataTableView, forms.ModalFormView): template_name = 'project/volumes/attach.html' success_url = reverse_lazy("horizon:project:volumes:index") + @memoized.memoized_method def get_object(self): - if not hasattr(self, "_object"): - volume_id = self.kwargs['volume_id'] - try: - self._object = cinder.volume_get(self.request, volume_id) - except Exception: - self._object = None - exceptions.handle(self.request, - _('Unable to retrieve volume information.')) - return self._object + volume_id = self.kwargs['volume_id'] + try: + return cinder.volume_get(self.request, volume_id) + except Exception: + self._object = None + exceptions.handle(self.request, + _('Unable to retrieve volume information.')) def get_data(self): try: @@ -187,11 +186,10 @@ class EditAttachmentsView(tables.DataTableView, forms.ModalFormView): return {'volume': self.get_object(), 'instances': instances} + @memoized.memoized_method def get_form(self): - if not hasattr(self, "_form"): - form_class = self.get_form_class() - self._form = super(EditAttachmentsView, self).get_form(form_class) - return self._form + form_class = self.get_form_class() + return super(EditAttachmentsView, self).get_form(form_class) def get_context_data(self, **kwargs): context = super(EditAttachmentsView, self).get_context_data(**kwargs) diff --git a/openstack_dashboard/dashboards/router/nexus1000v/views.py b/openstack_dashboard/dashboards/router/nexus1000v/views.py index f4c072b86a..30408a96e7 100644 --- a/openstack_dashboard/dashboards/router/nexus1000v/views.py +++ b/openstack_dashboard/dashboards/router/nexus1000v/views.py @@ -25,6 +25,7 @@ from horizon import exceptions from horizon import forms from horizon import tables from horizon import tabs +from horizon.utils import memoized from openstack_dashboard import api @@ -119,18 +120,18 @@ class UpdateNetworkProfileView(forms.ModalFormView): context["profile_id"] = self.kwargs['profile_id'] return context + @memoized.memoized_method def _get_object(self, *args, **kwargs): - if not hasattr(self, "_object"): - profile_id = self.kwargs['profile_id'] - try: - self._object = api.neutron.profile_get(self.request, - profile_id) - LOG.debug("Network Profile object=%s", self._object) - except Exception: - redirect = self.success_url - msg = _('Unable to retrieve network profile details.') - exceptions.handle(self.request, msg, redirect=redirect) - return self._object + profile_id = self.kwargs['profile_id'] + try: + profile = api.neutron.profile_get(self.request, + profile_id) + LOG.debug("Network Profile object=%s", profile) + return profile + except Exception: + redirect = self.success_url + msg = _('Unable to retrieve network profile details.') + exceptions.handle(self.request, msg, redirect=redirect) def get_initial(self): profile = self._get_object()